@adcp/sdk 7.10.2 → 7.11.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (305) hide show
  1. package/compliance/cache/3.1.0-rc.2/domains/brand/index.yaml +160 -0
  2. package/compliance/cache/3.1.0-rc.2/domains/brand/scenarios/distributed_brand_resolution.yaml +415 -0
  3. package/compliance/cache/3.1.0-rc.2/domains/brand/scenarios/single_side_trust_extension.yaml +454 -0
  4. package/compliance/cache/3.1.0-rc.2/domains/creative/index.yaml +339 -0
  5. package/compliance/cache/3.1.0-rc.2/domains/creative/scenarios/billing_out_of_band.yaml +153 -0
  6. package/compliance/cache/3.1.0-rc.2/domains/creative/scenarios/canonical_supported_formats.yaml +212 -0
  7. package/compliance/cache/3.1.0-rc.2/domains/creative/scenarios/creative_lifecycle_webhooks.yaml +389 -0
  8. package/compliance/cache/3.1.0-rc.2/domains/creative/scenarios/native_in_feed.yaml +543 -0
  9. package/compliance/cache/3.1.0-rc.2/domains/governance/index.yaml +682 -0
  10. package/compliance/cache/3.1.0-rc.2/domains/media-buy/index.yaml +789 -0
  11. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/audience_buy_flow.yaml +380 -0
  12. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/available_actions.yaml +565 -0
  13. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/billing_finality_delivery.yaml +354 -0
  14. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/canonical_formats.yaml +861 -0
  15. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/clicks_buy_flow.yaml +264 -0
  16. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/completed_views_buy_flow.yaml +344 -0
  17. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/create_media_buy_async.yaml +234 -0
  18. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/creative_fate_after_cancellation.yaml +419 -0
  19. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/creative_reception.yaml +247 -0
  20. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/delivery_reporting.yaml +357 -0
  21. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/dependency_impairment.yaml +633 -0
  22. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/dependency_impairment_cardinality.yaml +800 -0
  23. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/event_dedup_flow.yaml +399 -0
  24. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/frequency_cap_enforcement.yaml +309 -0
  25. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/governance_approved.yaml +214 -0
  26. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/governance_conditions.yaml +199 -0
  27. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/governance_denied.yaml +204 -0
  28. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/governance_denied_recovery.yaml +252 -0
  29. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/invalid_transitions.yaml +289 -0
  30. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/inventory_list_no_match.yaml +148 -0
  31. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/inventory_list_targeting.yaml +276 -0
  32. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/measurement_accountability.yaml +244 -0
  33. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/measurement_terms_rejected.yaml +203 -0
  34. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/package_correlation_legacy_fallback.yaml +113 -0
  35. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/pending_creatives_to_start.yaml +292 -0
  36. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/per_creative_conversion_attribution.yaml +500 -0
  37. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/performance_buy_flow.yaml +428 -0
  38. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/performance_buy_flow_roas.yaml +470 -0
  39. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/product_signal_targeting.yaml +373 -0
  40. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/proposal_finalize.yaml +399 -0
  41. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/proposal_finalize_asap_timing.yaml +264 -0
  42. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/proposal_not_found_errors.yaml +257 -0
  43. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/provenance_audit_observation.yaml +333 -0
  44. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/provenance_enforcement.yaml +517 -0
  45. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/provenance_truth_of_claim.yaml +294 -0
  46. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/reach_buy_flow.yaml +823 -0
  47. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/refine_finalize_exclusivity.yaml +360 -0
  48. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/refine_products.yaml +148 -0
  49. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/vendor_metric_accountability.yaml +293 -0
  50. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/vendor_metric_catalog_precondition.yaml +307 -0
  51. package/compliance/cache/3.1.0-rc.2/domains/media-buy/scenarios/vendor_metric_optimization_flow.yaml +576 -0
  52. package/compliance/cache/3.1.0-rc.2/domains/media-buy/state-machine.yaml +442 -0
  53. package/compliance/cache/3.1.0-rc.2/domains/signals/index.yaml +266 -0
  54. package/compliance/cache/3.1.0-rc.2/domains/sponsored-intelligence/index.yaml +256 -0
  55. package/compliance/cache/3.1.0-rc.2/index.json +356 -0
  56. package/compliance/cache/3.1.0-rc.2/protocols/brand/index.yaml +160 -0
  57. package/compliance/cache/3.1.0-rc.2/protocols/brand/scenarios/distributed_brand_resolution.yaml +415 -0
  58. package/compliance/cache/3.1.0-rc.2/protocols/brand/scenarios/single_side_trust_extension.yaml +454 -0
  59. package/compliance/cache/3.1.0-rc.2/protocols/creative/index.yaml +339 -0
  60. package/compliance/cache/3.1.0-rc.2/protocols/creative/scenarios/billing_out_of_band.yaml +153 -0
  61. package/compliance/cache/3.1.0-rc.2/protocols/creative/scenarios/canonical_supported_formats.yaml +212 -0
  62. package/compliance/cache/3.1.0-rc.2/protocols/creative/scenarios/creative_lifecycle_webhooks.yaml +389 -0
  63. package/compliance/cache/3.1.0-rc.2/protocols/creative/scenarios/native_in_feed.yaml +543 -0
  64. package/compliance/cache/3.1.0-rc.2/protocols/governance/index.yaml +682 -0
  65. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/index.yaml +789 -0
  66. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/audience_buy_flow.yaml +380 -0
  67. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/available_actions.yaml +565 -0
  68. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/billing_finality_delivery.yaml +354 -0
  69. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/canonical_formats.yaml +861 -0
  70. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/clicks_buy_flow.yaml +264 -0
  71. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/completed_views_buy_flow.yaml +344 -0
  72. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/create_media_buy_async.yaml +234 -0
  73. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/creative_fate_after_cancellation.yaml +419 -0
  74. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/creative_reception.yaml +247 -0
  75. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/delivery_reporting.yaml +357 -0
  76. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/dependency_impairment.yaml +633 -0
  77. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/dependency_impairment_cardinality.yaml +800 -0
  78. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/event_dedup_flow.yaml +399 -0
  79. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/frequency_cap_enforcement.yaml +309 -0
  80. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/governance_approved.yaml +214 -0
  81. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/governance_conditions.yaml +199 -0
  82. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/governance_denied.yaml +204 -0
  83. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/governance_denied_recovery.yaml +252 -0
  84. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/invalid_transitions.yaml +289 -0
  85. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/inventory_list_no_match.yaml +148 -0
  86. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/inventory_list_targeting.yaml +276 -0
  87. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/measurement_accountability.yaml +244 -0
  88. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/measurement_terms_rejected.yaml +203 -0
  89. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/package_correlation_legacy_fallback.yaml +113 -0
  90. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/pending_creatives_to_start.yaml +292 -0
  91. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/per_creative_conversion_attribution.yaml +500 -0
  92. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/performance_buy_flow.yaml +428 -0
  93. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/performance_buy_flow_roas.yaml +470 -0
  94. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/product_signal_targeting.yaml +373 -0
  95. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/proposal_finalize.yaml +399 -0
  96. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/proposal_finalize_asap_timing.yaml +264 -0
  97. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/proposal_not_found_errors.yaml +257 -0
  98. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/provenance_audit_observation.yaml +333 -0
  99. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/provenance_enforcement.yaml +517 -0
  100. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/provenance_truth_of_claim.yaml +294 -0
  101. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/reach_buy_flow.yaml +823 -0
  102. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/refine_finalize_exclusivity.yaml +360 -0
  103. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/refine_products.yaml +148 -0
  104. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/vendor_metric_accountability.yaml +293 -0
  105. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/vendor_metric_catalog_precondition.yaml +307 -0
  106. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/scenarios/vendor_metric_optimization_flow.yaml +576 -0
  107. package/compliance/cache/3.1.0-rc.2/protocols/media-buy/state-machine.yaml +442 -0
  108. package/compliance/cache/3.1.0-rc.2/protocols/signals/index.yaml +266 -0
  109. package/compliance/cache/3.1.0-rc.2/protocols/sponsored-intelligence/index.yaml +256 -0
  110. package/compliance/cache/3.1.0-rc.2/specialisms/audience-sync/index.yaml +313 -0
  111. package/compliance/cache/3.1.0-rc.2/specialisms/brand-rights/index.yaml +350 -0
  112. package/compliance/cache/3.1.0-rc.2/specialisms/brand-rights/scenarios/governance_denied.yaml +226 -0
  113. package/compliance/cache/3.1.0-rc.2/specialisms/collection-lists/index.yaml +359 -0
  114. package/compliance/cache/3.1.0-rc.2/specialisms/content-standards/index.yaml +572 -0
  115. package/compliance/cache/3.1.0-rc.2/specialisms/creative-ad-server/index.yaml +409 -0
  116. package/compliance/cache/3.1.0-rc.2/specialisms/creative-generative/generative-seller.yaml +807 -0
  117. package/compliance/cache/3.1.0-rc.2/specialisms/creative-generative/index.yaml +758 -0
  118. package/compliance/cache/3.1.0-rc.2/specialisms/creative-template/index.yaml +510 -0
  119. package/compliance/cache/3.1.0-rc.2/specialisms/governance-aware-seller/index.yaml +143 -0
  120. package/compliance/cache/3.1.0-rc.2/specialisms/governance-aware-seller/scenarios/governance_multi_agent_rejected.yaml +117 -0
  121. package/compliance/cache/3.1.0-rc.2/specialisms/governance-delivery-monitor/index.yaml +441 -0
  122. package/compliance/cache/3.1.0-rc.2/specialisms/governance-spend-authority/denied.yaml +221 -0
  123. package/compliance/cache/3.1.0-rc.2/specialisms/governance-spend-authority/index.yaml +330 -0
  124. package/compliance/cache/3.1.0-rc.2/specialisms/property-lists/index.yaml +482 -0
  125. package/compliance/cache/3.1.0-rc.2/specialisms/sales-broadcast-tv/index.yaml +738 -0
  126. package/compliance/cache/3.1.0-rc.2/specialisms/sales-catalog-driven/index.yaml +840 -0
  127. package/compliance/cache/3.1.0-rc.2/specialisms/sales-guaranteed/index.yaml +601 -0
  128. package/compliance/cache/3.1.0-rc.2/specialisms/sales-non-guaranteed/index.yaml +546 -0
  129. package/compliance/cache/3.1.0-rc.2/specialisms/sales-proposal-mode/index.yaml +586 -0
  130. package/compliance/cache/3.1.0-rc.2/specialisms/sales-social/index.yaml +919 -0
  131. package/compliance/cache/3.1.0-rc.2/specialisms/signal-marketplace/index.yaml +424 -0
  132. package/compliance/cache/3.1.0-rc.2/specialisms/signal-marketplace/scenarios/governance_denied.yaml +210 -0
  133. package/compliance/cache/3.1.0-rc.2/specialisms/signal-owned/index.yaml +317 -0
  134. package/compliance/cache/3.1.0-rc.2/specialisms/sponsored-intelligence/index.yaml +59 -0
  135. package/compliance/cache/3.1.0-rc.2/test-kits/acme-outdoor-live.yaml +78 -0
  136. package/compliance/cache/3.1.0-rc.2/test-kits/acme-outdoor.yaml +223 -0
  137. package/compliance/cache/3.1.0-rc.2/test-kits/billing-gate-runner.yaml +115 -0
  138. package/compliance/cache/3.1.0-rc.2/test-kits/bistro-oranje.yaml +126 -0
  139. package/compliance/cache/3.1.0-rc.2/test-kits/distributed-brand-runner.yaml +281 -0
  140. package/compliance/cache/3.1.0-rc.2/test-kits/nova-motors.yaml +262 -0
  141. package/compliance/cache/3.1.0-rc.2/test-kits/osei-natural.yaml +126 -0
  142. package/compliance/cache/3.1.0-rc.2/test-kits/parallel-dispatch-runner.yaml +196 -0
  143. package/compliance/cache/3.1.0-rc.2/test-kits/rate-limit-trip-runner.yaml +172 -0
  144. package/compliance/cache/3.1.0-rc.2/test-kits/signed-requests-runner.yaml +155 -0
  145. package/compliance/cache/3.1.0-rc.2/test-kits/single-side-trust-runner.yaml +294 -0
  146. package/compliance/cache/3.1.0-rc.2/test-kits/substitution-observer-runner.yaml +688 -0
  147. package/compliance/cache/3.1.0-rc.2/test-kits/summit-foods.yaml +125 -0
  148. package/compliance/cache/3.1.0-rc.2/test-kits/webhook-receiver-runner.yaml +265 -0
  149. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/001-minimal-plan.json +43 -0
  150. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/002-full-plan.json +217 -0
  151. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/003-bookkeeping-stripped.json +60 -0
  152. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/004a-human-review-omitted.json +43 -0
  153. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/004b-human-review-explicit-null.json +49 -0
  154. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/005a-policy-categories-order-1.json +53 -0
  155. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/005b-policy-categories-order-2.json +57 -0
  156. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/006a-ext-trace-v1.json +49 -0
  157. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/006b-ext-trace-v2.json +53 -0
  158. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/007-unicode-objectives.json +43 -0
  159. package/compliance/cache/3.1.0-rc.2/test-vectors/plan-hash/008-numeric-canonicalization.json +65 -0
  160. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/README.md +220 -0
  161. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/canonicalization.json +241 -0
  162. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/keys.json +60 -0
  163. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/001-no-signature-header.json +24 -0
  164. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/002-wrong-tag.json +26 -0
  165. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/003-expired-signature.json +26 -0
  166. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/004-window-too-long.json +26 -0
  167. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/005-alg-not-allowed.json +26 -0
  168. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/006-missing-covered-component.json +26 -0
  169. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/007-missing-content-digest.json +26 -0
  170. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/008-unknown-keyid.json +26 -0
  171. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/009-key-ops-missing-verify.json +27 -0
  172. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/010-content-digest-mismatch.json +33 -0
  173. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/011-malformed-header.json +27 -0
  174. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/012-missing-expires-param.json +26 -0
  175. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/013-expires-le-created.json +27 -0
  176. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/014-missing-nonce-param.json +27 -0
  177. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/015-signature-invalid.json +28 -0
  178. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/016-replayed-nonce.json +35 -0
  179. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/017-key-revoked.json +38 -0
  180. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/018-digest-covered-when-forbidden.json +28 -0
  181. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/019-signature-without-signature-input.json +26 -0
  182. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/020-rate-abuse.json +34 -0
  183. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/021-duplicate-signature-input-label.json +31 -0
  184. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/022-multi-valued-content-type.json +31 -0
  185. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/023-multi-valued-content-digest.json +32 -0
  186. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/024-unquoted-string-param.json +31 -0
  187. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/025-jwk-alg-crv-mismatch.json +43 -0
  188. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/026-non-ascii-host.json +31 -0
  189. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/027-webhook-registration-authentication-unsigned.json +25 -0
  190. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/negative/028-unsigned-protocol-method-required.json +26 -0
  191. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/001-basic-post.json +30 -0
  192. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/002-post-with-content-digest.json +31 -0
  193. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/003-es256-post.json +30 -0
  194. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/004-multiple-signature-labels.json +26 -0
  195. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/005-default-port-stripped.json +30 -0
  196. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/006-dot-segment-path.json +30 -0
  197. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/007-query-byte-preserved.json +30 -0
  198. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/008-percent-encoded-path.json +30 -0
  199. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/009-percent-encoded-unreserved-decoded.json +30 -0
  200. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/010-percent-encoded-slash-preserved.json +30 -0
  201. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/011-ipv6-authority.json +30 -0
  202. package/compliance/cache/3.1.0-rc.2/test-vectors/request-signing/positive/012-ipv6-authority-default-port-stripped.json +30 -0
  203. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/README.md +211 -0
  204. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/keys.json +61 -0
  205. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/001-wrong-tag.json +26 -0
  206. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/002-expired-signature.json +26 -0
  207. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/003-window-too-long.json +26 -0
  208. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/004-alg-not-allowed.json +26 -0
  209. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/005-missing-authority-component.json +26 -0
  210. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/006-missing-content-digest.json +25 -0
  211. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/007-unknown-keyid.json +26 -0
  212. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/008-wrong-adcp-use.json +26 -0
  213. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/009-content-digest-mismatch.json +26 -0
  214. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/010-malformed-signature-input.json +26 -0
  215. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/011-signature-without-input.json +25 -0
  216. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/012-missing-expires-param.json +26 -0
  217. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/013-expires-le-created.json +26 -0
  218. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/014-missing-nonce-param.json +26 -0
  219. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/015-signature-invalid.json +26 -0
  220. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/016-replayed-nonce.json +37 -0
  221. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/017-key-revoked.json +32 -0
  222. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/018-rate-abuse.json +33 -0
  223. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/019-revocation-stale.json +32 -0
  224. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/020-key-ops-missing-verify.json +41 -0
  225. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/negative/021-base64-alphabet-mixing.json +26 -0
  226. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/positive/001-basic-post.json +24 -0
  227. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/positive/002-es256-post.json +24 -0
  228. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/positive/003-multiple-signature-labels.json +24 -0
  229. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/positive/004-default-port-stripped.json +24 -0
  230. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/positive/005-percent-encoded-path.json +24 -0
  231. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/positive/006-query-byte-preserved.json +24 -0
  232. package/compliance/cache/3.1.0-rc.2/test-vectors/webhook-signing/positive/007-body-without-idempotency-key.json +25 -0
  233. package/compliance/cache/3.1.0-rc.2/universal/billing-gate-dispatch.yaml +450 -0
  234. package/compliance/cache/3.1.0-rc.2/universal/canonical-format-validate-input.yaml +640 -0
  235. package/compliance/cache/3.1.0-rc.2/universal/capability-discovery.yaml +125 -0
  236. package/compliance/cache/3.1.0-rc.2/universal/collection-lists-pagination-integrity.yaml +306 -0
  237. package/compliance/cache/3.1.0-rc.2/universal/comply-controller-mode-gate.yaml +141 -0
  238. package/compliance/cache/3.1.0-rc.2/universal/content-standards-pagination-integrity.yaml +326 -0
  239. package/compliance/cache/3.1.0-rc.2/universal/deterministic-testing.yaml +1430 -0
  240. package/compliance/cache/3.1.0-rc.2/universal/error-compliance-signals.yaml +377 -0
  241. package/compliance/cache/3.1.0-rc.2/universal/error-compliance.yaml +528 -0
  242. package/compliance/cache/3.1.0-rc.2/universal/fictional-entities.yaml +307 -0
  243. package/compliance/cache/3.1.0-rc.2/universal/get-media-buys-pagination-integrity.yaml +160 -0
  244. package/compliance/cache/3.1.0-rc.2/universal/get-signals-pagination-integrity.yaml +210 -0
  245. package/compliance/cache/3.1.0-rc.2/universal/idempotency.yaml +861 -0
  246. package/compliance/cache/3.1.0-rc.2/universal/notification-config-event-scope.yaml +119 -0
  247. package/compliance/cache/3.1.0-rc.2/universal/notification-config-lifecycle.yaml +337 -0
  248. package/compliance/cache/3.1.0-rc.2/universal/notification-config-rejections.yaml +107 -0
  249. package/compliance/cache/3.1.0-rc.2/universal/pagination-integrity-creative-formats.yaml +265 -0
  250. package/compliance/cache/3.1.0-rc.2/universal/pagination-integrity-list-accounts.yaml +245 -0
  251. package/compliance/cache/3.1.0-rc.2/universal/pagination-integrity.yaml +263 -0
  252. package/compliance/cache/3.1.0-rc.2/universal/property-lists-pagination-integrity.yaml +307 -0
  253. package/compliance/cache/3.1.0-rc.2/universal/read-tool-idempotency.yaml +405 -0
  254. package/compliance/cache/3.1.0-rc.2/universal/runner-output-contract.yaml +1285 -0
  255. package/compliance/cache/3.1.0-rc.2/universal/schema-validation-signals.yaml +181 -0
  256. package/compliance/cache/3.1.0-rc.2/universal/schema-validation.yaml +548 -0
  257. package/compliance/cache/3.1.0-rc.2/universal/security.yaml +539 -0
  258. package/compliance/cache/3.1.0-rc.2/universal/signed-requests.yaml +217 -0
  259. package/compliance/cache/3.1.0-rc.2/universal/stale-response-advisory.yaml +295 -0
  260. package/compliance/cache/3.1.0-rc.2/universal/storyboard-schema.yaml +2194 -0
  261. package/compliance/cache/3.1.0-rc.2/universal/v3-envelope-integrity.yaml +117 -0
  262. package/compliance/cache/3.1.0-rc.2/universal/version-negotiation.yaml +130 -0
  263. package/compliance/cache/3.1.0-rc.2/universal/webhook-emission.yaml +411 -0
  264. package/compliance/cache/3.1.0-rc.2/universal/wholesale-feed-bulk-webhooks.yaml +82 -0
  265. package/compliance/cache/3.1.0-rc.2/universal/wholesale-feed-product-webhooks.yaml +83 -0
  266. package/compliance/cache/3.1.0-rc.2/universal/wholesale-feed-products.yaml +151 -0
  267. package/compliance/cache/3.1.0-rc.2/universal/wholesale-feed-signal-webhooks.yaml +83 -0
  268. package/compliance/cache/3.1.0-rc.2/universal/wholesale-feed-signals.yaml +149 -0
  269. package/dist/lib/index.d.ts +1 -1
  270. package/dist/lib/index.d.ts.map +1 -1
  271. package/dist/lib/index.js +9 -5
  272. package/dist/lib/index.js.map +1 -1
  273. package/dist/lib/schemas-data/v2.5/_provenance.json +1 -1
  274. package/dist/lib/testing/storyboard/default-invariants.js +30 -1
  275. package/dist/lib/testing/storyboard/default-invariants.js.map +1 -1
  276. package/dist/lib/testing/storyboard/runner.d.ts.map +1 -1
  277. package/dist/lib/testing/storyboard/runner.js +84 -21
  278. package/dist/lib/testing/storyboard/runner.js.map +1 -1
  279. package/dist/lib/testing/storyboard/types.d.ts +21 -0
  280. package/dist/lib/testing/storyboard/types.d.ts.map +1 -1
  281. package/dist/lib/testing/storyboard/types.js.map +1 -1
  282. package/dist/lib/testing/types.d.ts +9 -0
  283. package/dist/lib/testing/types.d.ts.map +1 -1
  284. package/dist/lib/types/schemas.generated.d.ts +6707 -12040
  285. package/dist/lib/types/schemas.generated.d.ts.map +1 -1
  286. package/dist/lib/types/schemas.generated.js +1 -1
  287. package/dist/lib/types/schemas.generated.js.map +1 -1
  288. package/dist/lib/utils/signal-id-builders.d.ts +19 -0
  289. package/dist/lib/utils/signal-id-builders.d.ts.map +1 -1
  290. package/dist/lib/utils/signal-id-builders.js +30 -0
  291. package/dist/lib/utils/signal-id-builders.js.map +1 -1
  292. package/dist/lib/utils/tool-request-schemas.d.ts.map +1 -1
  293. package/dist/lib/utils/tool-request-schemas.js +3 -0
  294. package/dist/lib/utils/tool-request-schemas.js.map +1 -1
  295. package/dist/lib/v2/projection/constants.d.ts +28 -0
  296. package/dist/lib/v2/projection/constants.d.ts.map +1 -0
  297. package/dist/lib/v2/projection/constants.js +31 -0
  298. package/dist/lib/v2/projection/constants.js.map +1 -0
  299. package/dist/lib/v2/projection/registry.d.ts.map +1 -1
  300. package/dist/lib/v2/projection/registry.js +9 -4
  301. package/dist/lib/v2/projection/registry.js.map +1 -1
  302. package/dist/lib/version.d.ts +3 -3
  303. package/dist/lib/version.js +3 -3
  304. package/package.json +1 -1
  305. package/skills/SHAPE-GOTCHAS.md +5 -0
@@ -0,0 +1,633 @@
1
+ id: media_buy_seller/dependency_impairment
2
+ version: "2.0.0"
3
+ title: "Dependency impairment end-to-end — resource transition propagates to media buy health"
4
+ category: media_buy_seller
5
+ summary: "Forces a creative from approved → rejected on a non-terminal media buy, verifies the buy reflects health: impaired with a matching impairments[] entry, and recovers via assignment swap to a different creative (canonical recovery vector — re-approval of the same creative_id is uncommon in production)."
6
+ track: media_buy
7
+ required_tools:
8
+ - get_products
9
+ - create_media_buy
10
+ - get_media_buys
11
+ - sync_creatives
12
+ - update_media_buy
13
+ - comply_test_controller
14
+
15
+ narrative: |
16
+ Per the dependency-impairment surface ([adcp#2855](https://github.com/adcontextprotocol/adcp/issues/2855)
17
+ and `core/impairment.json`), sellers MUST propagate resource-state transitions
18
+ into the affected media buys. The compliance contract is `impairment.coherence`
19
+ (adcp#2859) — a cross-resource invariant tying `media_buy.impairments[]` to the
20
+ underlying resource state. The runner registers and grades this invariant via
21
+ adcp-client#1801; this storyboard is what makes it run end-to-end instead of
22
+ grading not_applicable.
23
+
24
+ Five phases, exercised entirely against the comply test controller's sandbox:
25
+
26
+ 1. **setup** — discover a product, create an active media buy, sync a creative
27
+ and assign it to the buy's package. Capture media_buy_id, package_id, and
28
+ creative_id for the rest of the run.
29
+ 2. **baseline_healthy** — read the buy via get_media_buys. `health` MUST be
30
+ `ok`, and `impairments[]` MUST be empty or absent. This establishes the
31
+ pre-transition snapshot the impairment.coherence runner ledgers against.
32
+ 3. **transition_offline** — call comply_test_controller force_creative_status
33
+ to flip the creative to `rejected` with a rejection_reason. This is the
34
+ resource-state transition the runner observes.
35
+ 4. **verify_impaired** — read the buy again. `health` MUST be `impaired`, and
36
+ `impairments[]` MUST contain an entry whose resource_type is `creative`,
37
+ resource_id matches the rejected creative, package_ids contains the
38
+ creative's package, transition.to is `rejected`, and the required
39
+ fields (impairment_id, reason_code, observed_at) are populated. This
40
+ closes the forward rule (every entry references a currently-offline
41
+ resource) and the inverse rule (the offline resource referenced by a
42
+ non-terminal buy appears in impairments[]) for this transition, and
43
+ captures the health-iff rule in the `impaired` direction.
44
+ 5. **swap_recovery** — sync a second creative (B, approved) and use
45
+ `update_media_buy` with `packages[].creative_assignments` (replacement
46
+ semantics — the new list fully replaces the old) to swap the package's
47
+ binding from creative A (still rejected in the library) to creative B
48
+ (approved). Read the buy and assert `health: ok` with `impairments[]`
49
+ empty/absent. This is the canonical recovery vector in production —
50
+ buyers rarely re-approve a rejected creative on the same ID; they swap
51
+ to a replacement asset. Creative A's library status stays `rejected`,
52
+ but it is no longer a dependency of any package on this buy, so the
53
+ impairment clears.
54
+
55
+ A seller that transitions a creative without propagating to the buy fails
56
+ phase 4. A seller that holds stale `impairments[]` after the swap (where
57
+ creative A is no longer referenced) fails phase 5. A seller that
58
+ maintains a stale `health: impaired` with empty `impairments[]` (or vice
59
+ versa) on a non-terminal buy fails the impairment.coherence runner
60
+ invariant alongside the per-step assertions.
61
+
62
+ **Same-ID re-approval as recovery vector.** Some sellers' review flows do
63
+ support `rejected → approved` on the same creative_id (post-policy review
64
+ reinstatement, takedown reversed). That's covered by the opt-in sibling
65
+ scenario `media_buy_seller/dependency_impairment_reapprove_recovery`
66
+ (filed at adcp#4682 as a secondary variant). Sellers without same-ID
67
+ re-approval grade that sibling not_applicable; this scenario (swap) is
68
+ the universal recovery path.
69
+
70
+ **Capability gating.** Sellers whose
71
+ `capabilities.media_buy.propagation_surfaces` does NOT include
72
+ `"snapshot"` (e.g., `["webhook"]` or `["out_of_band"]`) grade this
73
+ whole scenario not_applicable — their compliance contract is the
74
+ webhook channel or the offline agreement, not the snapshot. Sellers
75
+ declaring `["snapshot", "webhook"]` are graded on the snapshot surface
76
+ here and on the webhook contract separately. See lifecycle.mdx §
77
+ Compliance for the surface declaration.
78
+
79
+ Audience-track and catalog-track variants are out of scope here — the
80
+ comply test controller only ships force_creative_status today; the
81
+ force_audience_status / force_catalog_item_status surface lands in a
82
+ follow-up.
83
+
84
+ agent:
85
+ interaction_model: media_buy_seller
86
+ capabilities:
87
+ - sells_media
88
+ - has_creative_library
89
+ examples:
90
+ - "Any media buy seller that exposes comply_test_controller and propagates creative state to buy.impairments[]"
91
+
92
+ caller:
93
+ role: buyer_agent
94
+ example: "Pinnacle Agency (buyer)"
95
+
96
+ prerequisites:
97
+ description: |
98
+ Seller MUST expose comply_test_controller with force_creative_status support.
99
+ Sellers without the controller (or without force_creative_status) grade this
100
+ scenario not_applicable — the cross-resource exercise requires deterministic
101
+ resource transitions the buyer can drive directly.
102
+ test_kit: "test-kits/acme-outdoor.yaml"
103
+
104
+ phases:
105
+ - id: setup
106
+ title: "Create an active buy with a creative assignment"
107
+ narrative: |
108
+ Discover a product, create a media buy, sync one creative into the library
109
+ with an inline assignment to the buy's first package. The buy's `health`
110
+ starts as `ok` (default) and `impairments[]` is empty.
111
+
112
+ steps:
113
+ - id: get_products_brief
114
+ title: "Discover a product"
115
+ task: get_products
116
+ schema_ref: "media-buy/get-products-request.json"
117
+ response_schema_ref: "media-buy/get-products-response.json"
118
+ doc_ref: "/media-buy/task-reference/get_products"
119
+ comply_scenario: full_sales_flow
120
+ stateful: false
121
+ expected: |
122
+ Return at least one product with a pricing option and at least one format_id.
123
+ sample_request:
124
+ buying_mode: "brief"
125
+ brief: "Display inventory on outdoor lifestyle content for dependency-impairment testing."
126
+ filters:
127
+ is_fixed_price: true
128
+ account:
129
+ brand:
130
+ domain: "acmeoutdoor.example"
131
+ operator: "pinnacle-agency.example"
132
+ context:
133
+ correlation_id: "dependency_impairment--get_products"
134
+ context_outputs:
135
+ - path: "products[0].product_id"
136
+ key: "product_id"
137
+ - path: "products[0].pricing_options[0].pricing_option_id"
138
+ key: "pricing_option_id"
139
+ - path: "products[0].format_ids[0].agent_url"
140
+ key: "format_agent_url"
141
+ - path: "products[0].format_ids[0].id"
142
+ key: "format_id"
143
+ validations:
144
+ - check: response_schema
145
+ description: "Response matches get-products-response.json schema"
146
+ - check: field_present
147
+ path: "products[0].format_ids[0].id"
148
+ description: "Product exposes at least one format_id for creative sync"
149
+ - check: field_present
150
+ path: "products[0].pricing_options[0].fixed_price"
151
+ description: "The captured pricing option is fixed-price; fixed-price storyboards do not send bid_price"
152
+
153
+ - id: create_buy
154
+ title: "Create an active media buy"
155
+ task: create_media_buy
156
+ schema_ref: "media-buy/create-media-buy-request.json"
157
+ response_schema_ref: "media-buy/create-media-buy-response.json"
158
+ doc_ref: "/media-buy/task-reference/create_media_buy"
159
+ comply_scenario: create_media_buy
160
+ stateful: true
161
+ expected: |
162
+ Media buy created with media_buy_id and at least one package. Flight is
163
+ forward-dated; status is pending_creatives or pending_start.
164
+
165
+ sample_request:
166
+ brand:
167
+ domain: "acmeoutdoor.example"
168
+ account:
169
+ brand:
170
+ domain: "acmeoutdoor.example"
171
+ operator: "pinnacle-agency.example"
172
+ idempotency_key: "$generate:uuid_v4#dependency_impairment_create_buy"
173
+ start_time: "2026-11-01T00:00:00Z"
174
+ end_time: "2026-11-30T23:59:59Z"
175
+ packages:
176
+ - product_id: "$context.product_id"
177
+ budget: 5000
178
+ pricing_option_id: "$context.pricing_option_id"
179
+ context:
180
+ correlation_id: "dependency_impairment--create_buy"
181
+ context_outputs:
182
+ - path: "media_buy_id"
183
+ key: "media_buy_id"
184
+ - path: "packages[0].package_id"
185
+ key: "package_id"
186
+ validations:
187
+ - check: response_schema
188
+ description: "Response matches create-media-buy-response.json schema"
189
+ - check: field_present
190
+ path: "media_buy_id"
191
+ description: "Seller returns media_buy_id"
192
+ - check: field_present
193
+ path: "packages[0].package_id"
194
+ description: "Seller returns package_id"
195
+
196
+ - id: sync_creative
197
+ title: "Sync a creative into the library"
198
+ narrative: |
199
+ Sync one creative into the seller's library. The creative enters
200
+ through the seller's review flow but is not yet bound to a package —
201
+ the next step does the assignment via update_media_buy.
202
+ task: sync_creatives
203
+ schema_ref: "creative/sync-creatives-request.json"
204
+ response_schema_ref: "creative/sync-creatives-response.json"
205
+ doc_ref: "/creative/task-reference/sync_creatives"
206
+ comply_scenario: creative_sync
207
+ stateful: true
208
+ expected: |
209
+ Creative accepted (action: created). Status is processing,
210
+ pending_review, or approved.
211
+
212
+ sample_request:
213
+ account:
214
+ brand:
215
+ domain: "acmeoutdoor.example"
216
+ operator: "pinnacle-agency.example"
217
+ creatives:
218
+ - creative_id: "acme_dep_banner_001"
219
+ name: "Acme Outdoor dependency-test banner"
220
+ format_id:
221
+ agent_url: "$context.format_agent_url"
222
+ id: "$context.format_id"
223
+ assets:
224
+ image:
225
+ asset_type: "image"
226
+ url: "https://cdn.pinnacle-agency.example/acme-dep-banner.png"
227
+ width: 300
228
+ height: 250
229
+ mime_type: "image/png"
230
+ idempotency_key: "$generate:uuid_v4#dependency_impairment_sync_creative"
231
+ context:
232
+ correlation_id: "dependency_impairment--sync_creative"
233
+ context_outputs:
234
+ - path: "creatives[0].creative_id"
235
+ key: "creative_id"
236
+ validations:
237
+ - check: response_schema
238
+ description: "Response matches sync-creatives-response.json schema"
239
+ - check: field_present
240
+ path: "creatives[0].creative_id"
241
+ description: "Response echoes back the buyer-supplied creative_id"
242
+
243
+ - id: assign_creative_to_package
244
+ title: "Bind the creative to the package via update_media_buy"
245
+ narrative: |
246
+ The assignment is what makes the creative a dependency of the media
247
+ buy — impairment.coherence ties the propagation rule to the creative
248
+ ↔ package binding. The spec defines two equal canonical surfaces for
249
+ the binding: inline `sync_creatives.assignments[]` and
250
+ `update_media_buy.packages[].creative_assignments` (replacement
251
+ semantics). This scenario uses the update_media_buy surface; the
252
+ impairment contract is identical regardless of which path the buyer
253
+ chose to establish the binding.
254
+ task: update_media_buy
255
+ schema_ref: "media-buy/update-media-buy-request.json"
256
+ response_schema_ref: "media-buy/update-media-buy-response.json"
257
+ doc_ref: "/media-buy/task-reference/update_media_buy"
258
+ stateful: true
259
+ expected: |
260
+ Update accepted. The package's creative_assignments now contains
261
+ the synced creative.
262
+
263
+ sample_request:
264
+ account:
265
+ brand:
266
+ domain: "acmeoutdoor.example"
267
+ operator: "pinnacle-agency.example"
268
+ media_buy_id: "$context.media_buy_id"
269
+ packages:
270
+ - package_id: "$context.package_id"
271
+ creative_assignments:
272
+ - creative_id: "acme_dep_banner_001"
273
+ idempotency_key: "$generate:uuid_v4#dependency_impairment_assign_creative"
274
+ context:
275
+ correlation_id: "dependency_impairment--assign_creative"
276
+ validations:
277
+ - check: response_schema
278
+ description: "Response matches update-media-buy-response.json schema"
279
+
280
+ - id: force_creative_approved
281
+ title: "Force the creative to approved baseline"
282
+ narrative: |
283
+ Use comply_test_controller force_creative_status to seed the creative
284
+ at `approved` so the next phase observes a clean approved → rejected
285
+ transition. Sellers with their own deterministic review flow may
286
+ already land at approved; this call is the safe baseline that lets
287
+ the rest of the storyboard depend on a known starting state.
288
+ task: comply_test_controller
289
+ schema_ref: "compliance/comply-test-controller-request.json"
290
+ response_schema_ref: "compliance/comply-test-controller-response.json"
291
+ doc_ref: "/building/implementation/comply-test-controller"
292
+ comply_scenario: full_sales_flow
293
+ stateful: true
294
+ expected: |
295
+ success: true. Creative is now at status: approved on the seller side.
296
+
297
+ sample_request:
298
+ account:
299
+ sandbox: true
300
+ scenario: "force_creative_status"
301
+ params:
302
+ creative_id: "acme_dep_banner_001"
303
+ status: "approved"
304
+ context:
305
+ correlation_id: "dependency_impairment--force_creative_approved"
306
+ validations:
307
+ - check: response_schema
308
+ description: "Response matches comply-test-controller-response.json schema"
309
+ - check: field_value
310
+ path: "success"
311
+ allowed_values: [true]
312
+ description: "Controller acknowledged the directive"
313
+
314
+ - id: baseline_healthy
315
+ title: "Baseline: buy reads as healthy, no impairments"
316
+ narrative: |
317
+ With the creative at approved and assigned, the buy MUST report
318
+ `health: ok` and an empty (or absent) `impairments[]`. This is the
319
+ pre-transition snapshot impairment.coherence ledgers against.
320
+
321
+ steps:
322
+ - id: get_buy_baseline
323
+ title: "Read the buy — health: ok, impairments[] empty"
324
+ task: get_media_buys
325
+ schema_ref: "media-buy/get-media-buys-request.json"
326
+ response_schema_ref: "media-buy/get-media-buys-response.json"
327
+ doc_ref: "/media-buy/task-reference/get_media_buys"
328
+ comply_scenario: media_buy_lifecycle
329
+ stateful: true
330
+ expected: |
331
+ The buy is returned with health: ok and impairments[] empty or absent.
332
+
333
+ sample_request:
334
+ account:
335
+ brand:
336
+ domain: "acmeoutdoor.example"
337
+ operator: "pinnacle-agency.example"
338
+ media_buy_ids:
339
+ - "$context.media_buy_id"
340
+ context:
341
+ correlation_id: "dependency_impairment--get_buy_baseline"
342
+ validations:
343
+ - check: response_schema
344
+ description: "Response matches get-media-buys-response.json schema"
345
+ - check: field_value
346
+ path: "media_buys[0].media_buy_id"
347
+ value: "$context.media_buy_id"
348
+ description: "Seller returns the buy by media_buy_id"
349
+ - check: field_value
350
+ path: "media_buys[0].health"
351
+ allowed_values: ["ok"]
352
+ description: "Buy health is ok in the baseline snapshot (health-iff rule, ok direction)"
353
+ - check: field_value_or_absent
354
+ path: "media_buys[0].impairments"
355
+ value: []
356
+ description: "impairments[] is empty (or absent) in the baseline — no resources are offline yet"
357
+
358
+ - id: transition_offline
359
+ title: "Force the creative to rejected"
360
+ narrative: |
361
+ The seller transitions the creative from approved → rejected via
362
+ comply_test_controller. This is the resource-state transition that the
363
+ seller MUST propagate to every non-terminal buy referencing the creative.
364
+
365
+ steps:
366
+ - id: force_creative_rejected
367
+ title: "comply_test_controller force_creative_status → rejected"
368
+ task: comply_test_controller
369
+ schema_ref: "compliance/comply-test-controller-request.json"
370
+ response_schema_ref: "compliance/comply-test-controller-response.json"
371
+ doc_ref: "/building/implementation/comply-test-controller"
372
+ comply_scenario: creative_lifecycle
373
+ stateful: true
374
+ expected: |
375
+ success: true. Creative is now at status: rejected. The seller has
376
+ observed the transition; the next get_media_buys read MUST reflect
377
+ the impairment on the affected buy.
378
+
379
+ sample_request:
380
+ account:
381
+ sandbox: true
382
+ scenario: "force_creative_status"
383
+ params:
384
+ creative_id: "acme_dep_banner_001"
385
+ status: "rejected"
386
+ rejection_reason: "Dependency-impairment scenario: forcing approved → rejected to exercise impairment.coherence."
387
+ context:
388
+ correlation_id: "dependency_impairment--force_creative_rejected"
389
+ validations:
390
+ - check: response_schema
391
+ description: "Response matches comply-test-controller-response.json schema"
392
+ - check: field_value
393
+ path: "success"
394
+ allowed_values: [true]
395
+ description: "Controller acknowledged the rejection directive"
396
+
397
+ - id: verify_impaired
398
+ title: "Buy reads as impaired with a matching impairments[] entry"
399
+ narrative: |
400
+ After the rejection, the buy MUST report `health: impaired` and
401
+ `impairments[]` MUST contain an entry whose resource_type is `creative`,
402
+ resource_id matches the rejected creative, package_ids contains the
403
+ creative's package, and transition.to is `rejected`. This closes the
404
+ forward + inverse rules for this transition; the impairment.coherence
405
+ invariant grades the cross-resource match.
406
+
407
+ steps:
408
+ - id: get_buy_impaired
409
+ title: "Read the buy — health: impaired, impairment entry present"
410
+ task: get_media_buys
411
+ schema_ref: "media-buy/get-media-buys-request.json"
412
+ response_schema_ref: "media-buy/get-media-buys-response.json"
413
+ doc_ref: "/media-buy/task-reference/get_media_buys"
414
+ comply_scenario: media_buy_lifecycle
415
+ stateful: true
416
+ expected: |
417
+ The buy is returned with:
418
+ - health: impaired
419
+ - impairments[] containing at least one entry where
420
+ resource_type: creative, resource_id: acme_dep_banner_001,
421
+ package_ids includes the buy's package, transition.to: rejected.
422
+
423
+ sample_request:
424
+ account:
425
+ brand:
426
+ domain: "acmeoutdoor.example"
427
+ operator: "pinnacle-agency.example"
428
+ media_buy_ids:
429
+ - "$context.media_buy_id"
430
+ context:
431
+ correlation_id: "dependency_impairment--get_buy_impaired"
432
+ validations:
433
+ - check: response_schema
434
+ description: "Response matches get-media-buys-response.json schema"
435
+ - check: field_value
436
+ path: "media_buys[0].health"
437
+ allowed_values: ["impaired"]
438
+ description: "Buy health flipped to impaired after the creative was rejected (health-iff rule, impaired direction)"
439
+ - check: field_present
440
+ path: "media_buys[0].impairments[0]"
441
+ description: "Buy reports at least one impairment entry (inverse rule)"
442
+ - check: field_value
443
+ path: "media_buys[0].impairments[0].resource_type"
444
+ allowed_values: ["creative"]
445
+ description: "Impairment entry's resource_type is creative"
446
+ - check: field_value
447
+ path: "media_buys[0].impairments[0].resource_id"
448
+ value: "acme_dep_banner_001"
449
+ description: "Impairment entry's resource_id matches the rejected creative (forward rule)"
450
+ - check: field_value
451
+ path: "media_buys[0].impairments[0].package_ids[0]"
452
+ value: "$context.package_id"
453
+ description: "Impairment entry's package_ids[] contains the buy's package — without this, a seller could list a different package and still pass the impairment-present check"
454
+ - check: field_value
455
+ path: "media_buys[0].impairments[0].transition.to"
456
+ allowed_values: ["rejected"]
457
+ description: "Impairment entry's transition.to is rejected"
458
+ - check: field_present
459
+ path: "media_buys[0].impairments[0].impairment_id"
460
+ description: "Impairment carries the required impairment_id (notification_id for state-event webhooks; see snapshot-and-log Rule 1)"
461
+ - check: field_present
462
+ path: "media_buys[0].impairments[0].reason_code"
463
+ description: "Impairment carries a reason_code (required per impairment.json) — buyer needs this to route remediation"
464
+ - check: field_present
465
+ path: "media_buys[0].impairments[0].observed_at"
466
+ description: "Impairment carries observed_at (required per impairment.json) — buyer needs this to reconcile webhook ordering against the snapshot"
467
+
468
+ - id: swap_recovery
469
+ title: "Recover via assignment swap — different creative replaces the rejected one"
470
+ narrative: |
471
+ Sync a second creative (B) into the library as approved, then use
472
+ update_media_buy to swap the package's creative_assignments from
473
+ creative A (still rejected) to creative B. Re-read the buy and verify
474
+ health returns to ok with impairments[] cleared. Creative A's library
475
+ status stays rejected — the seller is NOT required to re-approve it
476
+ — but A is no longer a dependency of any package on this buy, so the
477
+ impairment clears.
478
+
479
+ This is the production-canonical recovery path. Buyers rarely re-approve
480
+ a rejected creative on the same ID; they ship a corrected asset under
481
+ a new ID and update assignments. The same-ID re-approval path is
482
+ covered separately by an opt-in sibling scenario (#4682 secondary
483
+ variant) for sellers whose review flow supports it.
484
+
485
+ steps:
486
+ - id: sync_replacement_creative
487
+ title: "Sync replacement creative B (approved baseline)"
488
+ narrative: |
489
+ Add a second creative to the library WITHOUT assigning it to the
490
+ package yet. The package's current binding is still to creative A
491
+ (rejected). The next step uses update_media_buy to do the swap.
492
+ task: sync_creatives
493
+ schema_ref: "creative/sync-creatives-request.json"
494
+ response_schema_ref: "creative/sync-creatives-response.json"
495
+ doc_ref: "/creative/task-reference/sync_creatives"
496
+ comply_scenario: creative_sync
497
+ stateful: true
498
+ expected: |
499
+ Replacement creative accepted (action: created). No assignment yet
500
+ — the package's binding remains on creative A until the next step.
501
+
502
+ sample_request:
503
+ account:
504
+ brand:
505
+ domain: "acmeoutdoor.example"
506
+ operator: "pinnacle-agency.example"
507
+ creatives:
508
+ - creative_id: "acme_dep_banner_002"
509
+ name: "Acme Outdoor dependency-test replacement banner"
510
+ format_id:
511
+ agent_url: "$context.format_agent_url"
512
+ id: "$context.format_id"
513
+ assets:
514
+ image:
515
+ asset_type: "image"
516
+ url: "https://cdn.pinnacle-agency.example/acme-dep-banner-replacement.png"
517
+ width: 300
518
+ height: 250
519
+ mime_type: "image/png"
520
+ idempotency_key: "$generate:uuid_v4#dependency_impairment_sync_replacement"
521
+ context:
522
+ correlation_id: "dependency_impairment--sync_replacement_creative"
523
+ validations:
524
+ - check: response_schema
525
+ description: "Response matches sync-creatives-response.json schema"
526
+ - check: field_present
527
+ path: "creatives[0].creative_id"
528
+ description: "Replacement creative_id returned"
529
+
530
+ - id: force_replacement_approved
531
+ title: "Force replacement creative B to approved"
532
+ narrative: |
533
+ Baseline creative B at approved via comply_test_controller so the
534
+ swap binds the package to an in-policy creative. Sellers whose
535
+ deterministic flow already lands B at approved on sync grade this
536
+ step a no-op; the call is the safe seed.
537
+ task: comply_test_controller
538
+ schema_ref: "compliance/comply-test-controller-request.json"
539
+ response_schema_ref: "compliance/comply-test-controller-response.json"
540
+ doc_ref: "/building/implementation/comply-test-controller"
541
+ comply_scenario: creative_lifecycle
542
+ stateful: true
543
+ expected: |
544
+ success: true. Replacement creative is now at status: approved.
545
+
546
+ sample_request:
547
+ account:
548
+ sandbox: true
549
+ scenario: "force_creative_status"
550
+ params:
551
+ creative_id: "acme_dep_banner_002"
552
+ status: "approved"
553
+ context:
554
+ correlation_id: "dependency_impairment--force_replacement_approved"
555
+ validations:
556
+ - check: response_schema
557
+ description: "Response matches comply-test-controller-response.json schema"
558
+ - check: field_value
559
+ path: "success"
560
+ allowed_values: [true]
561
+ description: "Controller acknowledged the directive"
562
+
563
+ - id: swap_assignment
564
+ title: "Swap the package's creative_assignments — replacement semantics"
565
+ narrative: |
566
+ update_media_buy with packages[].creative_assignments uses
567
+ replacement semantics (per package-update.json) — the new list
568
+ fully replaces the old. Provide ONLY creative B; creative A is
569
+ unbound from the package and is no longer a dependency of this
570
+ buy. The library's reject status on A is preserved.
571
+ task: update_media_buy
572
+ schema_ref: "media-buy/update-media-buy-request.json"
573
+ response_schema_ref: "media-buy/update-media-buy-response.json"
574
+ doc_ref: "/media-buy/task-reference/update_media_buy"
575
+ comply_scenario: media_buy_lifecycle
576
+ stateful: true
577
+ expected: |
578
+ The seller accepts the package update and the next get_media_buys
579
+ reflects the new assignment with the impairment cleared.
580
+
581
+ sample_request:
582
+ account:
583
+ brand:
584
+ domain: "acmeoutdoor.example"
585
+ operator: "pinnacle-agency.example"
586
+ media_buy_id: "$context.media_buy_id"
587
+ packages:
588
+ - package_id: "$context.package_id"
589
+ creative_assignments:
590
+ - creative_id: "acme_dep_banner_002"
591
+ idempotency_key: "$generate:uuid_v4#dependency_impairment_swap_assignment"
592
+ context:
593
+ correlation_id: "dependency_impairment--swap_assignment"
594
+ validations:
595
+ - check: response_schema
596
+ description: "Response matches update-media-buy-response.json schema"
597
+
598
+ - id: get_buy_recovered
599
+ title: "Read the buy — health: ok, impairments[] cleared via swap"
600
+ task: get_media_buys
601
+ schema_ref: "media-buy/get-media-buys-request.json"
602
+ response_schema_ref: "media-buy/get-media-buys-response.json"
603
+ doc_ref: "/media-buy/task-reference/get_media_buys"
604
+ comply_scenario: media_buy_lifecycle
605
+ stateful: true
606
+ expected: |
607
+ health: ok, impairments[] empty/absent. Creative A is still
608
+ rejected in the library (verifiable separately via list_creatives)
609
+ but is no longer assigned to the package, so the impairment
610
+ clears. A non-empty impairments[] here indicates the seller is
611
+ holding stale state — the assignment swap should have removed
612
+ creative A as a buy dependency.
613
+
614
+ sample_request:
615
+ account:
616
+ brand:
617
+ domain: "acmeoutdoor.example"
618
+ operator: "pinnacle-agency.example"
619
+ media_buy_ids:
620
+ - "$context.media_buy_id"
621
+ context:
622
+ correlation_id: "dependency_impairment--get_buy_recovered"
623
+ validations:
624
+ - check: response_schema
625
+ description: "Response matches get-media-buys-response.json schema"
626
+ - check: field_value
627
+ path: "media_buys[0].health"
628
+ allowed_values: ["ok"]
629
+ description: "Buy health returned to ok after assignment swap (health-iff rule, ok direction)"
630
+ - check: field_value_or_absent
631
+ path: "media_buys[0].impairments"
632
+ value: []
633
+ description: "impairments[] is empty (or absent) — seller cleared the stale A-entry when A stopped being a dependency. health-iff biconditional would fail with health: ok and a non-empty impairments[]."