Module adcp.types.buyer
AdCP buyer types — curated partial surface.
Buy-side (DSP / agency) surface — product discovery, briefs / refine, pricing, media buys the buyer sends, performance feedback, brand rights.
A stable, narrow alternative to importing the whole :mod:adcp.types
namespace. Every name here is also exported from :mod:adcp.types; this
module simply groups the ones a buyer integration reaches for, and never
exposes the internal generated layer.
This module is for curation and discoverability, not a separate
performance tier: importing it is cheap, but the first access to any AdCP
type (here or via :mod:adcp.types / :mod:adcp) realizes the full generated
Pydantic graph — there is no per-domain graph. Use it for a smaller, focused
import surface.
from adcp.types.buyer import GetProductsRequest
Classes
class AcceptProposalRequest (**data: Any)-
Expand source code
class AcceptProposalRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='forbid', ) idempotency_key: Annotated[ str, Field(max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$') ] name: Annotated[ str | None, Field( description='Human-readable MediaBuy name supplied by the buyer for trafficking UI display and operational communication. When supplied, this value wins over proposal.name; the seller MUST persist it and echo it unchanged on the commitment success response and subsequent get_media_buys reads. It is operational metadata outside accepted_proposal and is not covered by proposal_terms_digest or terms_digest. When an acceptance creates a MediaBuy and name is absent, the seller MAY seed the MediaBuy name from proposal.name only when proposal.name already satisfies the MediaBuy name constraints (non-whitespace and no longer than 255 characters); the seller MUST NOT silently truncate or otherwise rewrite it. A seeded value counts as a name created through AdCP and MUST be reported on commitment and read surfaces. This display label is not an identifier or financial reference.', max_length=255, min_length=1, pattern='\\S', ), ] = None account: canonical_account_ref.CanonicalAccountReference proposal_id: Annotated[str, Field(min_length=1)] proposal_terms_digest: Annotated[ str, Field( description='terms_digest from the committed proposal. The seller MUST atomically verify both ID and digest before acceptance.', pattern='^sha256:[A-Za-z0-9_-]{43}$', ), ] total_budget: Annotated[ TotalBudget | None, Field( description='Execution amount when the committed proposal defines scalable percentages or constraints rather than a fixed total.' ), ] = None daily_budget_cap: Annotated[ StrictFloat | None, Field( description="Optional hard aggregate daily spend ceiling applied when the committed proposal is accepted. It constrains execution without changing the proposal's negotiated pricing.", ge=0.0, ), ] = None budget_cap_timezone: Annotated[ str | None, Field( description='Optional shared IANA cap-day timezone override. Requires buyer_timezone_override support. When omitted, budget_capping.timezone_basis selects Account.timezone or fixed_timezone.', min_length=1, ), ] = None io_acceptance: IoAcceptance | None = None purchase_order_ref: Annotated[str | None, Field(max_length=255, min_length=1)] = None governance_context: Annotated[str | None, Field(max_length=4096, min_length=1)] = None push_notification_config: push_notification_config_1.PushNotificationConfig | None = None reporting_webhook: Annotated[ reporting_webhook_1.ReportingWebhook | None, Field( description='Optional reporting delivery configuration established atomically when the proposal is accepted. This is execution metadata and does not alter the accepted commercial terms digest.' ), ] = None opportunity: Annotated[ Opportunity | None, Field( description='Optional planning-cycle closure. Success infers closed with accepted_with_seller when status is omitted. If the proposal carries opportunity_id, a supplied ID MUST match; the accepted proposal preserves that association.' ), ] = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var account : CanonicalAccountReference1 | CanonicalAccountReference2var budget_cap_timezone : str | Nonevar context : ContextObject | Nonevar daily_budget_cap : float | Nonevar ext : ExtensionObject | Nonevar governance_context : str | Nonevar idempotency_key : strvar io_acceptance : IoAcceptance | Nonevar model_configvar name : str | Nonevar opportunity : Opportunity | Nonevar proposal_id : strvar proposal_terms_digest : strvar purchase_order_ref : str | Nonevar push_notification_config : PushNotificationConfig | Nonevar reporting_webhook : ReportingWebhook | Nonevar total_budget : TotalBudget | None
Instance variables
var adcp_major_version : int | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
Inherited members
class AcquireRightsRequest (**data: Any)-
Expand source code
class AcquireRightsRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='allow', ) governance_context: Annotated[ str | None, Field( description='Opaque intent authorization for this rights commitment. Required when governance applies to the resolved account.', max_length=4096, min_length=1, pattern='^[\\x20-\\x7E]+$', ), ] = None rights_id: Annotated[ str, Field(description='Rights offering identifier from get_rights response') ] pricing_option_id: Annotated[ str, Field(description='Selected pricing option from the rights offering') ] buyer: Annotated[brand_ref.BrandReference, Field(description="The buyer's brand identity")] account: Annotated[ account_ref.AccountReference | None, Field( description='Account context for this acquisition. Used by the brand agent to resolve any governance agent previously bound for this brand+operator pair via sync_governance. When both an inline governance_context token and a bound governance agent are present, the token is verified against that resolved relationship. An agent advertising adcp.governance_enforcement for acquire_rights MUST resolve an account and returns ACCOUNT_REQUIRED when neither the request nor an existing resource supplies one; it MUST NOT infer that a missing token means ungoverned. Legacy non-claiming agents may continue to treat omission of both fields as ungoverned during 3.x. Pass a natural key (brand, operator, optional sandbox) or a seller-assigned account_id from list_accounts.' ), ] = None campaign: Annotated[Campaign, Field(description='Campaign details for rights clearance')] revocation_webhook: Annotated[ push_notification_config_1.PushNotificationConfig, Field( description='Webhook for rights revocation notifications. If the rights holder needs to revoke rights (talent scandal, contract violation, etc.), they POST a revocation-notification to this URL. The buyer is responsible for stopping creative delivery upon receipt.' ), ] push_notification_config: Annotated[ push_notification_config_1.PushNotificationConfig | None, Field( description='Webhook for async status updates if the acquisition requires approval. The rights agent sends a webhook notification when the status transitions to acquired or rejected.' ), ] = None idempotency_key: Annotated[ str, Field( description='Client-generated key for safe retries. Resubmitting with the same key returns the original response rather than creating a duplicate acquisition. MUST be unique per (seller, request) pair to prevent cross-seller correlation. Use a fresh UUID v4 for each request.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var account : AccountReference1 | AccountReference2 | Nonevar buyer : BrandReferencevar campaign : Campaignvar context : ContextObject | Nonevar ext : ExtensionObject | Nonevar governance_context : str | Nonevar idempotency_key : strvar model_configvar pricing_option_id : strvar push_notification_config : PushNotificationConfig | Nonevar revocation_webhook : PushNotificationConfigvar rights_id : str
Inherited members
class BrandIdentity (**data: Any)-
Expand source code
class Brand(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) id: Annotated[ BrandId, Field(description='Brand identifier within the house. House chooses this ID.') ] url: Annotated[ AnyUrl | None, Field(description='Primary brand URL for context and asset discovery') ] = None identity_relying_parties: Annotated[ list[IdentityRelyingParty] | None, Field( description='Verified-identity relying parties scoped to this brand/property, for attestation provenance in TMP Identity Match. Use when a brand or property runs its own relying_party_id (per-property pseudonyms); entity-wide relying parties live on the house object. See specs/tmp-verified-identity-attestation.md.' ), ] = None names: Annotated[ list[LocalizedName], Field( description='Localized brand names. Multiple entries per language allowed for aliases.', min_length=1, ), ] keller_type: KellerType | None = None parent_brand: Annotated[ BrandId | None, Field(description='Parent brand ID for sub-brands and endorsed brands') ] = None description: Annotated[str | None, Field(description='Brand description')] = None industries: Annotated[ list[str] | None, Field( description="Brand industries (e.g., ['automotive'] or ['pharmaceutical', 'cpg'] for a consumer health company). Describes what the company does — not what regulatory regimes apply (use policy_categories for that).", min_length=1, ), ] = None target_audience: Annotated[str | None, Field(description='Primary target audience')] = None logos: Annotated[list[Logo] | None, Field(description='Brand logo assets')] = None colors: Colors | None = None fonts: Fonts | None = None tone: Annotated[ str | Tone | None, Field(description='Brand voice and messaging tone guidelines') ] = None tagline: Annotated[ str | Tagline | None, Field( description='Brand tagline or slogan. Accepts a plain string or a localized array matching the names pattern.' ), ] = None assets: Annotated[list[Asset] | None, Field(description='Brand asset library')] = None properties: Annotated[ list[Property] | None, Field( description='Digital properties associated with this brand — owned, managed, or represented' ), ] = None product_catalog: ProductCatalog | None = None privacy_policy_url: Annotated[ AnyUrl | None, Field(description="URL to the brand's privacy policy") ] = None data_subject_contestation: DataSubjectContestation | None = None disclaimers: Annotated[ list[Disclaimer] | None, Field(description='Legal disclaimers for creatives') ] = None trademarks: Annotated[ list[Trademark] | None, Field( description="Brand-level registered trademarks. Use for marks the brand owns or controls (e.g., a sub-brand's own marks distinct from the corporate parent). House-level trademarks live on the house object; resolution between the two is union — both lists are valid claims." ), ] = None voice_synthesis: Annotated[ VoiceSynthesis | None, Field(description='TTS voice synthesis configuration for AI-generated audio'), ] = None avatar: Annotated[Avatar | None, Field(description='Visual avatar configuration')] = None visual_guidelines: Annotated[ VisualGuidelines | None, Field(description='Structured visual rules for generative creative systems'), ] = None agents: Annotated[ Agents | None, Field( description='Agents authorized to act on behalf of this brand. Consumers resolving an agent by URL use the matching brand-level entry; do not infer a type-wide override of unrelated house-level entries when multiple same-type entries exist.' ), ] = None brand_agent: Annotated[ BrandAgent | None, Field( deprecated=True, description="Deprecated: use agents array with type 'brand' instead. Brand agent that provides dynamic brand data via MCP.", ), ] = None rights_agent: Annotated[ RightsAgent | None, Field( deprecated=True, description="Deprecated: use agents array with type 'rights' instead. Rights licensing agent for this brand.", ), ] = None contact: Annotated[Contact1 | None, Field(description='Brand-level contact information')] = None collections: Annotated[ list[Collection] | None, Field( description="Collections this person or brand is associated with. Enables bidirectional linking: a collection's talent references brand.json via brand_url, and brand.json links back to collections." ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Subclasses
Class variables
var agents : Agents | Nonevar assets : list[Asset] | Nonevar avatar : Avatar | Nonevar brand_agent : BrandAgent | Nonevar collections : list[Collection] | Nonevar colors : Colors | Nonevar contact : Contact1 | Nonevar data_subject_contestation : DataSubjectContestation | Nonevar description : str | Nonevar disclaimers : list[Disclaimer] | Nonevar fonts : Fonts | Nonevar id : BrandIdvar identity_relying_parties : list[IdentityRelyingParty] | Nonevar industries : list[str] | Nonevar keller_type : KellerType | Nonevar logos : list[Logo] | Nonevar model_configvar names : list[LocalizedName]var parent_brand : BrandId | Nonevar privacy_policy_url : pydantic.networks.AnyUrl | Nonevar product_catalog : ProductCatalog | Nonevar properties : list[Property] | Nonevar rights_agent : RightsAgent | Nonevar tagline : str | Tagline | Nonevar target_audience : str | Nonevar tone : str | Tone | Nonevar trademarks : list[Trademark] | Nonevar url : pydantic.networks.AnyUrl | Nonevar visual_guidelines : VisualGuidelines | Nonevar voice_synthesis : VoiceSynthesis | None
Inherited members
class BrandReference (**data: Any)-
Expand source code
class BrandReference(AdCPBaseModel): model_config = ConfigDict( extra='forbid', ) domain: Annotated[ str, Field( description="Domain where /.well-known/brand.json is hosted, or the brand's operating domain", pattern='^[a-z0-9]([a-z0-9-]*[a-z0-9])?(\\.[a-z0-9]([a-z0-9-]*[a-z0-9])?)*$', ), ] brand_id: Annotated[ brand_id_1.BrandId | None, Field( description='Brand identifier within the house portfolio. Optional for single-brand domains.' ), ] = None countries: Annotated[ list[Country] | None, Field( description='Canonical set of ISO 3166-1 alpha-2 countries for this advertiser identity. Omit for a global/default identity. Array order is not meaningful; producers MUST sort codes lexicographically before computing keys or signatures. This qualifies account identity and is not delivery targeting.', min_length=1, ), ] = None industries: Annotated[ list[str] | None, Field( description="Inline override for the brand's industries. Useful when the caller cannot modify the brand's canonical brand.json but needs to declare industries for governance (e.g., Annex III vertical detection). brand.json remains the canonical source; when omitted here, governance agents SHOULD resolve from brand.json." ), ] = None data_subject_contestation: Annotated[ DataSubjectContestation | None, Field( description="Inline override for the brand's contestation contact point. Useful when the operator does not control brand.json but needs to discharge Art 22(3) for this plan. brand.json is canonical; when omitted, governance agents resolve brand → house → missing." ), ] = None brand_kit_override: Annotated[ BrandKitOverride | None, Field( description="Inline override for brand-kit fields normally resolved from `/.well-known/brand.json` on `domain` (logo, colors, voice, tagline). Use when brand.json is missing, stale, or inappropriate for this specific call — e.g., a campaign-scoped tagline, a co-branded creative, a freshly-rebranded color palette the brand.json hasn't shipped yet. Same inline-override pattern as `industries` and `data_subject_contestation` above: brand.json is canonical, the override is per-call. Adopters needing to override fields outside this subset (`voice_attributes`, `prohibited_terms`, etc.) MUST publish a different brand.json and reference it via a different `domain` — the inline override is intentionally narrow to a small high-traffic subset.\n\n**Merge semantics (normative).** The merge is **field-level**, not whole-object replacement. Each field within `brand_kit_override` (`logo`, `colors`, `voice`, `tagline`) is evaluated independently — when a field is present on the override the override value applies; when a field is absent the brand.json value applies (or is absent if brand.json doesn't carry one either). For composite fields (`colors.primary`, `colors.secondary`, `colors.accent`), the merge is one level deeper: each color slot is evaluated independently — a producer can override `colors.primary` while still inheriting `colors.secondary` from brand.json. SDKs MUST NOT treat a present `brand_kit_override.colors` as wiping the brand.json `colors` block entirely; only the per-slot fields present in the override take precedence. Without this rule, a partial-override semantics would diverge across SDKs and produce inconsistent rendering for the same payload." ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var brand_id : BrandId | Nonevar brand_kit_override : BrandKitOverride | Nonevar countries : list[Country] | Nonevar data_subject_contestation : DataSubjectContestation | Nonevar domain : strvar industries : list[str] | Nonevar model_config
Inherited members
class BrandSource (*args, **kwds)-
Expand source code
class BrandSource(Enum): brand_json = "brand_json" community = "community" enriched = "enriched"Create a collection of name/value pairs.
Example enumeration:
>>> class Color(Enum): ... RED = 1 ... BLUE = 2 ... GREEN = 3Access them by:
- attribute access::
>>> Color.RED <Color.RED: 1>- value lookup:
>>> Color(1) <Color.RED: 1>- name lookup:
>>> Color['RED'] <Color.RED: 1>Enumerations can be iterated over, and know how many members they have:
>>> len(Color) 3>>> list(Color) [<Color.RED: 1>, <Color.BLUE: 2>, <Color.GREEN: 3>]Methods can be added to enumerations, and members can have their own attributes – see the documentation for details.
Ancestors
- enum.Enum
Class variables
var brand_jsonvar communityvar enriched
class BuyProductsRequest (**data: Any)-
Expand source code
class BuyProductsRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='forbid', ) idempotency_key: Annotated[ str, Field(max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$') ] name: Annotated[ str | None, Field( description='Human-readable name for this media buy, shared by buyer and seller for trafficking UI display and operational communication. When supplied, the seller MUST persist it and echo it unchanged on the commitment success response and subsequent get_media_buys reads. The name is operational metadata outside accepted_proposal and is not covered by terms_digest. This display label is not an identifier or financial reference.', max_length=255, min_length=1, pattern='\\S', ), ] = None account: Annotated[ canonical_account_ref.CanonicalAccountReference, Field( description='Execution account. A natural-key account is the single brand source and MUST NOT be combined with top-level brand.' ), ] brand: Annotated[ brand_key.BrandKey | None, Field( description='Brand source required when account is ID-only. Omit when account already contains brand and operator.' ), ] = None advertiser_industry: Annotated[ advertiser_industry_1.AdvertiserIndustry | None, Field( description='Industry classification for this campaign. Sellers may infer it from the resolved brand manifest when omitted.' ), ] = None feed_version: Annotated[ str, Field( description='list_products feed_version containing the published offers being accepted. Sellers reject stale or mismatched versions rather than silently applying changed terms.', min_length=1, ), ] pricing_version: Annotated[ str | None, Field( description='list_products pricing_version containing the accepted rate. Buyers MUST include this whenever list_products returned one; omission means the seller does not version pricing separately.', min_length=1, ), ] = None purchases: Annotated[list[product_purchase_input.ProductPurchaseInput], Field(min_length=1)] total_budget: TotalBudget | None = None daily_budget_cap: Annotated[ StrictFloat | None, Field( description="Optional hard aggregate daily spend ceiling in total_budget.currency or the media buy's derived currency. It bounds the shared daily spend pool without allocating or reserving amounts for purchases.", ge=0.0, ), ] = None frequency_cap: Annotated[ media_buy_frequency_cap.MediaBuyFrequencyCap | None, Field( description='Optional max-impression cap using one counter across purchases. Buyers send it only when aggregate_frequency_capping is advertised. Every selected product must declare compatible media_buy_support; otherwise the purchase is rejected atomically with UNSUPPORTED_FEATURE before any mutation, never clamped.' ), ] = None budget_cap_timezone: Annotated[ str | None, Field( description='Optional IANA timezone override shared by every aggregate and purchase daily cap. Requires buyer_timezone_override support; otherwise rejected with UNSUPPORTED_FEATURE. When omitted, budget_capping.timezone_basis selects Account.timezone or fixed_timezone.', min_length=1, ), ] = None budget_allocation: canonical_budget_allocation.CanonicalBudgetAllocation | None = None start_time: start_timing.StartTiming end_time: AwareDatetime pacing: Annotated[ pacing_1.Pacing | None, Field( description='Aggregate media-buy pacing. In seller-optimized allocation, a seller declaring media_buy.features.seller_optimized_budget MUST accept omission and `even`; it MAY reject `asap` or `front_loaded` with UNSUPPORTED_FEATURE (error.field `pacing`) before any provider mutation and MUST NOT silently coerce them to `even`. Fixed-allocation semantics are unchanged.' ), ] = None bidding: bidding_policy.BiddingPolicy | None = None paused: StrictBool | None = False purchase_order_ref: Annotated[str | None, Field(max_length=255, min_length=1)] = None agency_estimate_number: Annotated[str | None, Field(max_length=100)] = None invoice_recipient: Annotated[ business_entity.BusinessEntity | None, Field(description='Authorized per-buy billing entity override.'), ] = None governance_context: Annotated[str | None, Field(max_length=4096, min_length=1)] = None push_notification_config: push_notification_config_1.PushNotificationConfig | None = None reporting_webhook: Annotated[ reporting_webhook_1.ReportingWebhook | None, Field( description='Optional reporting delivery configuration established atomically with the MediaBuy. This is execution metadata and is not part of the immutable product pricing terms.' ), ] = None opportunity: Annotated[ Opportunity | None, Field( description='Optional planning-cycle closure for a direct product purchase. Success infers closed with accepted_with_seller when status is omitted; an explicit status MUST carry that same closure.' ), ] = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var account : CanonicalAccountReference1 | CanonicalAccountReference2var advertiser_industry : AdvertiserIndustry | Nonevar agency_estimate_number : str | Nonevar bidding : BiddingPolicy | Nonevar brand : BrandKey | Nonevar budget_allocation : CanonicalBudgetAllocation1 | CanonicalBudgetAllocation2 | Nonevar budget_cap_timezone : str | Nonevar context : ContextObject | Nonevar daily_budget_cap : float | Nonevar end_time : pydantic.types.AwareDatetimevar ext : ExtensionObject | Nonevar feed_version : strvar frequency_cap : MediaBuyFrequencyCap | Nonevar governance_context : str | Nonevar idempotency_key : strvar invoice_recipient : BusinessEntity | Nonevar model_configvar name : str | Nonevar opportunity : Opportunity | Nonevar pacing : Pacing | Nonevar paused : bool | Nonevar pricing_version : str | Nonevar purchase_order_ref : str | Nonevar purchases : list[ProductPurchaseInput]var push_notification_config : PushNotificationConfig | Nonevar reporting_webhook : ReportingWebhook | Nonevar start_time : Literal['asap'] | pydantic.types.AwareDatetimevar total_budget : TotalBudget | None
Instance variables
var adcp_major_version : int | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
Inherited members
class ControlMediaBuyRequest (**data: Any)-
Expand source code
class ControlMediaBuyRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='forbid', ) idempotency_key: Annotated[ str, Field(max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$') ] account: canonical_account_ref.CanonicalAccountReference media_buy_id: Annotated[str, Field(min_length=1)] revision: Annotated[ SchemaInt, Field( description='Required optimistic-concurrency revision from the latest MediaBuy snapshot.', ge=1, ), ] name: Annotated[ str | None, Field( description='Replace the human-readable MediaBuy name as revision-checked operational metadata. This display label is not an identifier, financial reference, or change to the accepted commercial terms.', max_length=255, min_length=1, pattern='\\S', ), ] = None paused: StrictBool | None = None canceled: Annotated[ Literal[True] | None, Field( description='Exercise an already-accepted unilateral cancellation right. A cancellation requiring seller agreement is requested by refining the accepted proposal.' ), ] = None cancellation_reason: Annotated[str | None, Field(max_length=500, min_length=1)] = None total_budget: TotalBudget | None = None daily_budget_cap: Annotated[ StrictFloat | None, Field( description='Replace the hard aggregate daily cap; null removes it. Numeric changes apply immediately with current-cap-day spend counted and do not redistribute purchase caps.', ge=0.0, ), ] = None frequency_cap: Annotated[ media_buy_frequency_cap.MediaBuyFrequencyCap | None, Field( description='Replace the shared MediaBuy frequency cap; null removes it. The change applies immediately without resetting counters: qualifying prior exposures still count in the resulting active window. Sellers MUST reject the complete mutation with UNSUPPORTED_FEATURE, before any change, if the cap is outside declared constraints or any active package cannot participate in the resulting shared counter, and MUST NOT clamp it. Requires update_media_buy_frequency_cap in available_actions.' ), ] = None budget_cap_timezone: Annotated[ str | None, Field( description='Replace the shared IANA cap-day timezone override; null restores the default selected by budget_capping.timezone_basis (Account.timezone or fixed_timezone). A timezone change begins at the next boundary under the previously effective timezone.', min_length=1, ), ] = None budget_allocation: canonical_budget_allocation.CanonicalBudgetAllocation | None = None pacing: Annotated[ pacing_1.Pacing | None, Field( description='Replace aggregate media-buy pacing. In seller-optimized allocation, a seller declaring media_buy.features.seller_optimized_budget MUST accept omission and `even`; it MAY reject `asap` or `front_loaded` with UNSUPPORTED_FEATURE (error.field `pacing`) before any provider mutation and MUST NOT silently coerce them to `even`. Fixed-allocation semantics are unchanged.' ), ] = None bidding: bidding_policy.BiddingPolicy | None = None packages: Annotated[ list[package_control.PackageControl] | None, Field( description='Operational patches keyed by package_id. Each package_id MUST appear at most once; sellers reject duplicate IDs atomically.', min_length=1, ), ] = None reporting_webhook: reporting_webhook_1.ReportingWebhook | None = None governance_context: Annotated[str | None, Field(max_length=4096, min_length=1)] = None push_notification_config: push_notification_config_1.PushNotificationConfig | None = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = None @model_validator(mode='after') def _require_schema_required_group(self) -> ControlMediaBuyRequest: # ``required`` asks whether the caller supplied the field, which is what # model_fields_set answers. An explicit null is a supplied value — on a # mutation input it is the command to clear — and a default the caller # never sent is not. for group in (('name',), ('paused',), ('canceled',), ('total_budget',), ('daily_budget_cap',), ('frequency_cap',), ('budget_cap_timezone',), ('budget_allocation',), ('pacing',), ('bidding',), ('packages',), ('reporting_webhook',),): if all(name in self.model_fields_set for name in group): return self raise ValueError( 'ControlMediaBuyRequest requires at least one of these field groups: name | paused | canceled | total_budget | daily_budget_cap | frequency_cap | budget_cap_timezone | budget_allocation | pacing | bidding | packages | reporting_webhook' )The request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var account : CanonicalAccountReference1 | CanonicalAccountReference2var bidding : BiddingPolicy | Nonevar budget_allocation : CanonicalBudgetAllocation1 | CanonicalBudgetAllocation2 | Nonevar budget_cap_timezone : str | Nonevar canceled : Literal[True] | Nonevar cancellation_reason : str | Nonevar context : ContextObject | Nonevar daily_budget_cap : float | Nonevar ext : ExtensionObject | Nonevar frequency_cap : MediaBuyFrequencyCap | Nonevar governance_context : str | Nonevar idempotency_key : strvar media_buy_id : strvar model_configvar name : str | Nonevar pacing : Pacing | Nonevar packages : list[PackageControl] | Nonevar paused : bool | Nonevar push_notification_config : PushNotificationConfig | Nonevar reporting_webhook : ReportingWebhook | Nonevar revision : intvar total_budget : TotalBudget | None
Instance variables
var adcp_major_version : int | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
Inherited members
class CpaPricingOption (**data: Any)-
Expand source code
class CpaPricingOption(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) pricing_option_id: Annotated[ str, Field(description='Unique identifier for this pricing option within the product') ] pricing_model: Annotated[ Literal['cpa'], Field(description='Cost per acquisition (conversion event)') ] = 'cpa' event_type: Annotated[ event_type_1.EventType, Field( description='The conversion event type that triggers billing (e.g., purchase, lead, app_install)' ), ] custom_event_name: Annotated[ str | None, Field( description="Name of the custom event when event_type is 'custom'. Required when event_type is 'custom', ignored otherwise." ), ] = None event_source_id: Annotated[ str | None, Field( description='When present, only events from this specific event source count toward billing. Allows different CPA rates for different sources (e.g., online vs in-store purchases). Must match an event source configured via sync_event_sources.' ), ] = None currency: Annotated[ str, Field( description='ISO 4217 currency code', examples=['USD', 'EUR', 'GBP', 'JPY'], pattern='^[A-Z]{3}$', ), ] fixed_price: Annotated[ StrictFloat, Field(description='Fixed price per acquisition in the specified currency', gt=0.0), ] min_spend_per_package: Annotated[ StrictFloat | None, Field( description='Minimum spend requirement per package using this pricing option, in the specified currency', ge=0.0, ), ] = None price_breakdown: Annotated[ price_breakdown_1.PriceBreakdown | None, Field( description='Breakdown of how fixed_price was derived from the list (rate card) price. Only meaningful when fixed_price is present.' ), ] = None eligible_adjustments: Annotated[ list[adjustment_kind.PriceAdjustmentKind] | None, Field( description='Adjustment kinds applicable to this pricing option. Tells buyer agents which adjustments are available before negotiation. When absent, no adjustments are pre-declared — the buyer should check price_breakdown if present.' ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var currency : strvar custom_event_name : str | Nonevar eligible_adjustments : list[PriceAdjustmentKind] | Nonevar event_source_id : str | Nonevar event_type : EventTypevar fixed_price : floatvar min_spend_per_package : float | Nonevar model_configvar price_breakdown : PriceBreakdown | Nonevar pricing_model : Literal['cpa']var pricing_option_id : str
Inherited members
class CpcPricingOption (**data: Any)-
Expand source code
class CpcPricingOption(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) pricing_option_id: Annotated[ str, Field(description='Unique identifier for this pricing option within the product') ] pricing_model: Annotated[Literal['cpc'], Field(description='Cost per click')] = 'cpc' currency: Annotated[ str, Field( description='ISO 4217 currency code', examples=['USD', 'EUR', 'GBP', 'JPY'], pattern='^[A-Z]{3}$', ), ] fixed_price: Annotated[ StrictFloat | None, Field( description='Fixed price per click. If present, this is fixed pricing. If absent, auction-based.', ge=0.0, ), ] = None floor_price: Annotated[ StrictFloat | None, Field( description='Minimum acceptable bid for auction pricing (mutually exclusive with fixed_price). Bids below this value will be rejected.', ge=0.0, ), ] = None max_bid: Annotated[ StrictBool | None, Field( deprecated=True, description='DEPRECATED in 3.2 and removed in the next major. Legacy hint used only to normalize package bid_price to bidding.max_bid (true) or bidding.bid_amount (false/absent). New buyers express intent directly in bidding.', ), ] = False price_guidance: Annotated[ price_guidance_1.PriceGuidance | None, Field(description='Optional pricing guidance for auction-based bidding'), ] = None min_spend_per_package: Annotated[ StrictFloat | None, Field( description='Minimum spend requirement per package using this pricing option, in the specified currency', ge=0.0, ), ] = None price_breakdown: Annotated[ price_breakdown_1.PriceBreakdown | None, Field( description='Breakdown of how fixed_price was derived from the list (rate card) price. Only meaningful when fixed_price is present.' ), ] = None eligible_adjustments: Annotated[ list[adjustment_kind.PriceAdjustmentKind] | None, Field( description='Adjustment kinds applicable to this pricing option. Tells buyer agents which adjustments are available before negotiation. When absent, no adjustments are pre-declared — the buyer should check price_breakdown if present.' ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var currency : strvar eligible_adjustments : list[PriceAdjustmentKind] | Nonevar fixed_price : float | Nonevar floor_price : float | Nonevar max_bid : bool | Nonevar min_spend_per_package : float | Nonevar model_configvar price_breakdown : PriceBreakdown | Nonevar price_guidance : PriceGuidance | Nonevar pricing_model : Literal['cpc']var pricing_option_id : str
Inherited members
class CpmPricingOption (**data: Any)-
Expand source code
class CpmPricingOption(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) pricing_option_id: Annotated[ str, Field(description='Unique identifier for this pricing option within the product') ] pricing_model: Annotated[Literal['cpm'], Field(description='Cost per 1,000 impressions')] = 'cpm' currency: Annotated[ str, Field( description='ISO 4217 currency code', examples=['USD', 'EUR', 'GBP', 'JPY'], pattern='^[A-Z]{3}$', ), ] fixed_price: Annotated[ StrictFloat | None, Field( description='Fixed price per unit. If present, this is fixed pricing. If absent, auction-based.', ge=0.0, ), ] = None floor_price: Annotated[ StrictFloat | None, Field( description='Minimum acceptable bid for auction pricing (mutually exclusive with fixed_price). Bids below this value will be rejected.', ge=0.0, ), ] = None max_bid: Annotated[ StrictBool | None, Field( deprecated=True, description='DEPRECATED in 3.2 and removed in the next major. Legacy hint used only to normalize package bid_price to bidding.max_bid (true) or bidding.bid_amount (false/absent). New buyers express intent directly in bidding.', ), ] = False price_guidance: Annotated[ price_guidance_1.PriceGuidance | None, Field(description='Optional pricing guidance for auction-based bidding'), ] = None min_spend_per_package: Annotated[ StrictFloat | None, Field( description='Minimum spend requirement per package using this pricing option, in the specified currency', ge=0.0, ), ] = None price_breakdown: Annotated[ price_breakdown_1.PriceBreakdown | None, Field( description='Breakdown of how fixed_price was derived from the list (rate card) price. Only meaningful when fixed_price is present.' ), ] = None eligible_adjustments: Annotated[ list[adjustment_kind.PriceAdjustmentKind] | None, Field( description='Adjustment kinds applicable to this pricing option. Tells buyer agents which adjustments are available before negotiation. When absent, no adjustments are pre-declared — the buyer should check price_breakdown if present.' ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var currency : strvar eligible_adjustments : list[PriceAdjustmentKind] | Nonevar fixed_price : float | Nonevar floor_price : float | Nonevar max_bid : bool | Nonevar min_spend_per_package : float | Nonevar model_configvar price_breakdown : PriceBreakdown | Nonevar price_guidance : PriceGuidance | Nonevar pricing_model : Literal['cpm']var pricing_option_id : str
Inherited members
class CreateMediaBuyRequest (**data: Any)-
Expand source code
class CreateMediaBuyRequest(_LegacyCreateMediaBuyRequest, CanonicalBoundaryModel): """Canonical create request; packages are canonical package requests.""" packages: list[PackageRequest] | None = NoneCanonical create request; packages are canonical package requests.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- CreateMediaBuyRequest
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var model_configvar packages : list[PackageRequest] | None
Inherited members
class DeclineProposalsRequest (**data: Any)-
Expand source code
class DeclineProposalsRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='forbid', ) context_id: Annotated[ str | None, Field( description='MCP compatibility field: servers ignore this value; A2A uses transport-native Message/Task contextId.', min_length=1, ), ] = None context: context_1.ContextObject | None = None governance_context: Annotated[str | None, Field(max_length=4096, min_length=1)] = None push_notification_config: push_notification_config_1.PushNotificationConfig | None = None idempotency_key: Annotated[ str, Field( description='Client-generated key required for retry-safe proposal decline.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] declines: Annotated[ list[proposal_decline.ProposalDecline], Field( description='Proposal declines to apply. proposal_id is the semantic uniqueness key and values MUST be unique even when two entries otherwise differ; implementations enforce this rule because JSON Schema uniqueItems only compares whole objects. Results preserve request order.', max_length=25, min_length=1, ), ] opportunity: Annotated[ opportunity_context.OpportunityContext | None, Field( description='Optional planning-cycle update. Every named proposal MUST belong to this opportunity_id. Sellers apply the update only when every result is declined; if any result is unable, the opportunity remains unchanged. Use status closed when these declines end the broader opportunity.' ), ] = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar context_id : str | Nonevar declines : list[ProposalDecline]var governance_context : str | Nonevar idempotency_key : strvar model_configvar opportunity : OpportunityContext | Nonevar push_notification_config : PushNotificationConfig | None
Inherited members
class FeedbackSource (*args, **kwds)-
Expand source code
class FeedbackSource(StrEnum): buyer_attribution = 'buyer_attribution' third_party_measurement = 'third_party_measurement' platform_analytics = 'platform_analytics' verification_partner = 'verification_partner'Enum where members are also (and must be) strings
Ancestors
- enum.StrEnum
- builtins.str
- enum.ReprEnum
- enum.Enum
Class variables
var buyer_attributionvar platform_analyticsvar third_party_measurementvar verification_partner
class FlatRatePricingOption (**data: Any)-
Expand source code
class FlatRatePricingOption(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) pricing_option_id: Annotated[ str, Field(description='Unique identifier for this pricing option within the product') ] pricing_model: Annotated[ Literal['flat_rate'], Field(description='Fixed cost regardless of delivery volume') ] = 'flat_rate' currency: Annotated[ str, Field( description='ISO 4217 currency code', examples=['USD', 'EUR', 'GBP', 'JPY'], pattern='^[A-Z]{3}$', ), ] fixed_price: Annotated[ StrictFloat | None, Field( description='Flat rate cost. If present, this is fixed pricing. If absent, auction-based.', ge=0.0, ), ] = None floor_price: Annotated[ StrictFloat | None, Field( description='Minimum acceptable bid for auction pricing (mutually exclusive with fixed_price). Bids below this value will be rejected.', ge=0.0, ), ] = None price_guidance: Annotated[ price_guidance_1.PriceGuidance | None, Field(description='Optional pricing guidance for auction-based bidding'), ] = None parameters: Annotated[ Parameters | None, Field( description='DOOH inventory allocation parameters. Sponsorship and takeover flat_rate options omit this field entirely — only include for digital out-of-home inventory.', title='DoohParameters', ), ] = None min_spend_per_package: Annotated[ StrictFloat | None, Field( description='Minimum spend requirement per package using this pricing option, in the specified currency', ge=0.0, ), ] = None price_breakdown: Annotated[ price_breakdown_1.PriceBreakdown | None, Field( description='Breakdown of how fixed_price was derived from the list (rate card) price. Only meaningful when fixed_price is present.' ), ] = None eligible_adjustments: Annotated[ list[adjustment_kind.PriceAdjustmentKind] | None, Field( description='Adjustment kinds applicable to this pricing option. Tells buyer agents which adjustments are available before negotiation. When absent, no adjustments are pre-declared — the buyer should check price_breakdown if present.' ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var currency : strvar eligible_adjustments : list[PriceAdjustmentKind] | Nonevar fixed_price : float | Nonevar floor_price : float | Nonevar min_spend_per_package : float | Nonevar model_configvar parameters : Parameters | Nonevar price_breakdown : PriceBreakdown | Nonevar price_guidance : PriceGuidance | Nonevar pricing_model : Literal['flat_rate']var pricing_option_id : str
Inherited members
class GetBrandIdentityRequest (**data: Any)-
Expand source code
class GetBrandIdentityRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='allow', ) brand_id: Annotated[str, Field(description='Brand identifier from brand.json brands array')] fields: Annotated[ list[Field1] | None, Field( description='Optional identity sections to include in the response. When omitted, all sections the caller is authorized to see are returned. Core fields (brand_id, house, names) are always returned and do not need to be requested.', min_length=1, ), ] = None use_case: Annotated[ str | None, Field( description="Intended use case, so the agent can tailor the response. A 'voice_synthesis' use case returns voice configs; a 'likeness' use case returns high-res photos and appearance guidelines." ), ] = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var brand_id : strvar context : ContextObject | Nonevar ext : ExtensionObject | Nonevar fields : list[Field1] | Nonevar model_configvar use_case : str | None
Inherited members
class GetProductsInputRequiredResponse (**data: Any)-
Expand source code
class GetProductsInputRequired(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) reason: Annotated[ Reason | None, Field(description='Reason code indicating why input is needed') ] = None partial_results: Annotated[ list[product.Product] | None, Field(description='Partial product results that may help inform the clarification'), ] = None suggestions: Annotated[ list[str] | None, Field(description='Suggested values or options for the required input') ] = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar ext : ExtensionObject | Nonevar model_configvar partial_results : list[Product] | Nonevar reason : Reason | Nonevar suggestions : list[str] | None
Inherited members
class GetProductsRequest (**data: Any)-
Expand source code
class GetProductsRequest(_LegacyGetProductsRequest, CanonicalBoundaryModel): """Canonical discovery request with legacy response-field selection rejected.""" filters: ProductFilters | None = None @field_validator("fields") @classmethod def _reject_legacy_fields(cls, value: Any) -> Any: if value and any( is_legacy_creative_identity_key(getattr(item, "value", item)) for item in value ): raise ValueError( "format_id and format_ids are unavailable on the canonical get_products API" ) return valueCanonical discovery request with legacy response-field selection rejected.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- GetProductsRequest
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var filters : ProductFilters | Nonevar model_config
class GetProductsBriefRequest (**data: Any)-
Expand source code
class GetProductsRequest(_LegacyGetProductsRequest, CanonicalBoundaryModel): """Canonical discovery request with legacy response-field selection rejected.""" filters: ProductFilters | None = None @field_validator("fields") @classmethod def _reject_legacy_fields(cls, value: Any) -> Any: if value and any( is_legacy_creative_identity_key(getattr(item, "value", item)) for item in value ): raise ValueError( "format_id and format_ids are unavailable on the canonical get_products API" ) return valueCanonical discovery request with legacy response-field selection rejected.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- GetProductsRequest
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var filters : ProductFilters | Nonevar model_config
class GetProductsRefineRequest (**data: Any)-
Expand source code
class GetProductsRequest(_LegacyGetProductsRequest, CanonicalBoundaryModel): """Canonical discovery request with legacy response-field selection rejected.""" filters: ProductFilters | None = None @field_validator("fields") @classmethod def _reject_legacy_fields(cls, value: Any) -> Any: if value and any( is_legacy_creative_identity_key(getattr(item, "value", item)) for item in value ): raise ValueError( "format_id and format_ids are unavailable on the canonical get_products API" ) return valueCanonical discovery request with legacy response-field selection rejected.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- GetProductsRequest
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var filters : ProductFilters | Nonevar model_config
class GetProductsWholesaleRequest (**data: Any)-
Expand source code
class GetProductsRequest(_LegacyGetProductsRequest, CanonicalBoundaryModel): """Canonical discovery request with legacy response-field selection rejected.""" filters: ProductFilters | None = None @field_validator("fields") @classmethod def _reject_legacy_fields(cls, value: Any) -> Any: if value and any( is_legacy_creative_identity_key(getattr(item, "value", item)) for item in value ): raise ValueError( "format_id and format_ids are unavailable on the canonical get_products API" ) return valueCanonical discovery request with legacy response-field selection rejected.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- GetProductsRequest
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var filters : ProductFilters | Nonevar model_config
Inherited members
class GetProductsResponse (**data: Any)-
Expand source code
class GetProductsResponse(_LegacyGetProductsResponse, CanonicalBoundaryModel): """Canonical discovery response; products are canonical products.""" products: list[Product] | None = None # type: ignore[assignment]Canonical discovery response; products are canonical products.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- GetProductsResponse
- AdcpResponse
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- ProtocolEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var model_configvar products : list[Product] | None
class GetProductsSuccessResponse (**data: Any)-
Expand source code
class GetProductsResponse(_LegacyGetProductsResponse, CanonicalBoundaryModel): """Canonical discovery response; products are canonical products.""" products: list[Product] | None = None # type: ignore[assignment]Canonical discovery response; products are canonical products.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- GetProductsResponse
- AdcpResponse
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- ProtocolEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var model_configvar products : list[Product] | None
Inherited members
class GetProductsSubmittedResponse (**data: Any)-
Expand source code
class GetProductsSubmitted(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) status: Annotated[ Literal['submitted'], Field( description='Task-level status literal. Discriminates this async envelope from the synchronous success shape, whose products array is issued in-line. See task-status.json for the full task-status enum.' ), ] = 'submitted' task_id: Annotated[ str, Field( description='Task handle the buyer uses with get_task_status (or the legacy AdCP tasks/get alias), and that the seller references on push-notification callbacks. The products array is issued on the completion artifact, not here. This AdCP application-layer handle remains the snake_case task_id in every transport payload and is distinct from any transport-native A2A Task id.' ), ] message: Annotated[ str | None, Field( description="Optional human-readable explanation of why the task is submitted — e.g., 'Custom curation queued; typical turnaround 10–30 minutes.' Plain text only. Buyers MUST treat this as untrusted seller input: escape before rendering to HTML UIs, and sanitize or isolate before passing to an LLM prompt context — a hostile seller may inject prompt-injection payloads aimed at the buyer's agent.", max_length=2000, ), ] = None estimated_completion: Annotated[ AwareDatetime | None, Field(description='Estimated completion time for the search') ] = None errors: Annotated[ list[error.Error] | None, Field( description='Optional advisory errors accompanying the submitted envelope. Use only for non-blocking warnings (e.g., throttled_severity advisories, governance observations). Terminal failures belong in the error branch, not here.' ), ] = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar errors : list[Error] | Nonevar estimated_completion : pydantic.types.AwareDatetime | Nonevar ext : ExtensionObject | Nonevar message : str | Nonevar model_configvar status : Literal['submitted']var task_id : str
Inherited members
class GetProductsWorkingResponse (**data: Any)-
Expand source code
class GetProductsWorking(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) percentage: Annotated[ StrictFloat | None, Field(description='Progress percentage of the search operation', ge=0.0, le=100.0), ] = None current_step: Annotated[ str | None, Field( description="Current step in the search process (e.g., 'searching_inventory', 'validating_availability')" ), ] = None total_steps: Annotated[ SchemaInt | None, Field(description='Total number of steps in the search process') ] = None step_number: Annotated[ SchemaInt | None, Field(description='Current step number (1-indexed)') ] = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar current_step : str | Nonevar ext : ExtensionObject | Nonevar model_configvar percentage : float | Nonevar step_number : int | Nonevar total_steps : int | None
Inherited members
class GetRightsRequest (**data: Any)-
Expand source code
class GetRightsRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='allow', ) query: Annotated[ str, Field( description='Natural language description of desired rights. The agent interprets intent, budget signals, and compatibility from this text.', max_length=2000, ), ] uses: Annotated[ list[right_use.RightUse], Field( description='Rights uses being requested. The agent returns options covering these uses, potentially bundled into composite pricing.', min_length=1, ), ] buyer_brand: Annotated[ brand_ref.BrandReference | None, Field( description="The buyer's brand. The agent fetches the buyer's brand.json for compatibility filtering (e.g., dietary conflicts, competitor exclusions)." ), ] = None countries: Annotated[ list[Country] | None, Field( description='Countries where rights are needed (ISO 3166-1 alpha-2). Filters to rights available in these markets.' ), ] = None brand_id: Annotated[ str | None, Field( description="Search within a specific brand's rights. If omitted, searches across the agent's full roster." ), ] = None right_type: Annotated[ right_type_1.RightType | None, Field(description='Filter by type of rights (talent, music, stock_media, etc.)'), ] = None include_excluded: Annotated[ StrictBool | None, Field( description='Include filtered-out results in the excluded array with reasons. Defaults to false.' ), ] = False pagination: Annotated[ pagination_request.PaginationRequest | None, Field(description='Pagination parameters for large result sets'), ] = None context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var brand_id : str | Nonevar buyer_brand : BrandReference | Nonevar context : ContextObject | Nonevar countries : list[Country] | Nonevar ext : ExtensionObject | Nonevar include_excluded : bool | Nonevar model_configvar pagination : PaginationRequest | Nonevar query : strvar right_type : RightType | Nonevar uses : list[RightUse]
Inherited members
class ListProductsRequest (**data: Any)-
Expand source code
class ListProductsRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='forbid', ) idempotency_key: Annotated[ str | None, Field( description='Optional replay key accepted uniformly on read calls.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] = None context_id: Annotated[ str | None, Field( description='MCP compatibility field: servers ignore this value; A2A uses transport-native Message/Task contextId.', min_length=1, ), ] = None context: context_1.ContextObject | None = None governance_context: Annotated[str | None, Field(max_length=4096, min_length=1)] = None push_notification_config: Annotated[ push_notification_config_1.PushNotificationConfig | None, Field( description='Uniform per-call envelope field accepted for SDK compatibility. This does not register a wholesale feed subscription; durable product.* and wholesale_feed.bulk_change subscribers are registered through sync_accounts notification_configs.' ), ] = None account: Annotated[ canonical_account_ref.CanonicalAccountReference | None, Field( description='Account scope for pricing and availability. A natural-key account is the single brand source and MUST NOT be combined with top-level brand.' ), ] = None brand: brand_key.BrandKey | None = None criteria: product_discovery_criteria.ProductDiscoveryCriteria | None = None fields: product_fields.ProductResponseFields | None = None cursor: Annotated[str | None, Field(min_length=1)] = None max_results: Annotated[SchemaInt | None, Field(ge=1, le=100)] = 25 if_feed_version: Annotated[ str | None, Field( description='Opaque feed version returned by a prior list_products response or wholesale product-feed webhook for the same cache scope and canonicalized selection. Used for repair and conditional reconciliation, not routine polling when webhooks are active.' ), ] = None if_pricing_version: Annotated[ str | None, Field( description='Opaque pricing version returned by a prior list_products response. Valid only with if_feed_version.' ), ] = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var account : CanonicalAccountReference1 | CanonicalAccountReference2 | Nonevar brand : BrandKey | Nonevar context : ContextObject | Nonevar context_id : str | Nonevar criteria : ProductDiscoveryCriteria | Nonevar cursor : str | Nonevar fields : ProductResponseFields | Nonevar governance_context : str | Nonevar idempotency_key : str | Nonevar if_feed_version : str | Nonevar if_pricing_version : str | Nonevar max_results : int | Nonevar model_configvar push_notification_config : PushNotificationConfig | None
Inherited members
class PackageRequest (**data: Any)-
Expand source code
class PackageRequest(_LegacyPackageRequest, CanonicalBoundaryModel): """Canonical package request preserving beta.3 selector constraints.""" if TYPE_CHECKING: # the removed field, hidden from the constructor too format_ids: _RemovedFormatIds = Field(default=None, init=False) creatives: list[CreativeAsset] | None = Field(default=None, min_length=1) @model_validator(mode="after") def _validate_format_params(self) -> PackageRequest: if self.params is not None and self.format_kind is None: raise ValueError("params requires format_kind") if self.params is not None and self.format_kind == "image": if ("width" in self.params) != ("height" in self.params): raise ValueError("image params width and height must co-occur") return selfCanonical package request preserving beta.3 selector constraints.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- PackageRequest
- AdcpVersionEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var creatives : list[CreativeAsset] | Nonevar model_configvar targeting_overlay : TargetingOverlayInput | TargetingOverlay | None
Inherited members
class PerformanceFeedback (**data: Any)-
Expand source code
class PerformanceFeedback(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) feedback_id: Annotated[ str, Field(description='Unique identifier for this performance feedback submission') ] media_buy_id: Annotated[str, Field(description="Publisher's media buy identifier")] package_id: Annotated[ str | None, Field( description='Specific package within the media buy (if feedback is package-specific)' ), ] = None creative_id: Annotated[ str | None, Field(description='Specific creative asset (if feedback is creative-specific)') ] = None measurement_period: Annotated[ MeasurementPeriod, Field(description='Time period for performance measurement') ] performance_index: Annotated[ StrictFloat, Field( description='Normalized performance score (0.0 = no value, 1.0 = expected, >1.0 = above expected)', ge=0.0, ), ] metric_type: Annotated[ metric_type_1.MetricType | None, Field( deprecated=True, description='**Deprecated as of this minor.** The legacy free-form metric enum that mixes metrics, verification, and attribution into one list. New implementations SHOULD use `metric` (the discriminated `(scope, metric_id, qualifier)` row shape) and populate `metric_type` with a best-effort string for one-minor backwards compatibility. When both `metric` and `metric_type` are present, consumers MUST use `metric` for dispatch. Removed at the next major. See [docs/measurement/taxonomy](https://docs.adcontextprotocol.org/docs/measurement/taxonomy) for why the layered shape replaces the flat enum.', ), ] = None metric: Annotated[ Metric | Metric7 | None, Field( description='The metric this feedback row pertains to, using the same `(scope, metric_id, qualifier)` row shape as `committed_metrics` and package-level delivery values (`metric_values` or `vendor_metric_values`). Preferred over the legacy `metric_type` field for new implementations. Brings performance-feedback into the same atomic unit and dispatch model as the rest of the measurement surface — buyer agents reconcile feedback against the contract surface using the row-level join on `(scope, metric_id, qualifier)`. **Optional and may be omitted entirely for holistic feedback** (e.g., a trader flagging a campaign as underperforming without a specific metric in mind — `performance_index` plus the response narrative carry the signal). Senders SHOULD populate `metric` when the feedback is metric-specific so consumers can route it to the right optimization path; senders MAY omit it for general performance feedback.', discriminator='scope', ), ] = None feedback_source: Annotated[ feedback_source_1.FeedbackSource, Field(description='Source of the performance data') ] vendor: Annotated[ brand_ref.BrandReference | None, Field( description="Vendor that produced this feedback. SHOULD be populated when `feedback_source` is `third_party_measurement` or `verification_partner` AND a single attesting vendor exists — without it, the row is unattributed and consumers can't verify authorization, resolve metric definitions, or route disputes. OMIT for blended outputs where no single vendor owns the result: MMM mixes (Nielsen MMM, Analytic Partners, in-house mix models combining multiple vendor inputs), multi-touch attribution outputs that join across vendors, and clean-room outputs (LiveRamp, Habu, AWS Clean Rooms) where the clean room is not the measurement source. For these cases, leave `vendor` absent and use the response's narrative payload to describe provenance. Optional for `buyer_attribution` and `platform_analytics` (those sources are implicit from context). The vendor's `brand.json` `agents[type='measurement']` is the discovery anchor; metric definitions live on the agent's `get_adcp_capabilities.measurement.metrics[]` block. Same identity discipline as `vendor_metric_value.vendor` and `performance-standard.vendor`." ), ] = None status: Annotated[Status, Field(description='Processing status of the performance feedback')] submitted_at: Annotated[ AwareDatetime, Field(description='ISO 8601 timestamp when feedback was submitted') ] applied_at: Annotated[ AwareDatetime | None, Field( description='ISO 8601 timestamp when feedback was applied to optimization algorithms' ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var applied_at : pydantic.types.AwareDatetime | Nonevar creative_id : str | Nonevar feedback_id : strvar feedback_source : FeedbackSourcevar measurement_period : MeasurementPeriodvar media_buy_id : strvar metric : Metric | Metric7 | Nonevar metric_type : MetricType | Nonevar model_configvar package_id : str | Nonevar performance_index : floatvar status : Statusvar submitted_at : pydantic.types.AwareDatetimevar vendor : BrandReference | None
Inherited members
class PriceGuidance (**data: Any)-
Expand source code
class PriceGuidance(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) p25: Annotated[ StrictFloat | None, Field(description='25th percentile of recent winning bids', ge=0.0) ] = None p50: Annotated[ StrictFloat | None, Field(description='Median of recent winning bids', ge=0.0) ] = None p75: Annotated[ StrictFloat | None, Field(description='75th percentile of recent winning bids', ge=0.0) ] = None p90: Annotated[ StrictFloat | None, Field(description='90th percentile of recent winning bids', ge=0.0) ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var model_configvar p25 : float | Nonevar p50 : float | Nonevar p75 : float | Nonevar p90 : float | None
Inherited members
class PricingCurrency (value: Any = <object object>, *, root: Any = <object object>)-
Expand source code
class PricingCurrency(ScalarStr): __slots__ = () _constraints = {'pattern': '^[A-Z]{3}$'} _json_schema_extra = {'description': "ISO 4217 currency code (e.g., 'USD', 'EUR', 'GBP')"}A
strgenerated from a JSON Schema string root.Ancestors
- adcp.types._scalar.ScalarStr
- adcp.types._scalar._ScalarRoot
- builtins.str
class PricingModel (*args, **kwds)-
Expand source code
class PricingModel(StrEnum): cpm = 'cpm' vcpm = 'vcpm' cpc = 'cpc' cpcv = 'cpcv' cpv = 'cpv' cpp = 'cpp' cpa = 'cpa' revenue_share = 'revenue_share' flat_rate = 'flat_rate' time = 'time'Enum where members are also (and must be) strings
Ancestors
- enum.StrEnum
- builtins.str
- enum.ReprEnum
- enum.Enum
Class variables
var cpavar cpcvar cpcvvar cpmvar cppvar cpvvar flat_ratevar timevar vcpm
class Product (**data: Any)-
Expand source code
class Product(_LegacyProduct, CanonicalBoundaryModel): """Canonical product; formats, placements and pricing are canonical.""" if TYPE_CHECKING: # the removed field, hidden from the constructor too format_ids: _RemovedFormatIds = Field(default=None, init=False) format_options: list[Format] = Field( # type: ignore[assignment] min_length=1, description="Canonical creative formats accepted by this product." ) placements: list[Placement] | None = Field(default=None, min_length=1) # type: ignore[assignment] pricing_options: list[CanonicalPricingOption] = Field(min_length=1)Canonical product; formats, placements and pricing are canonical.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- Product
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var format_ids : list[FormatReferenceStructuredObject] | Nonevar format_options : list[Format]var model_configvar placements : list[Placement] | Nonevar pricing_options : list[CpmPricingOption | VcpmPricingOption | CpcPricingOption | CpcvPricingOption | CpvPricingOption | CppPricingOption | CpaPricingOption | RevenueSharePricingOption | FlatRatePricingOption | TimeBasedPricingOption]
Instance variables
var data_provider_signals : list[DataProviderSignalSelector1 | DataProviderSignalSelector2 | DataProviderSignalSelector3] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var outcome_measurement : OutcomeMeasurement | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
Inherited members
class ProductCard (**data: Any)-
Expand source code
class ProductCard(AdCPBaseModel): title: Annotated[bound_value.A2UiBoundValue, Field(description='Product name')] price: Annotated[bound_value.A2UiBoundValue, Field(description='Price display string')] image: Annotated[bound_value.A2UiBoundValue | None, Field(description='Product image URL')] = ( None ) description: Annotated[ bound_value.A2UiBoundValue | None, Field(description='Product description') ] = None badge: Annotated[ bound_value.A2UiBoundValue | None, Field(description="Badge text (e.g., 'Best Seller')") ] = None ctaLabel: Annotated[ bound_value.A2UiBoundValue | None, Field(description='CTA button label') ] = None action: Action23 | None = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var action : Action23 | Nonevar badge : A2UiBoundValue1 | A2UiBoundValue2 | A2UiBoundValue3 | A2UiBoundValue4 | A2UiBoundValue5 | Nonevar ctaLabel : A2UiBoundValue1 | A2UiBoundValue2 | A2UiBoundValue3 | A2UiBoundValue4 | A2UiBoundValue5 | Nonevar description : A2UiBoundValue1 | A2UiBoundValue2 | A2UiBoundValue3 | A2UiBoundValue4 | A2UiBoundValue5 | Nonevar image : A2UiBoundValue1 | A2UiBoundValue2 | A2UiBoundValue3 | A2UiBoundValue4 | A2UiBoundValue5 | Nonevar model_configvar price : A2UiBoundValue1 | A2UiBoundValue2 | A2UiBoundValue3 | A2UiBoundValue4 | A2UiBoundValue5var title : A2UiBoundValue1 | A2UiBoundValue2 | A2UiBoundValue3 | A2UiBoundValue4 | A2UiBoundValue5
Inherited members
class ProductCardDetailed (**data: Any)-
Expand source code
class ProductCardDetailed(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) hero_image: Annotated[ image_asset.ImageAsset | None, Field(description='Primary hero image at the top of the detailed view.'), ] = None carousel_images: Annotated[ list[image_asset.ImageAsset] | None, Field(description='Additional images for a swipeable carousel below the hero.'), ] = None title: Annotated[str | None, Field(description='Page title (typically the product name).')] = ( None ) description: Annotated[ str | None, Field( description='Full descriptive copy. Markdown allowed in client renderers that support it; otherwise treat as plain text.' ), ] = None specifications: Annotated[ list[Specification] | None, Field( description="Structured key/value specifications (e.g., 'Aspect ratio: 9:16', 'Duration: 30s'). Each item is a labeled fact about the product." ), ] = None price_label: Annotated[str | None, Field(description='Formatted price or pricing summary.')] = ( None ) cta_label: Annotated[str | None, Field(description='Call-to-action button label.')] = None reference_assets: Annotated[ list[product_card_reference_asset.ProductCardReferenceAsset] | None, Field( description='Typed seller collateral for buyer planning — coverage maps, sample renders, environment photos, media kits. Distinct from hero_image/carousel_images, which are display-oriented.' ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var carousel_images : list[ImageAsset] | Nonevar cta_label : str | Nonevar description : str | Nonevar hero_image : ImageAsset | Nonevar model_configvar price_label : str | Nonevar reference_assets : list[ProductCardReferenceAsset] | Nonevar specifications : list[Specification] | Nonevar title : str | None
Inherited members
class ProductFilters (**data: Any)-
Expand source code
class ProductFilters(_LegacyProductFilters, CanonicalBoundaryModel): """Canonical product filters; legacy identity selection is unavailable.""" if TYPE_CHECKING: # the removed field, hidden from the constructor too format_ids: _RemovedFormatIds = Field(default=None, init=False)Canonical product filters; legacy identity selection is unavailable.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- ProductFilters
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var format_ids : list[FormatReferenceStructuredObject] | Nonevar model_config
Instance variables
var countries : list[Country] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var geo_proximity : list[GeoProximityItem] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var keywords : list[Keyword] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var metros : list[Metro] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var postal_areas : list[PostalArea] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var regions : list[Region] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var required_axe_integrations : list[pydantic.networks.AnyUrl] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var required_geo_targeting : list[RequiredGeoTargetingItem] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
var signal_targeting : list[SignalTargetingItem5 | SignalTargetingItem6 | SignalTargetingItem7] | None-
Expand source code
def __get__(self, obj: BaseModel | None, obj_type: type[BaseModel] | None = None) -> Any: if obj is None: if self.wrapped_property is not None: return self.wrapped_property.__get__(None, obj_type) raise AttributeError(self.field_name) warnings.warn(self.msg, DeprecationWarning, stacklevel=2) if self.wrapped_property is not None: return self.wrapped_property.__get__(obj, obj_type) return obj.__dict__[self.field_name]Read-only data descriptor used to emit a runtime deprecation warning before accessing a deprecated field.
- Attributes
- -----=
msg- The deprecation message to be emitted.
wrapped_property- The property instance if the deprecated field is a computed field, or
None. field_name- The name of the field being deprecated.
Inherited members
class ProvidePerformanceFeedbackRequest (**data: Any)-
Expand source code
class ProvidePerformanceFeedbackRequest(AdcpRequest, AdcpVersionEnvelope, PerformanceFeedbackAssertion): model_config = ConfigDict( extra='allow', ) idempotency_key: Annotated[ str, Field( description='Client-generated unique key for this logical assertion. MUST be unique per receiving agent to prevent cross-agent correlation; use a fresh UUID v4 for each new assertion. Retries use the same key and payload.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- PerformanceFeedbackAssertion
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar ext : ExtensionObject | Nonevar idempotency_key : strvar model_config
class ProvidePerformanceFeedbackByMediaBuyRequest (**data: Any)-
Expand source code
class ProvidePerformanceFeedbackRequest(AdcpRequest, AdcpVersionEnvelope, PerformanceFeedbackAssertion): model_config = ConfigDict( extra='allow', ) idempotency_key: Annotated[ str, Field( description='Client-generated unique key for this logical assertion. MUST be unique per receiving agent to prevent cross-agent correlation; use a fresh UUID v4 for each new assertion. Retries use the same key and payload.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- PerformanceFeedbackAssertion
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar ext : ExtensionObject | Nonevar idempotency_key : strvar model_config
class ProvidePerformanceFeedbackByBuyerRefRequest (**data: Any)-
Expand source code
class ProvidePerformanceFeedbackRequest(AdcpRequest, AdcpVersionEnvelope, PerformanceFeedbackAssertion): model_config = ConfigDict( extra='allow', ) idempotency_key: Annotated[ str, Field( description='Client-generated unique key for this logical assertion. MUST be unique per receiving agent to prevent cross-agent correlation; use a fresh UUID v4 for each new assertion. Retries use the same key and payload.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] context: context_1.ContextObject | None = None ext: ext_1.ExtensionObject | None = NoneThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- PerformanceFeedbackAssertion
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar ext : ExtensionObject | Nonevar idempotency_key : strvar model_config
Inherited members
class RefineProposalsRequest (**data: Any)-
Expand source code
class RefineProposalsRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='forbid', ) context_id: Annotated[ str | None, Field( description='MCP compatibility field: servers ignore this value; A2A uses transport-native Message/Task contextId.', min_length=1, ), ] = None context: context_1.ContextObject | None = None governance_context: Annotated[str | None, Field(max_length=4096, min_length=1)] = None push_notification_config: push_notification_config_1.PushNotificationConfig | None = None idempotency_key: Annotated[ str, Field( description='Client-generated key required for retry-safe proposal refinement.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] refinements: Annotated[ list[proposal_refinement.ProposalRefinement] | Refinements, Field( description='Proposal operations to apply, with at most 25 entries per request. revise creates a draft successor from a draft, committed, or accepted source. finalize MUST target a draft, reserves inventory, and creates a committed successor whose expires_at is the hold deadline. A batch containing finalize MUST contain only finalize entries and is atomic. proposal_id values MUST be unique; results preserve request order.', max_length=25, min_length=1, ), ]The request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var context : ContextObject | Nonevar context_id : str | Nonevar governance_context : str | Nonevar idempotency_key : strvar model_configvar push_notification_config : PushNotificationConfig | Nonevar refinements : list[ProposalRefinement2 | ProposalRefinement3 | ProposalRefinement4 | ProposalRefinement5 | ProposalRefinement6 | ProposalRefinement7 | ProposalRefinement8 | ProposalRefinement9] | Refinements
Inherited members
class RequestProposalsRequest (**data: Any)-
Expand source code
class RequestProposalsRequest(AdcpRequest, AdcpVersionEnvelope): model_config = ConfigDict( extra='forbid', ) context_id: Annotated[ str | None, Field( description='MCP compatibility field: servers ignore this value; A2A uses transport-native Message/Task contextId.', min_length=1, ), ] = None context: context_1.ContextObject | None = None governance_context: Annotated[str | None, Field(max_length=4096, min_length=1)] = None push_notification_config: push_notification_config_1.PushNotificationConfig | None = None idempotency_key: Annotated[ str, Field( description='Client-generated key required for retry-safe proposal creation.', max_length=255, min_length=16, pattern='^[A-Za-z0-9_.:-]{16,255}$', ), ] account: Annotated[ canonical_account_ref.CanonicalAccountReference | None, Field( description='Alternative brand source for proposal terms. Provide either this natural-key account containing brand and operator or top-level brand, not both.' ), ] = None brand: Annotated[ brand_key.BrandKey | None, Field( description='Alternative brand source for proposal terms. Provide either top-level brand or a natural-key account containing brand and operator, not both.' ), ] = None brief: Annotated[ str, Field( description='Campaign goal, strategy, and requirements that are not represented in structured criteria.', min_length=1, ), ] criteria: product_discovery_criteria.ProductDiscoveryCriteria | None = None opportunity: Annotated[ Opportunity | None, Field( description='Optional planning-cycle context that the seller associates with every proposal created by this request.' ), ] = None @model_validator(mode='after') def _require_schema_required_group(self) -> RequestProposalsRequest: # ``required`` asks whether the caller supplied the field, which is what # model_fields_set answers. An explicit null is a supplied value — on a # mutation input it is the command to clear — and a default the caller # never sent is not. for group in (('brand',), ('account',),): if all(name in self.model_fields_set for name in group): return self raise ValueError( 'RequestProposalsRequest requires at least one of these field groups: brand | account' )The request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var account : CanonicalAccountReference1 | CanonicalAccountReference2 | Nonevar brand : BrandKey | Nonevar brief : strvar context : ContextObject | Nonevar context_id : str | Nonevar criteria : ProductDiscoveryCriteria | Nonevar governance_context : str | Nonevar idempotency_key : strvar model_configvar opportunity : Opportunity | Nonevar push_notification_config : PushNotificationConfig | None
Inherited members
class RightsPricingOption (**data: Any)-
Expand source code
class RightsPricingOption(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) pricing_option_id: Annotated[ str, Field( description='Unique identifier for this pricing option. Referenced in acquire_rights and report_usage.' ), ] model: Annotated[ pricing_model.PricingModel, Field(description='Pricing model (cpm, flat_rate, etc.)') ] price: Annotated[ StrictFloat, Field( description='Price amount. Interpretation depends on model: CPM = cost per 1,000 impressions, flat_rate = fixed cost per period.', ge=0.0, ), ] currency: Annotated[str, Field(description='ISO 4217 currency code', pattern='^[A-Z]{3}$')] uses: Annotated[ list[right_use.RightUse], Field( description='Which rights uses this pricing option covers. A single option can bundle multiple uses (e.g., likeness + voice).', min_length=1, ), ] period: Annotated[ rights_billing_period.RightsBillingPeriod | None, Field(description='Billing period for flat_rate and time-based models'), ] = None impression_cap: Annotated[ SchemaInt | None, Field(description='Maximum impressions included in this pricing option per period', ge=1), ] = None overage_cpm: Annotated[ StrictFloat | None, Field(description='CPM rate applied to impressions exceeding the impression_cap', ge=0.0), ] = None description: Annotated[ str | None, Field(description='Human-readable description of this pricing option') ] = None ext: ext_1.ExtensionObject | None = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var currency : strvar description : str | Nonevar ext : ExtensionObject | Nonevar impression_cap : int | Nonevar model : PricingModelvar model_configvar overage_cpm : float | Nonevar period : RightsBillingPeriod | Nonevar price : floatvar pricing_option_id : strvar uses : list[RightUse]
Inherited members
class RightsTerms (**data: Any)-
Expand source code
class RightsTerms(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) pricing_option_id: str amount: Annotated[StrictFloat, Field(ge=0.0)] currency: Annotated[str, Field(pattern='^[A-Z]{3}$')] period: rights_billing_period.RightsBillingPeriod | None = None uses: list[right_use.RightUse] impression_cap: Annotated[SchemaInt | None, Field(ge=1)] = None overage_cpm: Annotated[StrictFloat | None, Field(ge=0.0)] = None start_date: date | None = None end_date: date | None = None exclusivity: Annotated[ Exclusivity | None, Field(description='Exclusivity terms if applicable') ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var amount : floatvar currency : strvar end_date : datetime.date | Nonevar exclusivity : Exclusivity | Nonevar impression_cap : int | Nonevar model_configvar overage_cpm : float | Nonevar period : RightsBillingPeriod | Nonevar pricing_option_id : strvar start_date : datetime.date | Nonevar uses : list[RightUse]
Inherited members
class TargetingOverlay (**data: Any)-
Expand source code
class TargetingOverlay(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) geo_countries: Annotated[ list[GeoCountry] | None, Field( description="Restrict delivery to specific countries. ISO 3166-1 alpha-2 codes (e.g., 'US', 'GB', 'DE').", min_length=1, ), ] = None geo_countries_exclude: Annotated[ Sequence[GeoCountriesExcludeItem] | None, Field( description="Exclude specific countries from delivery. ISO 3166-1 alpha-2 codes (e.g., 'US', 'GB', 'DE').", min_length=1, ), ] = None geo_regions: Annotated[ list[GeoRegion] | None, Field( description='Restrict delivery to exact canonical ISO 3166-2 subdivisions (states, provinces, regions, departments, or other subdivision categories). Unknown identifiers are invalid. At create or update, sellers MUST reject unsupported identifiers and MUST NOT silently widen, drop, or partially apply the list. During get_products, a seller may instead return a sparse, buyer-reviewable targeting_resolution modification for a valid but unsupported requested outcome. Exact internal translation preserves accepted identifiers in package readback.', min_length=1, ), ] = None geo_regions_exclude: Annotated[ Sequence[GeoRegionsExcludeItem] | None, Field( description='Exclude exact canonical ISO 3166-2 subdivisions. Support is independent from geo_regions inclusion support. Unknown identifiers and values also present in geo_regions are invalid. At create or update, sellers MUST reject unsupported identifiers and partial application; during get_products, a seller may instead return a sparse, buyer-reviewable targeting_resolution modification for a valid but unsupported requested outcome.', min_length=1, ), ] = None geo_metros: Annotated[ list[geo_metro.GeoMetro] | None, Field( description='Restrict delivery to specific metro areas. Each entry specifies the classification system and target values. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, title='Targeting Geo Metros', ), ] = None geo_metros_exclude: Annotated[ Sequence[GeoMetrosExcludeItem] | None, Field( description='Exclude specific metro areas from delivery. Each entry specifies the classification system and excluded values. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, ), ] = None geo_postal_areas: Annotated[ list[postal_area.PostalArea] | None, Field( description='Restrict delivery to specific postal areas. Prefer the native country + postal system form. The deprecated legacy country-fused postal-system tokens remain accepted for compatibility. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, ), ] = None geo_postal_areas_exclude: Annotated[ Sequence[postal_area.PostalArea] | None, Field( description='Exclude specific postal areas from delivery. Prefer the native country + postal system form. The deprecated legacy country-fused postal-system tokens remain accepted for compatibility. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, ), ] = None geo_places: Annotated[ list[geo_place_area.GeographicPlaceArea] | None, Field( description='Restrict delivery to catalog-backed named places. Values MUST be stable identifiers in the declared system, not display names. Sellers must declare supported systems, countries, and place types in get_adcp_capabilities and reject unsupported entries rather than silently dropping them.', min_length=1, ), ] = None geo_places_exclude: Annotated[ list[geo_place_area.GeographicPlaceArea] | None, Field( description='Exclude catalog-backed named places. Uses the same identifier-based shape as geo_places. Sellers MUST reject overlap with geo_places for the same country, system, place_type, and value.', min_length=1, ), ] = None daypart_targets: Annotated[ list[daypart_target.DaypartTarget] | None, Field( description='Restrict delivery to specific time windows. Each entry specifies days of week, an hour range, and an optional timezone that defaults to inventory_local. A concrete IANA zone uses one shared civil-time clock, while inventory_local evaluates each inventory unit in its seller-assigned local timezone. Entries are independent and MAY use different clocks.', min_length=1, ), ] = None axe_include_segment: Annotated[ str | None, Field( deprecated=True, description='Deprecated: Use TMP provider fields instead. AXE segment ID to include for targeting.', ), ] = None axe_exclude_segment: Annotated[ str | None, Field( deprecated=True, description='Deprecated: Use TMP provider fields instead. AXE segment ID to exclude from targeting.', ), ] = None audience_include: Annotated[ list[str] | None, Field( description='Restrict delivery to members of these first-party CRM audiences. Only users present in the uploaded lists are eligible. References audience_id values from sync_audiences on the same seller account — audience IDs are not portable across sellers. Not for lookalike expansion — express that intent in the campaign brief. Seller must declare support in get_adcp_capabilities.', min_length=1, ), ] = None audience_exclude: Annotated[ list[str] | None, Field( description='Suppress delivery to members of these first-party CRM audiences. Matched users are excluded regardless of other targeting. References audience_id values from sync_audiences on the same seller account — audience IDs are not portable across sellers. Seller must declare support in get_adcp_capabilities.', min_length=1, ), ] = None signal_targeting_groups: Annotated[ package_signal_targeting_groups.PackageSignalTargetingGroups | None, Field( description="Basic Boolean grouping for seller-offered signals. v1 supports a required top-level operator 'all' and child groups with operator 'any' for include groups or 'none' for exclusion groups. Example semantics: group 1 any(A, B) plus group 2 none(C, D) means (A OR B) AND NOT (C OR D). Signal entries reference named signal definitions with signal_ref scope 'product' for product-local signal options or scope 'data_provider' for external signals published in adagents.json signals[]. For simple include-only targeting, send one child group with operator 'any'. Sellers SHOULD reject entries that are not available for the product through inline signal_targeting_options or get_signals, are not active for the account, or exceed the product's signal_targeting_allowed/signal_targeting_rules/product terms. Signal targeting limits are product-scoped, not declared in get_adcp_capabilities, because products may be backed by different ad servers. Sellers MUST echo applied signal_targeting_groups on the resulting package state, including fixed/default selections. Sellers MAY return REQUOTE_REQUIRED when a targeting mutation changes commercial terms.", title='Targeting Signal Groups', ), ] = None signal_targeting: Annotated[ list[signal_targeting_1.SignalTargeting] | None, Field( deprecated=True, description='DEPRECATED. Use signal_targeting_groups for package-level signal targeting. Legacy flat signal_targeting remains accepted during the SignalRef migration window but cannot express grouped include/exclude composition or product-scoped pricing.', min_length=1, ), ] = None demographics: Annotated[ demographic_targeting_intent.DemographicTargetingIntent | None, Field( description='Canonical demographic audience targeting intent with optional constraints on how age may be determined. This is distinct from age_restriction: demographics selects an audience, while age_restriction expresses a legal eligibility or verification floor. Fresh create/update targeting MUST compile exactly or be rejected. During get_products, a seller may offer a different configured predicate only through sparse targeting_resolution modifications on a distinguishable product_id; selecting that product accepts the alternative. Sellers never silently broaden, narrow, default, drop, or substitute the basis.' ), ] = None frequency_cap: Annotated[ frequency_cap_1.FrequencyCap | None, Field(title='Targeting Frequency Cap') ] = None property_list: Annotated[ property_list_ref.PropertyListReference | None, Field( description="Reference to a property list for targeting specific properties within this product. The package runs on the intersection of the product's publisher_properties and this list. Sellers SHOULD return a validation error if the product has property_targeting_allowed: false.", title='Targeting Property List', ), ] = None property_list_exclude: Annotated[ property_list_ref.PropertyListReference | None, Field( description="Reference to a property list whose properties must not carry the buyer's ads. Matched properties are removed from delivery. Use for brand-safety do-not-run lists (apps, sites). Exclude wins on overlap with property_list, and applies regardless of the product's property_targeting_allowed flag. Seller must declare support in get_adcp_capabilities." ), ] = None collection_list: Annotated[ collection_list_ref.CollectionListReference | None, Field( description='Reference to a collection list for including specific collections (programs, publications, channels) within this product. The package runs on the intersection of matched collections and this list. Use for inclusion-based collection targeting. Seller must declare support in get_adcp_capabilities.', title='Targeting Collection List', ), ] = None collection_list_exclude: Annotated[ collection_list_ref.CollectionListReference | None, Field( description="Reference to a collection list for excluding specific collections (programs, publications, channels) from this product. Matched collections must not carry the buyer's ads. Use for brand safety do-not-air lists. Seller must declare support in get_adcp_capabilities." ), ] = None placement_selection: Annotated[ placement_selection_1.PlacementSelection | None, Field( description='Purchased placement selection within the product. This constrains package inventory; it is distinct from creative_assignments[].placement_refs, which only route individual creatives within the purchased set. On create, mode selected supplies the complete selected set and mode default uses the product default. In request-side Targeting Input, a non-null value replaces this dimension, omission preserves or inherits it, and null clears it when the product permits that broader inventory set.' ), ] = None collection_selection: Annotated[ collection_selection_1.CollectionSelection | None, Field( description="Purchased collection selection within the product. On create, mode selected supplies the complete selected set and mode default uses the product's full bundle. On package readback this is the committed selection sellers MUST echo as concrete selectors, materializing any collection_list composition; collection_list fields remain the buyer-managed list mechanism. In request-side Targeting Input, a non-null value replaces this dimension, omission preserves or inherits it, and null clears it when the product permits that broader inventory set.", title='Targeting Collection Selection', ), ] = None age_restriction: Annotated[ AgeRestriction | None, Field( description='Age restriction for compliance. Use for legal requirements (alcohol, gambling), not audience targeting.' ), ] = None device_platform: Annotated[ list[device_platform_1.DevicePlatform] | None, Field( description='Restrict to specific platforms. Use for technical compatibility (app only works on iOS). Values from Sec-CH-UA-Platform standard, extended for CTV.', min_length=1, ), ] = None device_platform_exclude: Annotated[ list[device_platform_1.DevicePlatform] | None, Field( description='Exclude specific operating-system platforms from delivery. When a platform appears in both device_platform and device_platform_exclude, exclusion wins. Sellers MUST reject a request they cannot enforce rather than silently dropping the exclusion.', min_length=1, ), ] = None device_type: Annotated[ list[device_type_1.DeviceType] | None, Field( description='Restrict to specific device form factors. Use for campaigns targeting hardware categories rather than operating systems (e.g., mobile-only promotions, CTV campaigns).', min_length=1, ), ] = None device_type_exclude: Annotated[ list[device_type_1.DeviceType] | None, Field( description='Exclude specific device form factors from delivery (e.g., exclude CTV for app-install campaigns).', min_length=1, ), ] = None browser: Annotated[ list[browser_family.BrowserFamily] | None, Field( description='Restrict delivery to specific canonical browser families in the impression delivery and rendering environment, not the post-click landing-page browser. Values MUST NOT be inferred solely from operating system, device, web/mobile-web inventory, or placement. Values in this array use OR semantics. When browser is supplied, families not listed are ineligible: other includes a seller-recognized family that is not explicitly enumerated, while unknown includes a browser the seller cannot classify into a recognized family. When the same family appears in browser and browser_exclude, exclusion wins. Browser and device constraints intersect; a seller that cannot enforce the exact combination MUST exclude or explicitly reconfigure the product during discovery and MUST reject it at create or update rather than silently widening delivery. Browser versions and seller-native IDs are intentionally unsupported.', min_length=1, ), ] = None browser_exclude: Annotated[ list[browser_family.BrowserFamily] | None, Field( description='Exclude specific canonical browser families from delivery. other excludes seller-recognized families that are not explicitly enumerated; unknown excludes browsers the seller cannot classify into a recognized family. When the same family appears in browser and browser_exclude, exclusion wins. Sellers MUST reject a request they cannot enforce rather than silently dropping the exclusion.', min_length=1, ), ] = None store_catchments: Annotated[ list[StoreCatchment] | None, Field( description='Target users within store catchment areas from a synced store catalog. Each entry references a store-type catalog and optionally narrows to specific stores or catchment zones.', min_length=1, ), ] = None geo_proximity: Annotated[ list[GeoProximityItem] | None, Field( description='Target users within travel time, distance, or a custom boundary around arbitrary geographic points. Multiple entries use OR semantics — a user within range of any listed point is eligible. For campaigns targeting 10+ locations, consider using store_catchments with a location catalog instead. Seller must declare support in get_adcp_capabilities.', min_length=1, ), ] = None language: Annotated[ list[locale_tag.LanguageTag] | None, Field( description="Restrict to users with specific language preferences using canonical BCP 47 language ranges. Each buyer range is evaluated against a user's language-preference tag with RFC 4647 section 3.3.1 Basic Filtering: 'fr' matches 'fr', 'fr-CA', and 'fr-FR', while 'fr-CA' matches 'fr-CA' and more-specific descendants but not 'fr' or 'fr-FR'. Values use OR logic.", min_length=1, title='Targeting Languages', ), ] = None keyword_targets: Annotated[ list[KeywordTarget] | None, Field( description='Keyword targeting for search and retail media platforms. Restricts delivery to queries matching the specified keywords. Each keyword is identified by the tuple (keyword, match_type) — the same keyword string with different match types are distinct targets. Sellers SHOULD reject duplicate (keyword, match_type) pairs within a single request. Seller must declare support in get_adcp_capabilities.', min_length=1, title='Targeting Keywords', ), ] = None negative_keywords: Annotated[ list[negative_keyword.NegativeKeyword] | None, Field( description='Keywords to exclude from delivery. Queries matching these keywords will not trigger the ad. Each negative keyword is identified by the tuple (keyword, match_type). Seller must declare support in get_adcp_capabilities.', min_length=1, title='Targeting Negative Keywords', ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var age_restriction : AgeRestriction | Nonevar audience_exclude : list[str] | Nonevar audience_include : list[str] | Nonevar axe_exclude_segment : str | Nonevar axe_include_segment : str | Nonevar browser : list[BrowserFamily] | Nonevar browser_exclude : list[BrowserFamily] | Nonevar collection_list : CollectionListReference | Nonevar collection_list_exclude : CollectionListReference | Nonevar collection_selection : CollectionSelection1 | CollectionSelection2 | Nonevar daypart_targets : list[DaypartTarget] | Nonevar demographics : DemographicTargetingIntent | Nonevar device_platform : list[DevicePlatform] | Nonevar device_platform_exclude : list[DevicePlatform] | Nonevar device_type : list[DeviceType] | Nonevar device_type_exclude : list[DeviceType] | Nonevar frequency_cap : FrequencyCap | Nonevar geo_countries : list[GeoCountry] | Nonevar geo_countries_exclude : collections.abc.Sequence[GeoCountriesExcludeItem] | Nonevar geo_metros : list[GeoMetro] | Nonevar geo_metros_exclude : collections.abc.Sequence[GeoMetrosExcludeItem] | Nonevar geo_places : list[GeographicPlaceArea] | Nonevar geo_places_exclude : list[GeographicPlaceArea] | Nonevar geo_postal_areas : list[PostalArea] | Nonevar geo_postal_areas_exclude : collections.abc.Sequence[PostalArea] | Nonevar geo_proximity : list[GeoProximityItem] | Nonevar geo_regions : list[GeoRegion] | Nonevar geo_regions_exclude : collections.abc.Sequence[GeoRegionsExcludeItem] | Nonevar keyword_targets : list[KeywordTarget] | Nonevar language : list[LanguageTag] | Nonevar model_configvar negative_keywords : list[NegativeKeyword] | Nonevar placement_selection : PlacementSelection1 | PlacementSelection2 | Nonevar property_list : PropertyListReference | Nonevar property_list_exclude : PropertyListReference | Nonevar signal_targeting : list[SignalTargeting1 | SignalTargeting2 | SignalTargeting3] | Nonevar signal_targeting_groups : PackageSignalTargetingGroups | Nonevar store_catchments : list[StoreCatchment] | None
Inherited members
class TargetingOverlayInput (**data: Any)-
Expand source code
class TargetingOverlayInput(AdCPBaseModel): model_config = ConfigDict( extra='allow', ) geo_countries: Annotated[ list[GeoCountry] | None, Field( description="Restrict delivery to specific countries. ISO 3166-1 alpha-2 codes (e.g., 'US', 'GB', 'DE').", min_length=1, ), ] = None geo_countries_exclude: Annotated[ list[GeoCountriesExcludeItem] | None, Field( description="Exclude specific countries from delivery. ISO 3166-1 alpha-2 codes (e.g., 'US', 'GB', 'DE').", min_length=1, ), ] = None geo_regions: Annotated[ list[GeoRegion] | None, Field( description='Restrict delivery to exact canonical ISO 3166-2 subdivisions (states, provinces, regions, departments, or other subdivision categories). Unknown identifiers are invalid. At create or update, sellers MUST reject unsupported identifiers and MUST NOT silently widen, drop, or partially apply the list. During get_products, a seller may instead return a sparse, buyer-reviewable targeting_resolution modification for a valid but unsupported requested outcome. Exact internal translation preserves accepted identifiers in package readback.', min_length=1, ), ] = None geo_regions_exclude: Annotated[ list[GeoRegionsExcludeItem] | None, Field( description='Exclude exact canonical ISO 3166-2 subdivisions. Support is independent from geo_regions inclusion support. Unknown identifiers and values also present in geo_regions are invalid. At create or update, sellers MUST reject unsupported identifiers and partial application; during get_products, a seller may instead return a sparse, buyer-reviewable targeting_resolution modification for a valid but unsupported requested outcome.', min_length=1, ), ] = None geo_metros: Annotated[ list[geo_metro.GeoMetro] | None, Field( description='Restrict delivery to specific metro areas. Each entry specifies the classification system and target values. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, title='Targeting Geo Metros', ), ] = None geo_metros_exclude: Annotated[ list[GeoMetrosExcludeItem] | None, Field( description='Exclude specific metro areas from delivery. Each entry specifies the classification system and excluded values. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, ), ] = None geo_postal_areas: Annotated[ list[postal_area.PostalArea] | None, Field( description='Restrict delivery to specific postal areas. Prefer the native country + postal system form. The deprecated legacy country-fused postal-system tokens remain accepted for compatibility. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, ), ] = None geo_postal_areas_exclude: Annotated[ list[postal_area.PostalArea] | None, Field( description='Exclude specific postal areas from delivery. Prefer the native country + postal system form. The deprecated legacy country-fused postal-system tokens remain accepted for compatibility. Seller must declare supported systems in get_adcp_capabilities.', min_length=1, ), ] = None geo_places: Annotated[ list[geo_place_area.GeographicPlaceArea] | None, Field( description='Restrict delivery to catalog-backed named places. Values MUST be stable identifiers in the declared system, not display names. Sellers must declare supported systems, countries, and place types in get_adcp_capabilities and reject unsupported entries rather than silently dropping them.', min_length=1, ), ] = None geo_places_exclude: Annotated[ list[geo_place_area.GeographicPlaceArea] | None, Field( description='Exclude catalog-backed named places. Uses the same identifier-based shape as geo_places. Sellers MUST reject overlap with geo_places for the same country, system, place_type, and value.', min_length=1, ), ] = None daypart_targets: Annotated[ list[daypart_target.DaypartTarget] | None, Field( description='Restrict delivery to specific time windows. Each entry specifies days of week, an hour range, and an optional timezone that defaults to inventory_local. A concrete IANA zone uses one shared civil-time clock, while inventory_local evaluates each inventory unit in its seller-assigned local timezone. Entries are independent and MAY use different clocks.', min_length=1, ), ] = None axe_include_segment: Annotated[ str | None, Field( deprecated=True, description='Deprecated: Use TMP provider fields instead. AXE segment ID to include for targeting.', ), ] = None axe_exclude_segment: Annotated[ str | None, Field( deprecated=True, description='Deprecated: Use TMP provider fields instead. AXE segment ID to exclude from targeting.', ), ] = None audience_include: Annotated[ list[str] | None, Field( description='Restrict delivery to members of these first-party CRM audiences. Only users present in the uploaded lists are eligible. References audience_id values from sync_audiences on the same seller account — audience IDs are not portable across sellers. Not for lookalike expansion — express that intent in the campaign brief. Seller must declare support in get_adcp_capabilities.', min_length=1, ), ] = None audience_exclude: Annotated[ list[str] | None, Field( description='Suppress delivery to members of these first-party CRM audiences. Matched users are excluded regardless of other targeting. References audience_id values from sync_audiences on the same seller account — audience IDs are not portable across sellers. Seller must declare support in get_adcp_capabilities.', min_length=1, ), ] = None signal_targeting_groups: package_signal_targeting_groups.PackageSignalTargetingGroups | None = ( None ) signal_targeting: Annotated[ list[signal_targeting_1.SignalTargeting] | None, Field( deprecated=True, description='DEPRECATED. Use signal_targeting_groups for package-level signal targeting. Legacy flat signal_targeting remains accepted during the SignalRef migration window but cannot express grouped include/exclude composition or product-scoped pricing.', min_length=1, ), ] = None demographics: demographic_targeting_intent.DemographicTargetingIntent | None = None frequency_cap: frequency_cap_1.FrequencyCap | None = None property_list: property_list_ref.PropertyListReference | None = None property_list_exclude: property_list_ref.PropertyListReference | None = None collection_list: collection_list_ref.CollectionListReference | None = None collection_list_exclude: collection_list_ref.CollectionListReference | None = None placement_selection: placement_selection_1.PlacementSelection | None = None collection_selection: collection_selection_1.CollectionSelection | None = None age_restriction: targeting.AgeRestriction | None = None device_platform: Annotated[ list[device_platform_1.DevicePlatform] | None, Field( description='Restrict to specific platforms. Use for technical compatibility (app only works on iOS). Values from Sec-CH-UA-Platform standard, extended for CTV.', min_length=1, ), ] = None device_platform_exclude: Annotated[ list[device_platform_1.DevicePlatform] | None, Field( description='Exclude specific operating-system platforms from delivery. When a platform appears in both device_platform and device_platform_exclude, exclusion wins. Sellers MUST reject a request they cannot enforce rather than silently dropping the exclusion.', min_length=1, ), ] = None device_type: Annotated[ list[device_type_1.DeviceType] | None, Field( description='Restrict to specific device form factors. Use for campaigns targeting hardware categories rather than operating systems (e.g., mobile-only promotions, CTV campaigns).', min_length=1, ), ] = None device_type_exclude: Annotated[ list[device_type_1.DeviceType] | None, Field( description='Exclude specific device form factors from delivery (e.g., exclude CTV for app-install campaigns).', min_length=1, ), ] = None browser: Annotated[ list[browser_family.BrowserFamily] | None, Field( description='Restrict delivery to specific canonical browser families in the impression delivery and rendering environment, not the post-click landing-page browser. Values MUST NOT be inferred solely from operating system, device, web/mobile-web inventory, or placement. Values in this array use OR semantics. When browser is supplied, families not listed are ineligible: other includes a seller-recognized family that is not explicitly enumerated, while unknown includes a browser the seller cannot classify into a recognized family. When the same family appears in browser and browser_exclude, exclusion wins. Browser and device constraints intersect; a seller that cannot enforce the exact combination MUST exclude or explicitly reconfigure the product during discovery and MUST reject it at create or update rather than silently widening delivery. Browser versions and seller-native IDs are intentionally unsupported.', min_length=1, ), ] = None browser_exclude: Annotated[ list[browser_family.BrowserFamily] | None, Field( description='Exclude specific canonical browser families from delivery. other excludes seller-recognized families that are not explicitly enumerated; unknown excludes browsers the seller cannot classify into a recognized family. When the same family appears in browser and browser_exclude, exclusion wins. Sellers MUST reject a request they cannot enforce rather than silently dropping the exclusion.', min_length=1, ), ] = None store_catchments: Annotated[ list[StoreCatchment] | None, Field( description='Target users within store catchment areas from a synced store catalog. Each entry references a store-type catalog and optionally narrows to specific stores or catchment zones.', min_length=1, ), ] = None geo_proximity: Annotated[ list[GeoProximityItem] | None, Field( description='Target users within travel time, distance, or a custom boundary around arbitrary geographic points. Multiple entries use OR semantics — a user within range of any listed point is eligible. For campaigns targeting 10+ locations, consider using store_catchments with a location catalog instead. Seller must declare support in get_adcp_capabilities.', min_length=1, ), ] = None language: Annotated[ list[locale_tag.LanguageTag] | None, Field( description="Restrict to users with specific language preferences using canonical BCP 47 language ranges. Each buyer range is evaluated against a user's language-preference tag with RFC 4647 section 3.3.1 Basic Filtering: 'fr' matches 'fr', 'fr-CA', and 'fr-FR', while 'fr-CA' matches 'fr-CA' and more-specific descendants but not 'fr' or 'fr-FR'. Values use OR logic.", min_length=1, title='Targeting Languages', ), ] = None keyword_targets: Annotated[ list[KeywordTarget] | None, Field( description='Keyword targeting for search and retail media platforms. Restricts delivery to queries matching the specified keywords. Each keyword is identified by the tuple (keyword, match_type) — the same keyword string with different match types are distinct targets. Sellers SHOULD reject duplicate (keyword, match_type) pairs within a single request. Seller must declare support in get_adcp_capabilities.', min_length=1, title='Targeting Keywords', ), ] = None negative_keywords: Annotated[ list[negative_keyword.NegativeKeyword] | None, Field( description='Keywords to exclude from delivery. Queries matching these keywords will not trigger the ad. Each negative keyword is identified by the tuple (keyword, match_type). Seller must declare support in get_adcp_capabilities.', min_length=1, title='Targeting Negative Keywords', ), ] = NoneBase model for AdCP types with spec-compliant serialization.
Defaults to
extra='ignore'so unknown fields from newer spec versions are silently dropped rather than causing validation errors. Generated types whose schemas setadditionalProperties: trueoverride this withextra='allow'in their ownmodel_config.Set
ADCP_STRICT_VALIDATION=1in the environment ("1","true","yes","on"are accepted) to flip the default toextra='forbid'. Use this during spec upgrades to catch silently-dropped renamed fields in tests. See :func:_resolve_extra_policy.Important
The env var is resolved once at module import time. Set it in your shell or CI environment before
import adcpruns — mutatingos.environ["ADCP_STRICT_VALIDATION"]after the firstadcpimport has no effect on already-imported model classes (they captured the policy at class-body evaluation).Consumers who want per-model strict validation can override
model_configon their subclass.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var age_restriction : AgeRestriction | Nonevar audience_exclude : list[str] | Nonevar audience_include : list[str] | Nonevar axe_exclude_segment : str | Nonevar axe_include_segment : str | Nonevar browser : list[BrowserFamily] | Nonevar browser_exclude : list[BrowserFamily] | Nonevar collection_list : CollectionListReference | Nonevar collection_list_exclude : CollectionListReference | Nonevar collection_selection : CollectionSelection1 | CollectionSelection2 | Nonevar daypart_targets : list[DaypartTarget] | Nonevar demographics : DemographicTargetingIntent | Nonevar device_platform : list[DevicePlatform] | Nonevar device_platform_exclude : list[DevicePlatform] | Nonevar device_type : list[DeviceType] | Nonevar device_type_exclude : list[DeviceType] | Nonevar frequency_cap : FrequencyCap | Nonevar geo_countries : list[GeoCountry] | Nonevar geo_countries_exclude : list[GeoCountriesExcludeItem] | Nonevar geo_metros : list[GeoMetro] | Nonevar geo_metros_exclude : list[GeoMetrosExcludeItem] | Nonevar geo_places : list[GeographicPlaceArea] | Nonevar geo_places_exclude : list[GeographicPlaceArea] | Nonevar geo_postal_areas : list[PostalArea] | Nonevar geo_postal_areas_exclude : list[PostalArea] | Nonevar geo_proximity : list[GeoProximityItem] | Nonevar geo_regions : list[GeoRegion] | Nonevar geo_regions_exclude : list[GeoRegionsExcludeItem] | Nonevar keyword_targets : list[KeywordTarget] | Nonevar language : list[LanguageTag] | Nonevar model_configvar negative_keywords : list[NegativeKeyword] | Nonevar placement_selection : PlacementSelection1 | PlacementSelection2 | Nonevar property_list : PropertyListReference | Nonevar property_list_exclude : PropertyListReference | Nonevar signal_targeting : list[SignalTargeting1 | SignalTargeting2 | SignalTargeting3] | Nonevar signal_targeting_groups : PackageSignalTargetingGroups | Nonevar store_catchments : list[StoreCatchment] | None
Inherited members
class UpdateMediaBuyRequest (**data: Any)-
Expand source code
class UpdateMediaBuyRequest(_LegacyUpdateMediaBuyRequest, CanonicalBoundaryModel): """Canonical update request; both package lists are canonical.""" packages: list[PackageUpdate] | None = None new_packages: list[PackageRequest] | None = Field( # type: ignore[assignment] default=None, min_length=1 )Canonical update request; both package lists are canonical.
Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- UpdateMediaBuyRequest
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- CanonicalBoundaryModel
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var model_configvar new_packages : list[PackageRequest] | Nonevar packages : list[PackageUpdate] | None
Inherited members
class VerifyBrandClaimsRequest (**data: Any)-
Expand source code
class VerifyBrandClaimsRequest(VerifyBrandClaimsRequestBulk): passThe request message of a task in the pinned bundle's task registry.
A consumer holding one can resolve its account, decide at-most-once, echo its context and negotiate version – the whole transport-boundary job – before knowing which tool it is.
issubclass(model, AdcpRequest)is the registration-time proof that a model is spec-derived rather than a hand-written parallel: a field test passes for a forged model, descent does not.Each accessor returns the field's value, or
Nonewhen this tool's schema declares no such field. Only 49 of the 87 request schemas declare anaccountand only 43 anidempotency_key, so asking the request is what replacesgetattr(req, "account", None)againstAnyat the boundary.Create a new model by parsing and validating input data from keyword arguments.
Raises [
ValidationError][pydantic_core.ValidationError] if the input data cannot be validated to form a valid model.selfis explicitly positional-only to allowselfas a field name.Ancestors
- VerifyBrandClaimsRequestBulk
- AdcpRequest
- adcp.types.base._AdcpMessage
- AdcpVersionEnvelope
- AdCPBaseModel
- pydantic.main.BaseModel
Class variables
var model_config
Inherited members