Skip to content

Add auction timeline offsets spec amendment - #1076

Open
jevansnyc wants to merge 4 commits into
feat/request-phase-timingfrom
spec/auction-timeline-offsets
Open

Add auction timeline offsets spec amendment#1076
jevansnyc wants to merge 4 commits into
feat/request-phase-timingfrom
spec/auction-timeline-offsets

Conversation

@jevansnyc

@jevansnyc jevansnyc commented Aug 26, 2026

Copy link
Copy Markdown
Collaborator

Spec-first follow-up to #1074, targeting the feature branch so it lands with (or after) the base spec rather than against main.

Adds section 18 to the request phase timing design: three T0-anchored auction milestones so the auction's timeline and the request's timeline finally share a clock.

Problem

Two clocks that never meet: auction_events_raw measures the auction internally (total_time_ms, per-provider provider_response_time_ms) on a clock that starts at auction creation; the access row is T0-anchored but only records auction_wait_ms (blocked time at collect). Nothing can answer: when did the auction start relative to request entry, when did the final bid land, and when was targeting committed toward GAM.

Design

  • Three first-call-wins marks on RequestTimings (same style as mark_headers_ready()): dispatched (bid requests left the edge), resolved (final bid or timeout), committed (write_bids_to_state returned; targeting available to the response pipeline in both buffered and streaming modes).
  • Four additive columns on access_logs_raw: auction_dispatched_ms / auction_resolved_ms / auction_committed_ms (Nullable UInt32; null = no auction ran) plus auction_id (join key to the per-bidder auction dataset; none sentinel).
  • No header emission, no config surface, no new emission path: values ride the existing snapshot and the existing tinybird.access_enabled gate. Additive schema evolution with JSONPaths + FORWARD_QUERY, checked with tb --cloud deploy --check.
  • "Committed toward GAM" is defined as edge-side commit: TS never calls GAM server-side; the browser GPT call carries the targeting, and that half of the timeline stays client-measured.

Why it matters

This is the overlap proof: a client-side wrapper cannot dispatch until the browser boots (t~3000ms on measured prospect pages); the server-side auction dispatches while the origin fetch is in flight. One access row then reads as a timeline (dispatch at t=D, resolve at t=R, commit at t=C, headers at t=H), with R - D joining per-bidder detail via auction_id, and auction_wait_ms finally interpretable next to it: (R - D) - auction_wait_ms approximates how much of the auction was absorbed by work the request needed anyway.

Update: implementation is included in this PR (per owner direction), as separate commits on top of the spec: the three marks on RequestTimings, the publisher call sites, the four row columns, and the datasource evolution (validated with tb --cloud deploy --check; the FORWARD_QUERY triggers a backfill at promotion, acceptable at current volume and required for the none sentinel on pre-existing rows). All CI gates pass locally.

🤖 Generated with Claude Code

Adds section 18 to the request phase timing spec: three first-call-wins
T0 offsets (auction dispatched, resolved, committed) on RequestTimings,
emitted as additive nullable columns on access_logs_raw with auction_id
as the join key to the per-bidder auction dataset. Answers the
overlap-proof questions the two existing clocks cannot: when the
auction started relative to request entry, when the final bid landed,
and when targeting was committed toward GAM.
Implements spec section 18: three first-call-wins marks on
RequestTimings (dispatched at the DispatchAuctionOutcome::Dispatched
arm, resolved after collect at both sites, committed after
write_bids_to_state at both sites), carried through TimingSnapshot into
four additive access_logs_raw columns: auction_dispatched_ms,
auction_resolved_ms, auction_committed_ms, and auction_id as the join
key to the per-bidder auction dataset. Null offsets mean no auction
ran; a failed dispatch records nothing. FORWARD_QUERY fills the new
columns with typed defaults for pre-existing rows.

No header emission, no config surface, no adapter changes: the values
ride the existing snapshot and the tinybird.access_enabled gate.
The Cloudflare integration harness writes
wrangler.integration.generated.toml at test time; it was swept into the
previous commit by accident. Ignore it so local CI=1 runs cannot commit
it again.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant