Skip to content

fix(compliance): assert governance_context echo + gate governance_approved/conditions (#5716)#5719

Closed
bokelley wants to merge 1 commit into
mainfrom
fix/governance-handshake-assertions
Closed

fix(compliance): assert governance_context echo + gate governance_approved/conditions (#5716)#5719
bokelley wants to merge 1 commit into
mainfrom
fix/governance-handshake-assertions

Conversation

@bokelley

Copy link
Copy Markdown
Contributor

Closes #5716.

Problem

governance_approved and governance_conditions asserted only response_schema on their terminal create_media_buy step. Since storyboard grading is deterministic validations[] only (the expected: prose is documentation, not graded), a seller that registers a governance agent but never calls check_governance creates a schema-valid buy and passes both — the governance handshake those scenarios are named for went untested.

(governance_denied / governance_denied_recovery were already safe — they carry hard expect_error + error_code: GOVERNANCE_DENIED assertions a non-consulting seller can't fake, and #5676 gated them.)

Fix

For both scenarios:

  1. Assert the handshake — add check: envelope_field_present, path: governance_context to the terminal step. governance_context is the token issued by check_governance (protocol-envelope.json), so only a seller that actually consulted the registered governance agent can echo it. (envelope_field_present is implemented in @adcp/sdk@9.0.0-beta.31, added per Storyboard authoring: response_schema_ref vs envelope-level field assertions in v3-envelope-integrity #3429.)
  2. Gate on the capability — add requires_capability: { path: media_buy.governance_aware, equals: true }, mirroring fix(compliance): add media_buy.governance_aware capability + gate governance_denied (#5665) [Option A] #5676, so sellers without outbound governance consultation grade not_applicable instead of newly false-failing.

On the "conditions" half of the issue

The issue asked to also assert conditions propagation. There is no dedicated wire field for governance conditions on the buy (create-media-buy-response.json, core/media-buy.json, and core/package.json have none). The governance_context token is the propagation/correlation mechanism (protocol-envelope.json: "primary correlation key for audit and reporting across the governance lifecycle"), with conditions retrievable at the governance agent. So the token echo is the correct assertable handshake signal. If the WG wants an explicit conditions field on the buy, that's a separate schema-modeling decision.

Validation

Targeted storyboard lints pass: lint-storyboard-check-enum (✓ envelope_field_present), lint-storyboard-validations-paths (✓ governance_context path), sdk-runner-capability-gates (✓ gate resolves). Full pre-commit suite green.

Note: the gate keys equals: true while the schema default is false, so the only sellers skipped are those that don't declare governance support — the intended skip, not the gated-value-equals-default trap.

🤖 Generated with Claude Code

…roved/conditions (#5716)

governance_approved and governance_conditions previously asserted only
response_schema on their terminal create_media_buy step, so a seller that
never consulted its registered governance agent still passed — the
governance handshake those scenarios are named for went untested.

Add `envelope_field_present: governance_context` (a token only a seller that
called check_governance can echo) to each, and gate both on
media_buy.governance_aware (mirroring governance_denied/_recovery from #5676)
so sellers without outbound governance consultation grade not_applicable
instead of newly false-failing.

Note: governance conditions have no dedicated wire field on the buy; the
governance_context token is the correlation/propagation mechanism (per
protocol-envelope.json), so the token echo is the assertable handshake signal.

Closes #5716

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@mintlify

mintlify Bot commented Jun 26, 2026

Copy link
Copy Markdown

Preview deployment for your docs. Learn more about Mintlify Previews.

Project Status Preview Updated (UTC)
adcp 🟢 Ready View Preview Jun 26, 2026, 10:13 AM

💡 Tip: Enable Workflows to automatically generate PRs for you.

@aao-release-bot aao-release-bot Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The gate is right. The assertion it's bolted to is unsound — it grades a seller→buyer echo the spec never requires, so it false-fails conformant sellers. ad-tech-protocol-expert: unsound, with cited spec divergence.

The block

The terminal create_media_buy step now asserts envelope_field_present: governance_context on the response envelope. No normative text requires a seller to echo governance_context back to the buyer on that response.

The token-flow contract (docs/governance/campaign/specification.mdx:696-699) is explicit about the seller obligation:

Seller: receives governance_context in the envelope, stores it alongside the media buy, and includes it on all subsequent check_governance calls for that media buy's lifecycle.

Buyer→seller→governance-agent forwarding. Not seller→buyer echo on the buy response. The schema agrees: governance_context is not in the envelope required array — only status is (static/schemas/source/core/protocol-envelope.json:61-62) — and create-media-buy-response.json defines no governance field on any of its response shapes.

The clincher is internal. The existing governance/index.yaml storyboard lists governance_context: echoed back as un-graded expected: prose (line 544), then deliberately omits it from its graded validations[] (lines 576-586 — response_schema, field_present: context, field_value: context.correlation_id). Whoever wrote that storyboard already knew the echo is not a gradeable invariant. This PR promotes that prose into a hard assertion without the normative basis the prose lacked.

What breaks for adopters: a governance-aware seller that calls check_governance, gets approved, persists the token, and forwards it on subsequent lifecycle calls — but does not echo it on the create_media_buy response — is fully conformant and newly false-fails both scenarios. That's spec drift on the compliance grading surface, gated capability or not.

The PR's own framing concedes the gap: it notes there is no wire field for governance conditions on the buy, then reaches for the envelope token as a proxy. The token is a real correlation key — at the governance agent, on check_governance calls. It is not a buy-response echo signal.

Things I checked

  • requires_capability: { path: media_buy.governance_aware, equals: true } is byte-identical to the #5676 precedent (governance_denied.yaml:17-19); media_buy.governance_aware is real (get-adcp-capabilities-response.json:214, default: false), so equals: true skips only non-declaring sellers — no gate-equals-default trap. This half is sound. code-reviewer: clean.
  • envelope_field_present is a valid check kind (runner-output-contract.yaml:47); the appended validations entry's indentation matches the existing response_schema entry; storyboard lints resolve the path. The YAML is correct — the defect is semantic, not structural.
  • Changeset exists (.changeset/5716-governance-handshake-assertions.md, patch) — appropriate for a compliance-config change. Not the issue.

How to unblock

Keep the requires_capability gate — that half mirrors #5676 correctly and ships as-is. Replace the governance_context echo with a handshake signal that is normatively grounded under this gate. Two options the expert surfaced:

  • Assert planned_delivery presence — its schema description (create-media-buy-response.json:90-92) says it is "Present when the account has governance_agents," which is an actual conformant-seller invariant.
  • Assert the governance call out-of-band via the governance agent's get_plan_audit_logs.

If the WG genuinely wants the seller to echo governance_context on the buy response, that's a normative MUST in the spec + a field on create-media-buy-response.json first — then the assertion. Assertion-first inverts the order.

One open question worth confirming regardless of path: does envelope_field_present at runtime inspect the response envelope or the request envelope? If the latter, the check is vacuously true (the buyer always attaches the token on the request) and tests nothing — a different defect, same line.

Requesting changes on the echo assertion. The gate is good; this is one targeted swap away from approvable.

@bokelley

Copy link
Copy Markdown
Contributor Author

Closing per Argus's review — the objection is correct, confirmed against the spec.

The envelope_field_present: governance_context assertion graded a seller→buyer echo on the create_media_buy response that no normative text requires:

  • docs/governance/campaign/specification.mdx:696-699 defines the flow as buyer→seller→governance-agent forwarding (the seller persists the token and includes it on subsequent check_governance calls), not a seller→buyer response echo.
  • governance_context is not in the envelope required[] (only status is), and create-media-buy-response.json defines no governance field.
  • The existing governance/index.yaml storyboard already lists the echo as ungraded expected: prose and deliberately omits it from validations[].

So a conformant seller that consults governance but doesn't echo the token would have newly false-failed. The capability gate half (requires_capability: media_buy.governance_aware) was sound, but it's not worth shipping alone.

The deeper issue: the happy-path scenarios can't deterministically prove consultation via the buy response, and they predate the spec's two-phase intent/purchase token flow (specification.mdx:138-182). The real fix is to align them with that flow — tracked in the rescoped #5716.

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.

compliance: align governance_approved/conditions with the two-phase governance token flow (they under-assert today)

1 participant