6.2 KiB
6.2 KiB
Ads Tracking Service Architecture / Kiến Trúc Dịch Vụ Theo Dõi Quảng Cáo
Tổng Quan / Overview
graph TB
subgraph "Tracking Sources"
PIX[Website Pixel]
SDK[Mobile SDK]
API[Server-side API]
end
subgraph "ads-tracking-service"
EVT[Event Ingestion]
ATTR[Attribution Engine]
STORE[(TimescaleDB)]
end
subgraph "Output"
ANAL[ads-analytics]
BILL[ads-billing]
end
PIX --> EVT
SDK --> EVT
API --> EVT
EVT --> STORE
EVT --> ATTR
ATTR --> ANAL
ATTR --> BILL
Domain Aggregates
TrackingPixelAggregate
- TrackingPixel (Root): Unique pixel per advertiser
- PixelEvent: PageView, AddToCart, Purchase, Lead
ConversionAggregate
- Conversion (Root): Actual conversion event
- ConversionValue: Revenue amount
- ConversionWindow: 1-day, 7-day, 28-day
AttributionAggregate
- Attribution (Root): Links conversion to ad
- AttributionModel: Last-click, First-click, Linear
- TouchPoint: Each ad interaction in journey
Attribution Logic
┌─────────────────────────────────────────────────────────────────┐
│ ATTRIBUTION FLOW │
├─────────────────────────────────────────────────────────────────┤
│ │
│ User Journey: │
│ ──────────── │
│ Day 1: See Ad A (impression) │
│ Day 3: Click Ad B │
│ Day 5: Click Ad C │
│ Day 6: Purchase $100 │
│ │
│ Attribution Models: │
│ ────────────────── │
│ Last-click: Ad C = 100% │
│ First-click: Ad B = 100% │
│ Linear: Ad B = 50%, Ad C = 50% │
│ Time-decay: Ad B = 25%, Ad C = 75% │
│ │
└─────────────────────────────────────────────────────────────────┘
Database Schema (TimescaleDB)
-- Pixels
CREATE TABLE tracking_pixels (
id UUID PRIMARY KEY,
advertiser_id UUID NOT NULL,
pixel_code VARCHAR(50) UNIQUE,
domain VARCHAR(255),
created_at TIMESTAMP DEFAULT NOW()
);
-- Events (hypertable for time-series)
CREATE TABLE pixel_events (
id UUID,
pixel_id UUID REFERENCES tracking_pixels(id),
event_type VARCHAR(50), -- 'PageView', 'AddToCart', 'Purchase'
event_data JSONB,
user_id VARCHAR(255),
session_id VARCHAR(255),
event_time TIMESTAMPTZ NOT NULL
);
SELECT create_hypertable('pixel_events', 'event_time');
-- Ad interactions (for attribution)
CREATE TABLE ad_interactions (
id UUID PRIMARY KEY,
user_id VARCHAR(255),
ad_id UUID,
campaign_id UUID,
interaction_type VARCHAR(20), -- 'impression', 'click'
interaction_time TIMESTAMPTZ NOT NULL
);
-- Conversions with attribution
CREATE TABLE conversions (
id UUID PRIMARY KEY,
pixel_event_id UUID,
attributed_ad_id UUID,
attributed_campaign_id UUID,
attribution_model VARCHAR(50),
conversion_value DECIMAL(18, 2),
converted_at TIMESTAMPTZ
);
Attribution Window Settings
| Setting | Click Window | View Window |
|---|---|---|
| 7/1 (default) | 7 days | 1 day |
| 7/0 | 7 days | None |
| 28/1 | 28 days | 1 day |
| 1/1 | 1 day | 1 day |
Pixel Integration Code
<!-- Website Pixel -->
<script>
!function(g,o,od,go){
g.ggq=g.ggq||[];
var n=o.createElement('script');
n.async=1;
n.src='https://tracking.goodgo.com/pixel.js';
o.body.appendChild(n)
}(window,document);
ggq('init', 'PX-XXXXXX');
ggq('track', 'PageView');
</script>
<!-- Track Purchase -->
<script>
ggq('track', 'Purchase', {
value: 99.99,
currency: 'VND',
order_id: 'ORD-12345'
});
</script>
Server-side Conversion API
/// <summary>
/// EN: Server-side conversion tracking.
/// VI: Tracking conversion phía server.
/// </summary>
[HttpPost("events/server")]
public async Task<ActionResult> TrackServerEvent(
[FromBody] ServerEventRequest request)
{
// EN: More reliable than pixel (no ad blockers)
// VI: Đáng tin cậy hơn pixel (không bị ad blocker)
var result = await _mediator.Send(new TrackServerEventCommand
{
PixelId = request.PixelId,
EventType = request.EventType,
EventData = request.EventData,
UserId = request.UserId, // hashed
EventTime = request.EventTime
});
return Ok(result);
}
Integration Events
// Consume from ads-serving
public record AdImpressionTrackedEvent(
Guid AdId, string UserId, string Placement, DateTime TrackedAt);
public record AdClickTrackedEvent(
Guid AdId, string UserId, string DestinationUrl, DateTime TrackedAt);
// Publish to ads-analytics
public record ConversionAttributedEvent(
Guid ConversionId, Guid AdId, Guid CampaignId,
decimal ConversionValue, string AttributionModel);
API Endpoints
| Method | Endpoint | Description |
|---|---|---|
GET |
/api/v1/ads-tracking/pixels/{advertiserId} |
Get pixel code |
POST |
/api/v1/ads-tracking/events |
Track pixel event |
POST |
/api/v1/ads-tracking/events/server |
Server-side event |
GET |
/api/v1/ads-tracking/conversions |
List conversions |