feat(media-buy): add per-package daily_budget_cap with budget_capping capability - #5990
feat(media-buy): add per-package daily_budget_cap with budget_capping capability#5990garvitkaushik-123 wants to merge 3 commits into
Conversation
There was a problem hiding this comment.
Argus is not auto-reviewing this PR because it modifies protected paths that require human review (static/schemas/source/media-buy/get-media-buys-response.json, static/schemas/source/media-buy/package-request.json, static/schemas/source/media-buy/package-update.json, static/schemas/source/protocol/get-adcp-capabilities-response.json). A human reviewer should review and merge this PR; Argus will resume on subsequent PRs once these changes land on main.
There was a problem hiding this comment.
Argus is not auto-reviewing this PR because it modifies protected paths that require human review (static/schemas/source/core/package.json, static/schemas/source/media-buy/get-media-buys-response.json, static/schemas/source/media-buy/package-request.json, static/schemas/source/media-buy/package-update.json, static/schemas/source/protocol/get-adcp-capabilities-response.json). A human reviewer should review and merge this PR; Argus will resume on subsequent PRs once these changes land on main.
|
Release-line classification: this is a legitimate additive feature with a minor changeset, so it is queued for 3.2 rather than 3.1.5. Please keep it open pending the remaining WG ratification items; once #5984 lands, update the known-gap note when this feature is finalized. |
… capability Implements the ratification-pending design from RFC adcontextprotocol#5983. Buyers had no protocol path to bound per-day spend — only budget, pacing, and flight window, none a hard daily ceiling (the gap documented in adcontextprotocol#4429). - package-request.json / package-update.json: daily_budget_cap (number, media buy currency) + optional budget_cap_timezone override. Orthogonal to pacing. - get-media-buys-response.json: echo daily_budget_cap + resolved budget_cap_timezone per package for enforcement verification. - get-adcp-capabilities-response.json: media_buy.budget_capping capability (supported_periods, enforcement hard/soft, effective_timezone, buyer_timezone_override), modeled on frequency_capping. Undeclared support MUST reject daily_budget_cap with UNSUPPORTED_FEATURE. Timezone anchors to the seller billing boundary: effective_timezone MUST equal get_account_financials.timezone when financials are available (TZ-C). Scope is day-only; daily_impression_cap parity deferred per the RFC's open WG questions. Closes adcontextprotocol#5983
Audit follow-up. The response echo was added only to the inline package shape
in get-media-buys-response.json, so create_media_buy and update_media_buy
responses (which $ref core/package.json) did not echo the accepted cap — a
scope gap given the field must be verifiable on every read surface.
- Add daily_budget_cap + budget_cap_timezone to core/package.json (covers
create-media-buy-response and update-media-buy-response).
- Drop the invented x-echo key from get-media-buys-response (prose MUST-echo
is the contract; x-echo is not an established convention in this repo).
- Align package-update daily_budget_cap currency phrasing with its budget
sibling ("currency specified by the pricing option").
- Add a core/package.json regression case.
…et_cap field adcontextprotocol#5984 (merged) documented "no per-day cap field" as a known gap. This feature adds the field, so the note now describes daily_budget_cap — orthogonal to pacing, seller-billing-timezone boundary, capability-gated — and keeps the pacing-approximation fallback for sellers without support. Adds the field to the Budget & Pacing Controls table.
ecb4519 to
64b5044
Compare
There was a problem hiding this comment.
Argus is not auto-reviewing this PR because it modifies protected paths that require human review (static/schemas/source/core/package.json, static/schemas/source/media-buy/get-media-buys-response.json, static/schemas/source/media-buy/package-request.json, static/schemas/source/media-buy/package-update.json, static/schemas/source/protocol/get-adcp-capabilities-response.json). A human reviewer should review and merge this PR; Argus will resume on subsequent PRs once these changes land on main.
|
TZ-C captures the reconciliation issue well. Because the |
|
@sangilish — valid observation. The schema tests here confirm each response is individually well-formed, but they can't catch the cross-surface mismatch (two conformant responses that together violate the Recommendation: track separately rather than fold into this PR. Two reasons:
The right artifact is a follow-up One thing @garvitkaushik-123 could do before merge: add a Generated by Claude Code |
|
Filed #6010 as the follow-up compliance suite issue ("conformance storyboard: verify Generated by Claude Code |
Summary
Implements the Agreed (pending WG ratification) design from RFC #5983 — bokelley's Secretariat memo plus the TZ-C timezone convergence. Buyers running against client-approved daily authorizations (agency) or ROAS floors (performance) had no protocol path to bound per-day spend;
pacing: "even"is a leaky approximation that fails under mid-flight budget changes. Closes the gap documented in #4429.Changes
package-request.jsondaily_budget_cap(number, media-buy currency) + optionalbudget_cap_timezonepackage-update.jsoncore/package.jsondaily_budget_cap+ resolvedbudget_cap_timezone— this is the shapecreate-media-buy-responseandupdate-media-buy-responsereferenceget-media-buys-response.jsonget-adcp-capabilities-response.jsonmedia_buy.budget_cappingobject (supported_periods,enforcement,effective_timezone,buyer_timezone_override)Response echo lands on every read surface:
core/package.jsoncoverscreate_media_buy+update_media_buyresponses, and the inlineget_media_buyspackage shape covers reads.Design points, matching the memo:
pacing— the cap is the ceiling the pacing engine operates within;pacing: "asap"+ a cap is valid and coherent.UNSUPPORTED_FEATURE(never silent-drop), same contract asfrequency_cappingandaccount_financials.hard/soft) so buyers aren't surprised by soft-vs-hard differences.budget_capping.effective_timezone, which MUST equalget_account_financials.timezonewhen financials are available — the cross-surface consistency rule bokelley raised in the last comment. DST transition days = one local calendar day carrying the full cap. Buyer override only whenbuyer_timezone_override: true.package-update.json+ response echo are in-scope here, not a follow-up.Deliberately out of scope (open WG items in the RFC)
daily_impression_capparity — an explicit open WG vote; both experts lean defer.supported_periodsis an array so future periods (hour/week) are additive.update_media_buyaction-vocabulary mapping —daily_budget_capchanges are not mapped to a gatedavailable_actions[]entry, consistent withimpressions(also an unmapped per-package delivery control). Happy to add an action if the WG wants cap changes separately gated.This is the ratification-pending design; happy to adjust to the WG's final vote on the open items.
Test plan
test:schemas,test:examples,test:json-schemapasscomposed-schema-validationcases: acceptsdaily_budget_cap+budget_cap_timezonewithpacing: "asap"; rejects negative cap; accepts update raising the cap; Package response object echoes both fields (locks the create/update-response echo)Per @bokelley's comment: #5984 has merged, so this branch is now rebased on
mainand the create_media_buy "known gap: no daily cap" note is rewritten to documentdaily_budget_cap(with the pacing-approximation fallback kept for sellers without support). The note lands atomically with the feature.