@adcp/sdk 12.0.0 → 12.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/lib/adapters/content-standards-adapter.mjs +0 -6
- package/dist/lib/adapters/content-standards-adapter.mjs.map +1 -1
- package/dist/lib/adapters/derived-account-store.mjs +0 -6
- package/dist/lib/adapters/derived-account-store.mjs.map +1 -1
- package/dist/lib/adapters/governance-adapter.mjs +0 -6
- package/dist/lib/adapters/governance-adapter.mjs.map +1 -1
- package/dist/lib/adapters/implicit-account-store.mjs +0 -6
- package/dist/lib/adapters/implicit-account-store.mjs.map +1 -1
- package/dist/lib/adapters/index.mjs +0 -6
- package/dist/lib/adapters/index.mjs.map +1 -1
- package/dist/lib/adapters/legacy/v2-5/create_media_buy.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/create_media_buy.mjs.map +1 -1
- package/dist/lib/adapters/legacy/v2-5/get_products.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/get_products.mjs.map +1 -1
- package/dist/lib/adapters/legacy/v2-5/index.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/index.mjs.map +1 -1
- package/dist/lib/adapters/legacy/v2-5/list_creative_formats.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/list_creative_formats.mjs.map +1 -1
- package/dist/lib/adapters/legacy/v2-5/preview_creative.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/preview_creative.mjs.map +1 -1
- package/dist/lib/adapters/legacy/v2-5/sync_creatives.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/sync_creatives.mjs.map +1 -1
- package/dist/lib/adapters/legacy/v2-5/types.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/update_media_buy.mjs +0 -6
- package/dist/lib/adapters/legacy/v2-5/update_media_buy.mjs.map +1 -1
- package/dist/lib/adapters/oauth-passthrough-resolver.mjs +0 -6
- package/dist/lib/adapters/oauth-passthrough-resolver.mjs.map +1 -1
- package/dist/lib/adapters/property-list-adapter.mjs +0 -6
- package/dist/lib/adapters/property-list-adapter.mjs.map +1 -1
- package/dist/lib/adapters/roster-account-store.mjs +0 -6
- package/dist/lib/adapters/roster-account-store.mjs.map +1 -1
- package/dist/lib/adapters/si-session-manager.mjs +0 -6
- package/dist/lib/adapters/si-session-manager.mjs.map +1 -1
- package/dist/lib/adapters/version/3.0/brand-fields.mjs +0 -6
- package/dist/lib/adapters/version/3.0/brand-fields.mjs.map +1 -1
- package/dist/lib/adapters/version/3.0/get-products.mjs +0 -6
- package/dist/lib/adapters/version/3.0/get-products.mjs.map +1 -1
- package/dist/lib/adapters/version/3.0/index.mjs +0 -6
- package/dist/lib/adapters/version/3.0/index.mjs.map +1 -1
- package/dist/lib/adapters/version/3.0/sync-accounts.mjs +0 -6
- package/dist/lib/adapters/version/3.0/sync-accounts.mjs.map +1 -1
- package/dist/lib/adapters/version/index.mjs +0 -6
- package/dist/lib/adapters/version/index.mjs.map +1 -1
- package/dist/lib/adapters/version/types.mjs +0 -6
- package/dist/lib/advanced.mjs +0 -6
- package/dist/lib/advanced.mjs.map +1 -1
- package/dist/lib/agents/index.generated.mjs +0 -6
- package/dist/lib/agents/index.generated.mjs.map +1 -1
- package/dist/lib/auth/index.mjs +0 -6
- package/dist/lib/auth/index.mjs.map +1 -1
- package/dist/lib/auth/oauth/CLIFlowHandler.mjs +0 -6
- package/dist/lib/auth/oauth/CLIFlowHandler.mjs.map +1 -1
- package/dist/lib/auth/oauth/ClientCredentialsFlow.mjs +0 -6
- package/dist/lib/auth/oauth/ClientCredentialsFlow.mjs.map +1 -1
- package/dist/lib/auth/oauth/MCPOAuthProvider.mjs +0 -6
- package/dist/lib/auth/oauth/MCPOAuthProvider.mjs.map +1 -1
- package/dist/lib/auth/oauth/NonInteractiveFlowHandler.mjs +0 -6
- package/dist/lib/auth/oauth/NonInteractiveFlowHandler.mjs.map +1 -1
- package/dist/lib/auth/oauth/authorization-required.mjs +0 -6
- package/dist/lib/auth/oauth/authorization-required.mjs.map +1 -1
- package/dist/lib/auth/oauth/diagnose.mjs +0 -6
- package/dist/lib/auth/oauth/diagnose.mjs.map +1 -1
- package/dist/lib/auth/oauth/diagnostics.mjs +0 -6
- package/dist/lib/auth/oauth/diagnostics.mjs.map +1 -1
- package/dist/lib/auth/oauth/discovery.mjs +0 -6
- package/dist/lib/auth/oauth/discovery.mjs.map +1 -1
- package/dist/lib/auth/oauth/file-storage.mjs +0 -6
- package/dist/lib/auth/oauth/file-storage.mjs.map +1 -1
- package/dist/lib/auth/oauth/index.mjs +0 -6
- package/dist/lib/auth/oauth/index.mjs.map +1 -1
- package/dist/lib/auth/oauth/secret-resolver.mjs +0 -6
- package/dist/lib/auth/oauth/secret-resolver.mjs.map +1 -1
- package/dist/lib/auth/oauth/storage-registry.mjs +0 -6
- package/dist/lib/auth/oauth/storage-registry.mjs.map +1 -1
- package/dist/lib/auth/oauth/types.mjs +0 -6
- package/dist/lib/auth/oauth/types.mjs.map +1 -1
- package/dist/lib/auth/oauth/web-flow.mjs +0 -6
- package/dist/lib/auth/oauth/web-flow.mjs.map +1 -1
- package/dist/lib/brand/index.mjs +0 -6
- package/dist/lib/brand/index.mjs.map +1 -1
- package/dist/lib/canonical-references/index.mjs +6 -7
- package/dist/lib/canonical-references/index.mjs.map +1 -1
- package/dist/lib/client/index.mjs +0 -6
- package/dist/lib/client/index.mjs.map +1 -1
- package/dist/lib/compliance/index.mjs +0 -6
- package/dist/lib/compliance/index.mjs.map +1 -1
- package/dist/lib/compliance-fixtures/index.mjs +0 -6
- package/dist/lib/compliance-fixtures/index.mjs.map +1 -1
- package/dist/lib/compliance-fixtures/test-authorization-server.mjs +0 -6
- package/dist/lib/compliance-fixtures/test-authorization-server.mjs.map +1 -1
- package/dist/lib/conformance/index.mjs +0 -6
- package/dist/lib/conformance/index.mjs.map +1 -1
- package/dist/lib/conformance/invariants/uniformError.mjs +0 -6
- package/dist/lib/conformance/invariants/uniformError.mjs.map +1 -1
- package/dist/lib/conformance/invariants/uniformErrorComparator.mjs +0 -6
- package/dist/lib/conformance/invariants/uniformErrorComparator.mjs.map +1 -1
- package/dist/lib/conformance/oracle.mjs +0 -6
- package/dist/lib/conformance/oracle.mjs.map +1 -1
- package/dist/lib/conformance/runConformance.mjs +0 -6
- package/dist/lib/conformance/runConformance.mjs.map +1 -1
- package/dist/lib/conformance/runners.mjs +0 -6
- package/dist/lib/conformance/runners.mjs.map +1 -1
- package/dist/lib/conformance/schemaArbitrary.mjs +0 -6
- package/dist/lib/conformance/schemaArbitrary.mjs.map +1 -1
- package/dist/lib/conformance/schemaLoader.mjs +5 -6
- package/dist/lib/conformance/schemaLoader.mjs.map +1 -1
- package/dist/lib/conformance/seeder.mjs +0 -6
- package/dist/lib/conformance/seeder.mjs.map +1 -1
- package/dist/lib/conformance/types.mjs +0 -6
- package/dist/lib/conformance/types.mjs.map +1 -1
- package/dist/lib/conformance/webhook.mjs +0 -6
- package/dist/lib/conformance/webhook.mjs.map +1 -1
- package/dist/lib/core/ADCPMultiAgentClient.mjs +0 -6
- package/dist/lib/core/ADCPMultiAgentClient.mjs.map +1 -1
- package/dist/lib/core/AgentClient.mjs +0 -6
- package/dist/lib/core/AgentClient.mjs.map +1 -1
- package/dist/lib/core/AsyncHandler.mjs +0 -6
- package/dist/lib/core/AsyncHandler.mjs.map +1 -1
- package/dist/lib/core/ConfigurationManager.mjs +0 -6
- package/dist/lib/core/ConfigurationManager.mjs.map +1 -1
- package/dist/lib/core/ConversationTypes.mjs +0 -6
- package/dist/lib/core/CreativeAgentClient.mjs +0 -6
- package/dist/lib/core/CreativeAgentClient.mjs.map +1 -1
- package/dist/lib/core/GovernanceMiddleware.mjs +0 -6
- package/dist/lib/core/GovernanceMiddleware.mjs.map +1 -1
- package/dist/lib/core/GovernanceTypes.mjs +0 -6
- package/dist/lib/core/GovernanceTypes.mjs.map +1 -1
- package/dist/lib/core/ProtocolResponseParser.mjs +0 -6
- package/dist/lib/core/ProtocolResponseParser.mjs.map +1 -1
- package/dist/lib/core/ResponseValidator.mjs +0 -6
- package/dist/lib/core/ResponseValidator.mjs.map +1 -1
- package/dist/lib/core/SingleAgentClient.mjs +0 -6
- package/dist/lib/core/SingleAgentClient.mjs.map +1 -1
- package/dist/lib/core/TaskEventTypes.mjs +0 -6
- package/dist/lib/core/TaskEventTypes.mjs.map +1 -1
- package/dist/lib/core/TaskExecutor.mjs +0 -6
- package/dist/lib/core/TaskExecutor.mjs.map +1 -1
- package/dist/lib/core/match.mjs +0 -6
- package/dist/lib/core/match.mjs.map +1 -1
- package/dist/lib/core/task-status.mjs +0 -6
- package/dist/lib/core/task-status.mjs.map +1 -1
- package/dist/lib/core/webhook-url.mjs +0 -6
- package/dist/lib/core/webhook-url.mjs.map +1 -1
- package/dist/lib/discovery/adagents-redirects.mjs +0 -6
- package/dist/lib/discovery/adagents-redirects.mjs.map +1 -1
- package/dist/lib/discovery/agent-directory.mjs +0 -6
- package/dist/lib/discovery/agent-directory.mjs.map +1 -1
- package/dist/lib/discovery/inline-publisher-properties.mjs +0 -6
- package/dist/lib/discovery/inline-publisher-properties.mjs.map +1 -1
- package/dist/lib/discovery/network-consistency-checker.mjs +0 -6
- package/dist/lib/discovery/network-consistency-checker.mjs.map +1 -1
- package/dist/lib/discovery/property-crawler.mjs +0 -6
- package/dist/lib/discovery/property-crawler.mjs.map +1 -1
- package/dist/lib/discovery/property-index.mjs +0 -6
- package/dist/lib/discovery/property-index.mjs.map +1 -1
- package/dist/lib/discovery/publisher-property-selector.mjs +0 -6
- package/dist/lib/discovery/publisher-property-selector.mjs.map +1 -1
- package/dist/lib/discovery/resolve-agent-properties.mjs +0 -6
- package/dist/lib/discovery/resolve-agent-properties.mjs.map +1 -1
- package/dist/lib/discovery/types.mjs +0 -6
- package/dist/lib/discovery/validate-adagents.mjs +0 -6
- package/dist/lib/discovery/validate-adagents.mjs.map +1 -1
- package/dist/lib/enums.mjs +0 -6
- package/dist/lib/enums.mjs.map +1 -1
- package/dist/lib/errors/index.mjs +0 -6
- package/dist/lib/errors/index.mjs.map +1 -1
- package/dist/lib/express-mcp/index.mjs +0 -6
- package/dist/lib/express-mcp/index.mjs.map +1 -1
- package/dist/lib/governance/index.mjs +0 -6
- package/dist/lib/governance/index.mjs.map +1 -1
- package/dist/lib/handlers/types.mjs +0 -6
- package/dist/lib/handlers/types.mjs.map +1 -1
- package/dist/lib/index.d.mts +1 -1
- package/dist/lib/index.d.ts +1 -1
- package/dist/lib/index.d.ts.map +1 -1
- package/dist/lib/index.js.map +1 -1
- package/dist/lib/index.mjs +0 -6
- package/dist/lib/index.mjs.map +1 -1
- package/dist/lib/media-buy/available-actions.mjs +0 -6
- package/dist/lib/media-buy/available-actions.mjs.map +1 -1
- package/dist/lib/media-buy/index.mjs +0 -6
- package/dist/lib/media-buy/index.mjs.map +1 -1
- package/dist/lib/media-buy/preflight.mjs +0 -6
- package/dist/lib/media-buy/preflight.mjs.map +1 -1
- package/dist/lib/media-buy/property-policy.mjs +0 -6
- package/dist/lib/media-buy/property-policy.mjs.map +1 -1
- package/dist/lib/media-buy/types.mjs +0 -6
- package/dist/lib/media-buy/types.mjs.map +1 -1
- package/dist/lib/media-buy/update-fields.generated.mjs +0 -6
- package/dist/lib/media-buy/update-fields.generated.mjs.map +1 -1
- package/dist/lib/mock-server/creative-ad-server/seed-data.mjs +0 -6
- package/dist/lib/mock-server/creative-ad-server/seed-data.mjs.map +1 -1
- package/dist/lib/mock-server/creative-ad-server/server.mjs +0 -6
- package/dist/lib/mock-server/creative-ad-server/server.mjs.map +1 -1
- package/dist/lib/mock-server/creative-template/seed-data.mjs +0 -6
- package/dist/lib/mock-server/creative-template/seed-data.mjs.map +1 -1
- package/dist/lib/mock-server/creative-template/server.mjs +0 -6
- package/dist/lib/mock-server/creative-template/server.mjs.map +1 -1
- package/dist/lib/mock-server/index.mjs +0 -6
- package/dist/lib/mock-server/index.mjs.map +1 -1
- package/dist/lib/mock-server/sales-guaranteed/recipe.mjs +0 -6
- package/dist/lib/mock-server/sales-guaranteed/recipe.mjs.map +1 -1
- package/dist/lib/mock-server/sales-guaranteed/seed-data.mjs +0 -6
- package/dist/lib/mock-server/sales-guaranteed/seed-data.mjs.map +1 -1
- package/dist/lib/mock-server/sales-guaranteed/server.mjs +0 -6
- package/dist/lib/mock-server/sales-guaranteed/server.mjs.map +1 -1
- package/dist/lib/mock-server/sales-non-guaranteed/recipe.mjs +0 -6
- package/dist/lib/mock-server/sales-non-guaranteed/recipe.mjs.map +1 -1
- package/dist/lib/mock-server/sales-non-guaranteed/seed-data.mjs +0 -6
- package/dist/lib/mock-server/sales-non-guaranteed/seed-data.mjs.map +1 -1
- package/dist/lib/mock-server/sales-non-guaranteed/server.mjs +0 -6
- package/dist/lib/mock-server/sales-non-guaranteed/server.mjs.map +1 -1
- package/dist/lib/mock-server/sales-social/seed-data.mjs +0 -6
- package/dist/lib/mock-server/sales-social/seed-data.mjs.map +1 -1
- package/dist/lib/mock-server/sales-social/server.mjs +0 -6
- package/dist/lib/mock-server/sales-social/server.mjs.map +1 -1
- package/dist/lib/mock-server/scenario.mjs +0 -6
- package/dist/lib/mock-server/scenario.mjs.map +1 -1
- package/dist/lib/mock-server/signal-marketplace/seed-data.mjs +0 -6
- package/dist/lib/mock-server/signal-marketplace/seed-data.mjs.map +1 -1
- package/dist/lib/mock-server/signal-marketplace/server.mjs +0 -6
- package/dist/lib/mock-server/signal-marketplace/server.mjs.map +1 -1
- package/dist/lib/mock-server/sponsored-intelligence/seed-data.mjs +0 -6
- package/dist/lib/mock-server/sponsored-intelligence/seed-data.mjs.map +1 -1
- package/dist/lib/mock-server/sponsored-intelligence/server.mjs +0 -6
- package/dist/lib/mock-server/sponsored-intelligence/server.mjs.map +1 -1
- package/dist/lib/net/address-guards.mjs +0 -6
- package/dist/lib/net/address-guards.mjs.map +1 -1
- package/dist/lib/net/index.mjs +0 -6
- package/dist/lib/net/index.mjs.map +1 -1
- package/dist/lib/net/ssrf-fetch.mjs +0 -6
- package/dist/lib/net/ssrf-fetch.mjs.map +1 -1
- package/dist/lib/observability/index.mjs +0 -6
- package/dist/lib/observability/index.mjs.map +1 -1
- package/dist/lib/observability/tracing.mjs +6 -7
- package/dist/lib/observability/tracing.mjs.map +1 -1
- package/dist/lib/protocols/a2a.mjs +0 -6
- package/dist/lib/protocols/a2a.mjs.map +1 -1
- package/dist/lib/protocols/abort.mjs +0 -6
- package/dist/lib/protocols/abort.mjs.map +1 -1
- package/dist/lib/protocols/index.mjs +0 -6
- package/dist/lib/protocols/index.mjs.map +1 -1
- package/dist/lib/protocols/mcp-modern.mjs +0 -6
- package/dist/lib/protocols/mcp-modern.mjs.map +1 -1
- package/dist/lib/protocols/mcp-tasks.mjs +0 -6
- package/dist/lib/protocols/mcp-tasks.mjs.map +1 -1
- package/dist/lib/protocols/mcp.mjs +0 -6
- package/dist/lib/protocols/mcp.mjs.map +1 -1
- package/dist/lib/protocols/rawResponseCapture.mjs +0 -6
- package/dist/lib/protocols/rawResponseCapture.mjs.map +1 -1
- package/dist/lib/protocols/responseSizeLimit.mjs +0 -6
- package/dist/lib/protocols/responseSizeLimit.mjs.map +1 -1
- package/dist/lib/protocols/transportDiagnostics.mjs +0 -6
- package/dist/lib/protocols/transportDiagnostics.mjs.map +1 -1
- package/dist/lib/registry/cursor-store.mjs +0 -6
- package/dist/lib/registry/cursor-store.mjs.map +1 -1
- package/dist/lib/registry/feed-stream.mjs +0 -6
- package/dist/lib/registry/feed-stream.mjs.map +1 -1
- package/dist/lib/registry/index.mjs +0 -6
- package/dist/lib/registry/index.mjs.map +1 -1
- package/dist/lib/registry/property-registry.mjs +0 -6
- package/dist/lib/registry/property-registry.mjs.map +1 -1
- package/dist/lib/registry/sync.mjs +0 -6
- package/dist/lib/registry/sync.mjs.map +1 -1
- package/dist/lib/registry/types.generated.mjs +0 -6
- package/dist/lib/registry/types.mjs +0 -6
- package/dist/lib/schemas/index.mjs +0 -6
- package/dist/lib/schemas/index.mjs.map +1 -1
- package/dist/lib/schemas-data/v2.5/_provenance.json +1 -1
- package/dist/lib/server/a2a-adapter.mjs +0 -6
- package/dist/lib/server/a2a-adapter.mjs.map +1 -1
- package/dist/lib/server/account-mode.mjs +0 -6
- package/dist/lib/server/account-mode.mjs.map +1 -1
- package/dist/lib/server/adcp-server.mjs +0 -6
- package/dist/lib/server/adcp-server.mjs.map +1 -1
- package/dist/lib/server/auth-introspection.mjs +0 -6
- package/dist/lib/server/auth-introspection.mjs.map +1 -1
- package/dist/lib/server/auth-signature.mjs +0 -6
- package/dist/lib/server/auth-signature.mjs.map +1 -1
- package/dist/lib/server/auth.mjs +0 -6
- package/dist/lib/server/auth.mjs.map +1 -1
- package/dist/lib/server/create-adcp-server.d.mts +13 -0
- package/dist/lib/server/create-adcp-server.d.ts +13 -0
- package/dist/lib/server/create-adcp-server.d.ts.map +1 -1
- package/dist/lib/server/create-adcp-server.js +3 -2
- package/dist/lib/server/create-adcp-server.js.map +1 -1
- package/dist/lib/server/create-adcp-server.mjs +3 -8
- package/dist/lib/server/create-adcp-server.mjs.map +1 -1
- package/dist/lib/server/credential-policy.mjs +0 -6
- package/dist/lib/server/credential-policy.mjs.map +1 -1
- package/dist/lib/server/ctx-metadata/backends/memory.mjs +0 -6
- package/dist/lib/server/ctx-metadata/backends/memory.mjs.map +1 -1
- package/dist/lib/server/ctx-metadata/backends/pg.mjs +0 -6
- package/dist/lib/server/ctx-metadata/backends/pg.mjs.map +1 -1
- package/dist/lib/server/ctx-metadata/backends/redis.mjs +0 -6
- package/dist/lib/server/ctx-metadata/backends/redis.mjs.map +1 -1
- package/dist/lib/server/ctx-metadata/index.mjs +0 -6
- package/dist/lib/server/ctx-metadata/index.mjs.map +1 -1
- package/dist/lib/server/ctx-metadata/store.mjs +0 -6
- package/dist/lib/server/ctx-metadata/store.mjs.map +1 -1
- package/dist/lib/server/ctx-metadata/wire-shape.mjs +0 -6
- package/dist/lib/server/ctx-metadata/wire-shape.mjs.map +1 -1
- package/dist/lib/server/decisioning/account.mjs +0 -6
- package/dist/lib/server/decisioning/account.mjs.map +1 -1
- package/dist/lib/server/decisioning/admin-router.mjs +0 -6
- package/dist/lib/server/decisioning/admin-router.mjs.map +1 -1
- package/dist/lib/server/decisioning/assembly-helpers.mjs +0 -6
- package/dist/lib/server/decisioning/assembly-helpers.mjs.map +1 -1
- package/dist/lib/server/decisioning/async-outcome.mjs +0 -6
- package/dist/lib/server/decisioning/async-outcome.mjs.map +1 -1
- package/dist/lib/server/decisioning/buyer-agent.mjs +0 -6
- package/dist/lib/server/decisioning/buyer-agent.mjs.map +1 -1
- package/dist/lib/server/decisioning/capabilities.mjs +0 -6
- package/dist/lib/server/decisioning/capabilities.mjs.map +1 -1
- package/dist/lib/server/decisioning/compose.mjs +0 -6
- package/dist/lib/server/decisioning/compose.mjs.map +1 -1
- package/dist/lib/server/decisioning/context.mjs +0 -6
- package/dist/lib/server/decisioning/errors-typed.mjs +0 -6
- package/dist/lib/server/decisioning/errors-typed.mjs.map +1 -1
- package/dist/lib/server/decisioning/helpers.mjs +0 -6
- package/dist/lib/server/decisioning/helpers.mjs.map +1 -1
- package/dist/lib/server/decisioning/index.mjs +0 -6
- package/dist/lib/server/decisioning/index.mjs.map +1 -1
- package/dist/lib/server/decisioning/list-helpers.mjs +0 -6
- package/dist/lib/server/decisioning/list-helpers.mjs.map +1 -1
- package/dist/lib/server/decisioning/manifest-helpers.mjs +0 -6
- package/dist/lib/server/decisioning/manifest-helpers.mjs.map +1 -1
- package/dist/lib/server/decisioning/pagination.mjs +0 -6
- package/dist/lib/server/decisioning/platform-helpers.mjs +0 -6
- package/dist/lib/server/decisioning/platform-helpers.mjs.map +1 -1
- package/dist/lib/server/decisioning/platform.mjs +0 -6
- package/dist/lib/server/decisioning/proposal/dispatch.mjs +0 -6
- package/dist/lib/server/decisioning/proposal/dispatch.mjs.map +1 -1
- package/dist/lib/server/decisioning/proposal/index.mjs +0 -6
- package/dist/lib/server/decisioning/proposal/index.mjs.map +1 -1
- package/dist/lib/server/decisioning/proposal/lifecycle.mjs +0 -6
- package/dist/lib/server/decisioning/proposal/lifecycle.mjs.map +1 -1
- package/dist/lib/server/decisioning/proposal/mock-manager.mjs +0 -6
- package/dist/lib/server/decisioning/proposal/mock-manager.mjs.map +1 -1
- package/dist/lib/server/decisioning/proposal/store.mjs +0 -6
- package/dist/lib/server/decisioning/proposal/store.mjs.map +1 -1
- package/dist/lib/server/decisioning/proposal/types.mjs +0 -6
- package/dist/lib/server/decisioning/proposal/types.mjs.map +1 -1
- package/dist/lib/server/decisioning/resolve-presets.mjs +0 -6
- package/dist/lib/server/decisioning/resolve-presets.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/entity-hydration.generated.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/entity-hydration.generated.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/from-platform.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/from-platform.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/observed-modes.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/observed-modes.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/postgres-task-registry.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/postgres-task-registry.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/protocol-for-tool.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/protocol-for-tool.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/task-registry.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/task-registry.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/to-context.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/to-context.mjs.map +1 -1
- package/dist/lib/server/decisioning/runtime/validate-platform.mjs +0 -6
- package/dist/lib/server/decisioning/runtime/validate-platform.mjs.map +1 -1
- package/dist/lib/server/decisioning/specialisms/audiences.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/brand-rights.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/campaign-governance.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/content-standards.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/creative-ad-server.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/creative.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/lists.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/sales.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/signals.mjs +0 -6
- package/dist/lib/server/decisioning/specialisms/sponsored-intelligence.mjs +0 -6
- package/dist/lib/server/decisioning/start-time.mjs +0 -6
- package/dist/lib/server/decisioning/start-time.mjs.map +1 -1
- package/dist/lib/server/decisioning/status-changes.mjs +0 -6
- package/dist/lib/server/decisioning/status-changes.mjs.map +1 -1
- package/dist/lib/server/decisioning/status-mappers.mjs +0 -6
- package/dist/lib/server/decisioning/status-mappers.mjs.map +1 -1
- package/dist/lib/server/decisioning/tenant-registry.mjs +0 -6
- package/dist/lib/server/decisioning/tenant-registry.mjs.map +1 -1
- package/dist/lib/server/decisioning/tenant-store.mjs +0 -6
- package/dist/lib/server/decisioning/tenant-store.mjs.map +1 -1
- package/dist/lib/server/decisioning/validate-specialisms.mjs +0 -6
- package/dist/lib/server/decisioning/validate-specialisms.mjs.map +1 -1
- package/dist/lib/server/dynamic-registry.mjs +0 -6
- package/dist/lib/server/dynamic-registry.mjs.map +1 -1
- package/dist/lib/server/envelope-allowlist.mjs +0 -6
- package/dist/lib/server/envelope-allowlist.mjs.map +1 -1
- package/dist/lib/server/error-arm-tools.mjs +5 -6
- package/dist/lib/server/error-arm-tools.mjs.map +1 -1
- package/dist/lib/server/errors.mjs +0 -6
- package/dist/lib/server/errors.mjs.map +1 -1
- package/dist/lib/server/example-tld-guard.mjs +0 -6
- package/dist/lib/server/example-tld-guard.mjs.map +1 -1
- package/dist/lib/server/express-adapter.mjs +0 -6
- package/dist/lib/server/express-adapter.mjs.map +1 -1
- package/dist/lib/server/governance.mjs +0 -6
- package/dist/lib/server/governance.mjs.map +1 -1
- package/dist/lib/server/idempotency/backends/lazy.mjs +0 -6
- package/dist/lib/server/idempotency/backends/lazy.mjs.map +1 -1
- package/dist/lib/server/idempotency/backends/memory.mjs +0 -6
- package/dist/lib/server/idempotency/backends/memory.mjs.map +1 -1
- package/dist/lib/server/idempotency/backends/pg.mjs +0 -6
- package/dist/lib/server/idempotency/backends/pg.mjs.map +1 -1
- package/dist/lib/server/idempotency/backends/redis.mjs +0 -6
- package/dist/lib/server/idempotency/backends/redis.mjs.map +1 -1
- package/dist/lib/server/idempotency/index.mjs +0 -6
- package/dist/lib/server/idempotency/index.mjs.map +1 -1
- package/dist/lib/server/idempotency/store.mjs +0 -6
- package/dist/lib/server/idempotency/store.mjs.map +1 -1
- package/dist/lib/server/index.d.mts +1 -1
- package/dist/lib/server/index.d.ts +1 -1
- package/dist/lib/server/index.d.ts.map +1 -1
- package/dist/lib/server/index.js.map +1 -1
- package/dist/lib/server/index.mjs +0 -6
- package/dist/lib/server/index.mjs.map +1 -1
- package/dist/lib/server/legacy/v5/index.d.mts +1 -1
- package/dist/lib/server/legacy/v5/index.d.ts +1 -1
- package/dist/lib/server/legacy/v5/index.d.ts.map +1 -1
- package/dist/lib/server/legacy/v5/index.js.map +1 -1
- package/dist/lib/server/legacy/v5/index.mjs +0 -6
- package/dist/lib/server/legacy/v5/index.mjs.map +1 -1
- package/dist/lib/server/mcp-modern-server.mjs +0 -6
- package/dist/lib/server/mcp-modern-server.mjs.map +1 -1
- package/dist/lib/server/media-buy-actions.mjs +0 -6
- package/dist/lib/server/media-buy-actions.mjs.map +1 -1
- package/dist/lib/server/media-buy-helpers.mjs +0 -6
- package/dist/lib/server/media-buy-helpers.mjs.map +1 -1
- package/dist/lib/server/media-buy-store.mjs +0 -6
- package/dist/lib/server/media-buy-store.mjs.map +1 -1
- package/dist/lib/server/normalize-errors.mjs +0 -6
- package/dist/lib/server/normalize-errors.mjs.map +1 -1
- package/dist/lib/server/operational-platform.mjs +0 -6
- package/dist/lib/server/operational-platform.mjs.map +1 -1
- package/dist/lib/server/pick-safe-details.mjs +0 -6
- package/dist/lib/server/pick-safe-details.mjs.map +1 -1
- package/dist/lib/server/pin-and-bind-fetch.mjs +0 -6
- package/dist/lib/server/pin-and-bind-fetch.mjs.map +1 -1
- package/dist/lib/server/postgres-state-store.mjs +0 -6
- package/dist/lib/server/postgres-state-store.mjs.map +1 -1
- package/dist/lib/server/postgres-task-store.mjs +0 -6
- package/dist/lib/server/postgres-task-store.mjs.map +1 -1
- package/dist/lib/server/product-defaults.mjs +0 -6
- package/dist/lib/server/product-defaults.mjs.map +1 -1
- package/dist/lib/server/redact.mjs +0 -6
- package/dist/lib/server/redact.mjs.map +1 -1
- package/dist/lib/server/responses.mjs +0 -6
- package/dist/lib/server/responses.mjs.map +1 -1
- package/dist/lib/server/serve.mjs +0 -6
- package/dist/lib/server/serve.mjs.map +1 -1
- package/dist/lib/server/socket-mode/conformance-client.mjs +0 -6
- package/dist/lib/server/socket-mode/conformance-client.mjs.map +1 -1
- package/dist/lib/server/socket-mode/index.mjs +0 -6
- package/dist/lib/server/socket-mode/index.mjs.map +1 -1
- package/dist/lib/server/socket-mode/ws-transport.mjs +0 -6
- package/dist/lib/server/socket-mode/ws-transport.mjs.map +1 -1
- package/dist/lib/server/state-machine.mjs +0 -6
- package/dist/lib/server/state-machine.mjs.map +1 -1
- package/dist/lib/server/state-store.mjs +0 -6
- package/dist/lib/server/state-store.mjs.map +1 -1
- package/dist/lib/server/structured-serialize.mjs +0 -6
- package/dist/lib/server/structured-serialize.mjs.map +1 -1
- package/dist/lib/server/targeting-helpers.mjs +0 -6
- package/dist/lib/server/targeting-helpers.mjs.map +1 -1
- package/dist/lib/server/tasks.mjs +0 -6
- package/dist/lib/server/tasks.mjs.map +1 -1
- package/dist/lib/server/test-controller-bridge.mjs +0 -6
- package/dist/lib/server/test-controller-bridge.mjs.map +1 -1
- package/dist/lib/server/test-controller.mjs +0 -6
- package/dist/lib/server/test-controller.mjs.map +1 -1
- package/dist/lib/server/upstream-helpers.mjs +0 -6
- package/dist/lib/server/upstream-helpers.mjs.map +1 -1
- package/dist/lib/server/webhook-emitter.mjs +0 -6
- package/dist/lib/server/webhook-emitter.mjs.map +1 -1
- package/dist/lib/server/wire-safe.mjs +0 -6
- package/dist/lib/server/wire-safe.mjs.map +1 -1
- package/dist/lib/server/wire-spec-fields.generated.mjs +0 -6
- package/dist/lib/server/wire-spec-fields.generated.mjs.map +1 -1
- package/dist/lib/server/wrap-envelope.mjs +0 -6
- package/dist/lib/server/wrap-envelope.mjs.map +1 -1
- package/dist/lib/signing/agent-context.mjs +0 -6
- package/dist/lib/signing/agent-context.mjs.map +1 -1
- package/dist/lib/signing/agent-fetch.mjs +0 -6
- package/dist/lib/signing/agent-fetch.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/canonicalize.mjs +0 -6
- package/dist/lib/signing/agent-resolver/canonicalize.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/capabilities-types.mjs +0 -6
- package/dist/lib/signing/agent-resolver/capabilities-types.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/consistency.mjs +0 -6
- package/dist/lib/signing/agent-resolver/consistency.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/errors.mjs +0 -6
- package/dist/lib/signing/agent-resolver/errors.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/etld.mjs +0 -6
- package/dist/lib/signing/agent-resolver/etld.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/fetch-helpers.mjs +0 -6
- package/dist/lib/signing/agent-resolver/fetch-helpers.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/index.mjs +0 -6
- package/dist/lib/signing/agent-resolver/index.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/jwks-set.mjs +0 -6
- package/dist/lib/signing/agent-resolver/jwks-set.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/resolve-agent.mjs +0 -6
- package/dist/lib/signing/agent-resolver/resolve-agent.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/select-agent.mjs +0 -6
- package/dist/lib/signing/agent-resolver/select-agent.mjs.map +1 -1
- package/dist/lib/signing/agent-resolver/strict-json.mjs +0 -6
- package/dist/lib/signing/agent-resolver/strict-json.mjs.map +1 -1
- package/dist/lib/signing/brand-jwks.mjs +0 -6
- package/dist/lib/signing/brand-jwks.mjs.map +1 -1
- package/dist/lib/signing/canonicalize.mjs +0 -6
- package/dist/lib/signing/canonicalize.mjs.map +1 -1
- package/dist/lib/signing/capability-cache.mjs +0 -6
- package/dist/lib/signing/capability-cache.mjs.map +1 -1
- package/dist/lib/signing/capability-priming.mjs +0 -6
- package/dist/lib/signing/capability-priming.mjs.map +1 -1
- package/dist/lib/signing/client.mjs +0 -6
- package/dist/lib/signing/client.mjs.map +1 -1
- package/dist/lib/signing/content-digest.mjs +0 -6
- package/dist/lib/signing/content-digest.mjs.map +1 -1
- package/dist/lib/signing/crypto.mjs +0 -6
- package/dist/lib/signing/crypto.mjs.map +1 -1
- package/dist/lib/signing/ecdsa-encoding.mjs +0 -6
- package/dist/lib/signing/ecdsa-encoding.mjs.map +1 -1
- package/dist/lib/signing/errors.mjs +0 -6
- package/dist/lib/signing/errors.mjs.map +1 -1
- package/dist/lib/signing/fetch-async.mjs +0 -6
- package/dist/lib/signing/fetch-async.mjs.map +1 -1
- package/dist/lib/signing/fetch.mjs +0 -6
- package/dist/lib/signing/fetch.mjs.map +1 -1
- package/dist/lib/signing/index.mjs +0 -6
- package/dist/lib/signing/index.mjs.map +1 -1
- package/dist/lib/signing/jwks-helpers.mjs +0 -6
- package/dist/lib/signing/jwks-helpers.mjs.map +1 -1
- package/dist/lib/signing/jwks-https.mjs +0 -6
- package/dist/lib/signing/jwks-https.mjs.map +1 -1
- package/dist/lib/signing/jwks.mjs +0 -6
- package/dist/lib/signing/jwks.mjs.map +1 -1
- package/dist/lib/signing/middleware.mjs +0 -6
- package/dist/lib/signing/middleware.mjs.map +1 -1
- package/dist/lib/signing/parser.mjs +0 -6
- package/dist/lib/signing/parser.mjs.map +1 -1
- package/dist/lib/signing/postgres-replay-store.mjs +0 -6
- package/dist/lib/signing/postgres-replay-store.mjs.map +1 -1
- package/dist/lib/signing/protocol-response.mjs +0 -6
- package/dist/lib/signing/protocol-response.mjs.map +1 -1
- package/dist/lib/signing/provider.mjs +0 -6
- package/dist/lib/signing/redis-replay-store.mjs +0 -6
- package/dist/lib/signing/redis-replay-store.mjs.map +1 -1
- package/dist/lib/signing/replay.mjs +0 -6
- package/dist/lib/signing/replay.mjs.map +1 -1
- package/dist/lib/signing/request-context.mjs +0 -6
- package/dist/lib/signing/request-context.mjs.map +1 -1
- package/dist/lib/signing/revocation-https.mjs +0 -6
- package/dist/lib/signing/revocation-https.mjs.map +1 -1
- package/dist/lib/signing/revocation.mjs +0 -6
- package/dist/lib/signing/revocation.mjs.map +1 -1
- package/dist/lib/signing/server.mjs +0 -6
- package/dist/lib/signing/server.mjs.map +1 -1
- package/dist/lib/signing/signer-async.mjs +0 -6
- package/dist/lib/signing/signer-async.mjs.map +1 -1
- package/dist/lib/signing/signer.mjs +0 -6
- package/dist/lib/signing/signer.mjs.map +1 -1
- package/dist/lib/signing/testing.mjs +0 -6
- package/dist/lib/signing/testing.mjs.map +1 -1
- package/dist/lib/signing/types.mjs +0 -6
- package/dist/lib/signing/types.mjs.map +1 -1
- package/dist/lib/signing/verifier.mjs +0 -6
- package/dist/lib/signing/verifier.mjs.map +1 -1
- package/dist/lib/signing/webhook-auth-detection.mjs +0 -6
- package/dist/lib/signing/webhook-auth-detection.mjs.map +1 -1
- package/dist/lib/signing/webhook-verifier.mjs +0 -6
- package/dist/lib/signing/webhook-verifier.mjs.map +1 -1
- package/dist/lib/storage/MemoryStorage.mjs +0 -6
- package/dist/lib/storage/MemoryStorage.mjs.map +1 -1
- package/dist/lib/storage/interfaces.mjs +0 -6
- package/dist/lib/substitution/encoder/SubstitutionEncoder.mjs +0 -6
- package/dist/lib/substitution/encoder/SubstitutionEncoder.mjs.map +1 -1
- package/dist/lib/substitution/encoder/index.mjs +0 -6
- package/dist/lib/substitution/encoder/index.mjs.map +1 -1
- package/dist/lib/substitution/index.mjs +0 -6
- package/dist/lib/substitution/index.mjs.map +1 -1
- package/dist/lib/substitution/observer/SubstitutionObserver.mjs +0 -6
- package/dist/lib/substitution/observer/SubstitutionObserver.mjs.map +1 -1
- package/dist/lib/substitution/observer/alignment.mjs +0 -6
- package/dist/lib/substitution/observer/alignment.mjs.map +1 -1
- package/dist/lib/substitution/observer/assertions.mjs +0 -6
- package/dist/lib/substitution/observer/assertions.mjs.map +1 -1
- package/dist/lib/substitution/observer/html-parser.mjs +0 -6
- package/dist/lib/substitution/observer/html-parser.mjs.map +1 -1
- package/dist/lib/substitution/observer/index.mjs +0 -6
- package/dist/lib/substitution/observer/index.mjs.map +1 -1
- package/dist/lib/substitution/observer/ssrf.mjs +0 -6
- package/dist/lib/substitution/observer/ssrf.mjs.map +1 -1
- package/dist/lib/substitution/rfc3986.mjs +0 -6
- package/dist/lib/substitution/rfc3986.mjs.map +1 -1
- package/dist/lib/substitution/translate.mjs +0 -6
- package/dist/lib/substitution/translate.mjs.map +1 -1
- package/dist/lib/substitution/types.mjs +0 -6
- package/dist/lib/substitution/vectors.mjs +0 -6
- package/dist/lib/substitution/vectors.mjs.map +1 -1
- package/dist/lib/testing/agent-tester.mjs +0 -6
- package/dist/lib/testing/agent-tester.mjs.map +1 -1
- package/dist/lib/testing/client.mjs +0 -6
- package/dist/lib/testing/client.mjs.map +1 -1
- package/dist/lib/testing/compliance/briefs.mjs +0 -6
- package/dist/lib/testing/compliance/briefs.mjs.map +1 -1
- package/dist/lib/testing/compliance/comply.mjs +0 -6
- package/dist/lib/testing/compliance/comply.mjs.map +1 -1
- package/dist/lib/testing/compliance/index.mjs +0 -6
- package/dist/lib/testing/compliance/index.mjs.map +1 -1
- package/dist/lib/testing/compliance/spec-conformance.mjs +0 -6
- package/dist/lib/testing/compliance/spec-conformance.mjs.map +1 -1
- package/dist/lib/testing/compliance/storyboard-tracks.mjs +0 -6
- package/dist/lib/testing/compliance/storyboard-tracks.mjs.map +1 -1
- package/dist/lib/testing/compliance/summary.mjs +0 -6
- package/dist/lib/testing/compliance/summary.mjs.map +1 -1
- package/dist/lib/testing/compliance/types.mjs +0 -6
- package/dist/lib/testing/comply-controller.mjs +0 -6
- package/dist/lib/testing/comply-controller.mjs.map +1 -1
- package/dist/lib/testing/controller-assertions.mjs +0 -6
- package/dist/lib/testing/controller-assertions.mjs.map +1 -1
- package/dist/lib/testing/formatter.mjs +0 -6
- package/dist/lib/testing/formatter.mjs.map +1 -1
- package/dist/lib/testing/index.mjs +0 -6
- package/dist/lib/testing/index.mjs.map +1 -1
- package/dist/lib/testing/local-agent-runner.mjs +0 -6
- package/dist/lib/testing/local-agent-runner.mjs.map +1 -1
- package/dist/lib/testing/orchestrator.mjs +0 -6
- package/dist/lib/testing/orchestrator.mjs.map +1 -1
- package/dist/lib/testing/personas/index.mjs +0 -6
- package/dist/lib/testing/personas/index.mjs.map +1 -1
- package/dist/lib/testing/scenarios/brand-rights.mjs +0 -6
- package/dist/lib/testing/scenarios/brand-rights.mjs.map +1 -1
- package/dist/lib/testing/scenarios/capabilities.mjs +0 -6
- package/dist/lib/testing/scenarios/capabilities.mjs.map +1 -1
- package/dist/lib/testing/scenarios/creative.mjs +0 -6
- package/dist/lib/testing/scenarios/creative.mjs.map +1 -1
- package/dist/lib/testing/scenarios/deterministic.mjs +0 -6
- package/dist/lib/testing/scenarios/deterministic.mjs.map +1 -1
- package/dist/lib/testing/scenarios/discovery.mjs +0 -6
- package/dist/lib/testing/scenarios/discovery.mjs.map +1 -1
- package/dist/lib/testing/scenarios/edge-cases.mjs +0 -6
- package/dist/lib/testing/scenarios/edge-cases.mjs.map +1 -1
- package/dist/lib/testing/scenarios/error-compliance.mjs +0 -6
- package/dist/lib/testing/scenarios/error-compliance.mjs.map +1 -1
- package/dist/lib/testing/scenarios/governance.mjs +0 -6
- package/dist/lib/testing/scenarios/governance.mjs.map +1 -1
- package/dist/lib/testing/scenarios/health.mjs +0 -6
- package/dist/lib/testing/scenarios/health.mjs.map +1 -1
- package/dist/lib/testing/scenarios/index.mjs +0 -6
- package/dist/lib/testing/scenarios/index.mjs.map +1 -1
- package/dist/lib/testing/scenarios/media-buy.mjs +0 -6
- package/dist/lib/testing/scenarios/media-buy.mjs.map +1 -1
- package/dist/lib/testing/scenarios/schema-compliance.mjs +0 -6
- package/dist/lib/testing/scenarios/schema-compliance.mjs.map +1 -1
- package/dist/lib/testing/scenarios/signals.mjs +0 -6
- package/dist/lib/testing/scenarios/signals.mjs.map +1 -1
- package/dist/lib/testing/scenarios/sponsored-intelligence.mjs +0 -6
- package/dist/lib/testing/scenarios/sponsored-intelligence.mjs.map +1 -1
- package/dist/lib/testing/scenarios/trusted-match.mjs +0 -6
- package/dist/lib/testing/scenarios/trusted-match.mjs.map +1 -1
- package/dist/lib/testing/seed-merge.mjs +0 -6
- package/dist/lib/testing/seed-merge.mjs.map +1 -1
- package/dist/lib/testing/storyboard/agent-routing.mjs +0 -6
- package/dist/lib/testing/storyboard/agent-routing.mjs.map +1 -1
- package/dist/lib/testing/storyboard/assertions.mjs +0 -6
- package/dist/lib/testing/storyboard/assertions.mjs.map +1 -1
- package/dist/lib/testing/storyboard/canonical-format-satisfaction.mjs +0 -6
- package/dist/lib/testing/storyboard/canonical-format-satisfaction.mjs.map +1 -1
- package/dist/lib/testing/storyboard/compliance.mjs +5 -6
- package/dist/lib/testing/storyboard/compliance.mjs.map +1 -1
- package/dist/lib/testing/storyboard/context.mjs +0 -6
- package/dist/lib/testing/storyboard/context.mjs.map +1 -1
- package/dist/lib/testing/storyboard/default-invariants.mjs +0 -6
- package/dist/lib/testing/storyboard/default-invariants.mjs.map +1 -1
- package/dist/lib/testing/storyboard/index.mjs +0 -6
- package/dist/lib/testing/storyboard/index.mjs.map +1 -1
- package/dist/lib/testing/storyboard/junit.mjs +0 -6
- package/dist/lib/testing/storyboard/junit.mjs.map +1 -1
- package/dist/lib/testing/storyboard/loader.mjs +0 -6
- package/dist/lib/testing/storyboard/loader.mjs.map +1 -1
- package/dist/lib/testing/storyboard/parallel-dispatch.mjs +0 -6
- package/dist/lib/testing/storyboard/parallel-dispatch.mjs.map +1 -1
- package/dist/lib/testing/storyboard/path.mjs +0 -6
- package/dist/lib/testing/storyboard/path.mjs.map +1 -1
- package/dist/lib/testing/storyboard/probes.mjs +0 -6
- package/dist/lib/testing/storyboard/probes.mjs.map +1 -1
- package/dist/lib/testing/storyboard/rate-limit-trip.mjs +0 -6
- package/dist/lib/testing/storyboard/rate-limit-trip.mjs.map +1 -1
- package/dist/lib/testing/storyboard/rejection-hints.mjs +0 -6
- package/dist/lib/testing/storyboard/rejection-hints.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-builder.mjs +0 -6
- package/dist/lib/testing/storyboard/request-builder.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/builder.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/builder.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/grader.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/grader.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/index.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/index.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/probe-dispatch.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/probe-dispatch.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/probe.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/probe.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/synthesize.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/synthesize.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/test-kit.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/test-kit.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/types.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/types.mjs.map +1 -1
- package/dist/lib/testing/storyboard/request-signing/vector-loader.mjs +0 -6
- package/dist/lib/testing/storyboard/request-signing/vector-loader.mjs.map +1 -1
- package/dist/lib/testing/storyboard/runner.mjs +0 -6
- package/dist/lib/testing/storyboard/runner.mjs.map +1 -1
- package/dist/lib/testing/storyboard/sandbox-entities.mjs +0 -6
- package/dist/lib/testing/storyboard/sandbox-entities.mjs.map +1 -1
- package/dist/lib/testing/storyboard/seeding.mjs +0 -6
- package/dist/lib/testing/storyboard/seeding.mjs.map +1 -1
- package/dist/lib/testing/storyboard/shape-drift-hints.mjs +0 -6
- package/dist/lib/testing/storyboard/shape-drift-hints.mjs.map +1 -1
- package/dist/lib/testing/storyboard/signer-grader/grader.mjs +0 -6
- package/dist/lib/testing/storyboard/signer-grader/grader.mjs.map +1 -1
- package/dist/lib/testing/storyboard/signer-grader/index.mjs +0 -6
- package/dist/lib/testing/storyboard/signer-grader/index.mjs.map +1 -1
- package/dist/lib/testing/storyboard/signer-grader/types.mjs +0 -6
- package/dist/lib/testing/storyboard/strict-validation-hints.mjs +0 -6
- package/dist/lib/testing/storyboard/strict-validation-hints.mjs.map +1 -1
- package/dist/lib/testing/storyboard/task-map.mjs +0 -6
- package/dist/lib/testing/storyboard/task-map.mjs.map +1 -1
- package/dist/lib/testing/storyboard/test-kit.mjs +0 -6
- package/dist/lib/testing/storyboard/test-kit.mjs.map +1 -1
- package/dist/lib/testing/storyboard/types.mjs +0 -6
- package/dist/lib/testing/storyboard/types.mjs.map +1 -1
- package/dist/lib/testing/storyboard/validations.mjs +0 -6
- package/dist/lib/testing/storyboard/validations.mjs.map +1 -1
- package/dist/lib/testing/storyboard/webhook-assertions.mjs +0 -6
- package/dist/lib/testing/storyboard/webhook-assertions.mjs.map +1 -1
- package/dist/lib/testing/storyboard/webhook-receiver.mjs +0 -6
- package/dist/lib/testing/storyboard/webhook-receiver.mjs.map +1 -1
- package/dist/lib/testing/stubs/governance-agent-stub.mjs +0 -6
- package/dist/lib/testing/stubs/governance-agent-stub.mjs.map +1 -1
- package/dist/lib/testing/stubs/index.mjs +0 -6
- package/dist/lib/testing/stubs/index.mjs.map +1 -1
- package/dist/lib/testing/test-controller.mjs +0 -6
- package/dist/lib/testing/test-controller.mjs.map +1 -1
- package/dist/lib/testing/test-helpers.mjs +0 -6
- package/dist/lib/testing/test-helpers.mjs.map +1 -1
- package/dist/lib/testing/types.mjs +0 -6
- package/dist/lib/types/adcp.mjs +0 -6
- package/dist/lib/types/adcp.mjs.map +1 -1
- package/dist/lib/types/asset-instances.mjs +0 -6
- package/dist/lib/types/compat.mjs +0 -6
- package/dist/lib/types/compat.mjs.map +1 -1
- package/dist/lib/types/core.generated.mjs +0 -6
- package/dist/lib/types/enums.generated.mjs +0 -6
- package/dist/lib/types/enums.generated.mjs.map +1 -1
- package/dist/lib/types/error-codes.mjs +0 -6
- package/dist/lib/types/error-codes.mjs.map +1 -1
- package/dist/lib/types/error-details.aliases.mjs +0 -6
- package/dist/lib/types/error-details.aliases.mjs.map +1 -1
- package/dist/lib/types/format-asset-slots.mjs +0 -6
- package/dist/lib/types/forward-compat-error-codes.mjs +0 -6
- package/dist/lib/types/forward-compat-error-codes.mjs.map +1 -1
- package/dist/lib/types/index.mjs +0 -6
- package/dist/lib/types/index.mjs.map +1 -1
- package/dist/lib/types/inline-enums.aliases.mjs +0 -6
- package/dist/lib/types/inline-enums.aliases.mjs.map +1 -1
- package/dist/lib/types/inline-enums.generated.mjs +0 -6
- package/dist/lib/types/inline-enums.generated.mjs.map +1 -1
- package/dist/lib/types/manifest.generated.mjs +0 -6
- package/dist/lib/types/manifest.generated.mjs.map +1 -1
- package/dist/lib/types/schemas.generated.mjs +0 -6
- package/dist/lib/types/schemas.generated.mjs.map +1 -1
- package/dist/lib/types/server-payload-aliases.mjs +0 -6
- package/dist/lib/types/server-payload.mjs +0 -6
- package/dist/lib/types/sync-rows.mjs +0 -6
- package/dist/lib/types/tools.generated.mjs +0 -6
- package/dist/lib/types/v2-5/index.mjs +0 -6
- package/dist/lib/types/v2-5/index.mjs.map +1 -1
- package/dist/lib/types/v2-5/tools.generated.mjs +0 -6
- package/dist/lib/types/v3-1-beta/index.mjs +0 -6
- package/dist/lib/types/v3-1-beta/index.mjs.map +1 -1
- package/dist/lib/types/v3-1-beta/tools.generated.mjs +0 -6
- package/dist/lib/types/wellknown-schemas.generated.mjs +0 -6
- package/dist/lib/types/wellknown-schemas.generated.mjs.map +1 -1
- package/dist/lib/upstream-recorder/constants.mjs +0 -6
- package/dist/lib/upstream-recorder/constants.mjs.map +1 -1
- package/dist/lib/upstream-recorder/index.mjs +0 -6
- package/dist/lib/upstream-recorder/index.mjs.map +1 -1
- package/dist/lib/upstream-recorder/recorder.mjs +0 -6
- package/dist/lib/upstream-recorder/recorder.mjs.map +1 -1
- package/dist/lib/upstream-recorder/types.mjs +0 -6
- package/dist/lib/upstream-recorder/types.mjs.map +1 -1
- package/dist/lib/utils/a2a-artifacts.mjs +0 -6
- package/dist/lib/utils/a2a-artifacts.mjs.map +1 -1
- package/dist/lib/utils/a2a-discovery.mjs +0 -6
- package/dist/lib/utils/a2a-discovery.mjs.map +1 -1
- package/dist/lib/utils/activation-key-builders.mjs +0 -6
- package/dist/lib/utils/activation-key-builders.mjs.map +1 -1
- package/dist/lib/utils/adcp-version-config.mjs +0 -6
- package/dist/lib/utils/adcp-version-config.mjs.map +1 -1
- package/dist/lib/utils/asset-builders.mjs +0 -6
- package/dist/lib/utils/asset-builders.mjs.map +1 -1
- package/dist/lib/utils/build-creative-return-builders.mjs +0 -6
- package/dist/lib/utils/build-creative-return-builders.mjs.map +1 -1
- package/dist/lib/utils/buyer-retry-policy.mjs +0 -6
- package/dist/lib/utils/buyer-retry-policy.mjs.map +1 -1
- package/dist/lib/utils/capabilities.mjs +0 -6
- package/dist/lib/utils/capabilities.mjs.map +1 -1
- package/dist/lib/utils/capability-rollups.mjs +0 -6
- package/dist/lib/utils/capability-rollups.mjs.map +1 -1
- package/dist/lib/utils/creative-adapter.mjs +0 -6
- package/dist/lib/utils/creative-adapter.mjs.map +1 -1
- package/dist/lib/utils/creative-delivery.mjs +0 -6
- package/dist/lib/utils/creative-delivery.mjs.map +1 -1
- package/dist/lib/utils/deprecation.mjs +0 -6
- package/dist/lib/utils/deprecation.mjs.map +1 -1
- package/dist/lib/utils/envelope-status-compat.mjs +0 -6
- package/dist/lib/utils/envelope-status-compat.mjs.map +1 -1
- package/dist/lib/utils/error-extraction.mjs +0 -6
- package/dist/lib/utils/error-extraction.mjs.map +1 -1
- package/dist/lib/utils/extract-result.mjs +0 -6
- package/dist/lib/utils/extract-result.mjs.map +1 -1
- package/dist/lib/utils/format-asset-slot-builders.mjs +0 -6
- package/dist/lib/utils/format-asset-slot-builders.mjs.map +1 -1
- package/dist/lib/utils/format-assets.mjs +0 -6
- package/dist/lib/utils/format-assets.mjs.map +1 -1
- package/dist/lib/utils/format-render-builders.mjs +0 -6
- package/dist/lib/utils/format-render-builders.mjs.map +1 -1
- package/dist/lib/utils/format-renders.mjs +0 -6
- package/dist/lib/utils/format-renders.mjs.map +1 -1
- package/dist/lib/utils/get-products-cache-scope.mjs +0 -6
- package/dist/lib/utils/get-products-cache-scope.mjs.map +1 -1
- package/dist/lib/utils/glob.mjs +0 -6
- package/dist/lib/utils/glob.mjs.map +1 -1
- package/dist/lib/utils/global-async-local-storage.mjs +0 -6
- package/dist/lib/utils/global-async-local-storage.mjs.map +1 -1
- package/dist/lib/utils/idempotency.mjs +0 -6
- package/dist/lib/utils/idempotency.mjs.map +1 -1
- package/dist/lib/utils/index.mjs +0 -6
- package/dist/lib/utils/index.mjs.map +1 -1
- package/dist/lib/utils/jcs.mjs +0 -6
- package/dist/lib/utils/jcs.mjs.map +1 -1
- package/dist/lib/utils/json-depth.mjs +0 -6
- package/dist/lib/utils/json-depth.mjs.map +1 -1
- package/dist/lib/utils/logger.mjs +0 -6
- package/dist/lib/utils/logger.mjs.map +1 -1
- package/dist/lib/utils/media-buy-delivery-notification-builders.mjs +0 -6
- package/dist/lib/utils/media-buy-delivery-notification-builders.mjs.map +1 -1
- package/dist/lib/utils/media-buy-status.mjs +0 -6
- package/dist/lib/utils/media-buy-status.mjs.map +1 -1
- package/dist/lib/utils/pagination.mjs +0 -6
- package/dist/lib/utils/pagination.mjs.map +1 -1
- package/dist/lib/utils/preview-creative-builders.mjs +0 -6
- package/dist/lib/utils/preview-creative-builders.mjs.map +1 -1
- package/dist/lib/utils/preview-normalizer.mjs +0 -6
- package/dist/lib/utils/preview-normalizer.mjs.map +1 -1
- package/dist/lib/utils/preview-utils.mjs +0 -6
- package/dist/lib/utils/preview-utils.mjs.map +1 -1
- package/dist/lib/utils/pricing-adapter.mjs +0 -6
- package/dist/lib/utils/pricing-adapter.mjs.map +1 -1
- package/dist/lib/utils/probe-policy.mjs +0 -6
- package/dist/lib/utils/probe-policy.mjs.map +1 -1
- package/dist/lib/utils/protocol-detection.mjs +0 -6
- package/dist/lib/utils/protocol-detection.mjs.map +1 -1
- package/dist/lib/utils/redact-secrets.mjs +0 -6
- package/dist/lib/utils/redact-secrets.mjs.map +1 -1
- package/dist/lib/utils/redis-default-prefix-warn.mjs +0 -6
- package/dist/lib/utils/redis-default-prefix-warn.mjs.map +1 -1
- package/dist/lib/utils/render-builders.mjs +0 -6
- package/dist/lib/utils/render-builders.mjs.map +1 -1
- package/dist/lib/utils/request-normalizer.mjs +0 -6
- package/dist/lib/utils/request-normalizer.mjs.map +1 -1
- package/dist/lib/utils/response-schemas.mjs +0 -6
- package/dist/lib/utils/response-schemas.mjs.map +1 -1
- package/dist/lib/utils/response-unwrapper.mjs +0 -6
- package/dist/lib/utils/response-unwrapper.mjs.map +1 -1
- package/dist/lib/utils/retry.mjs +0 -6
- package/dist/lib/utils/retry.mjs.map +1 -1
- package/dist/lib/utils/signal-discovery-helpers.mjs +0 -6
- package/dist/lib/utils/signal-discovery-helpers.mjs.map +1 -1
- package/dist/lib/utils/signal-id-builders.mjs +0 -6
- package/dist/lib/utils/signal-id-builders.mjs.map +1 -1
- package/dist/lib/utils/sync-creatives-adapter.mjs +0 -6
- package/dist/lib/utils/sync-creatives-adapter.mjs.map +1 -1
- package/dist/lib/utils/task-state.mjs +0 -6
- package/dist/lib/utils/task-state.mjs.map +1 -1
- package/dist/lib/utils/tool-request-schemas.mjs +0 -6
- package/dist/lib/utils/tool-request-schemas.mjs.map +1 -1
- package/dist/lib/utils/typeGuards.mjs +0 -6
- package/dist/lib/utils/typeGuards.mjs.map +1 -1
- package/dist/lib/utils/union-errors.mjs +0 -6
- package/dist/lib/utils/union-errors.mjs.map +1 -1
- package/dist/lib/utils/validate-user-agent.mjs +0 -6
- package/dist/lib/utils/validate-user-agent.mjs.map +1 -1
- package/dist/lib/v2/format-schema/fetch.mjs +0 -6
- package/dist/lib/v2/format-schema/fetch.mjs.map +1 -1
- package/dist/lib/v2/format-schema/index.mjs +0 -6
- package/dist/lib/v2/format-schema/index.mjs.map +1 -1
- package/dist/lib/v2/format-schema/regex-safety.mjs +0 -6
- package/dist/lib/v2/format-schema/regex-safety.mjs.map +1 -1
- package/dist/lib/v2/format-schema/resolver.mjs +7 -8
- package/dist/lib/v2/format-schema/resolver.mjs.map +1 -1
- package/dist/lib/v2/format-schema/sandbox-refs.mjs +0 -6
- package/dist/lib/v2/format-schema/sandbox-refs.mjs.map +1 -1
- package/dist/lib/v2/projection/augment-response.mjs +0 -6
- package/dist/lib/v2/projection/augment-response.mjs.map +1 -1
- package/dist/lib/v2/projection/builders.mjs +0 -6
- package/dist/lib/v2/projection/builders.mjs.map +1 -1
- package/dist/lib/v2/projection/cache-versions.mjs +0 -6
- package/dist/lib/v2/projection/cache-versions.mjs.map +1 -1
- package/dist/lib/v2/projection/canonical-properties.mjs +5 -6
- package/dist/lib/v2/projection/canonical-properties.mjs.map +1 -1
- package/dist/lib/v2/projection/catalog.mjs +5 -6
- package/dist/lib/v2/projection/catalog.mjs.map +1 -1
- package/dist/lib/v2/projection/constants.mjs +0 -6
- package/dist/lib/v2/projection/constants.mjs.map +1 -1
- package/dist/lib/v2/projection/index.mjs +0 -6
- package/dist/lib/v2/projection/index.mjs.map +1 -1
- package/dist/lib/v2/projection/registry.mjs +5 -6
- package/dist/lib/v2/projection/registry.mjs.map +1 -1
- package/dist/lib/v2/projection/types.mjs +0 -6
- package/dist/lib/v2/projection/v1-to-v2.mjs +0 -6
- package/dist/lib/v2/projection/v1-to-v2.mjs.map +1 -1
- package/dist/lib/v2/projection/v2-to-v1.mjs +0 -6
- package/dist/lib/v2/projection/v2-to-v1.mjs.map +1 -1
- package/dist/lib/v2/projection/write-side.mjs +0 -6
- package/dist/lib/v2/projection/write-side.mjs.map +1 -1
- package/dist/lib/v2/publisher-catalog/formats.mjs +0 -6
- package/dist/lib/v2/publisher-catalog/formats.mjs.map +1 -1
- package/dist/lib/v2/publisher-catalog/index.mjs +0 -6
- package/dist/lib/v2/publisher-catalog/index.mjs.map +1 -1
- package/dist/lib/validation/client-hooks.mjs +0 -6
- package/dist/lib/validation/client-hooks.mjs.map +1 -1
- package/dist/lib/validation/hints.mjs +0 -6
- package/dist/lib/validation/hints.mjs.map +1 -1
- package/dist/lib/validation/index.mjs +0 -6
- package/dist/lib/validation/index.mjs.map +1 -1
- package/dist/lib/validation/schema-errors.mjs +0 -6
- package/dist/lib/validation/schema-errors.mjs.map +1 -1
- package/dist/lib/validation/schema-loader.mjs +5 -6
- package/dist/lib/validation/schema-loader.mjs.map +1 -1
- package/dist/lib/validation/schema-validator.mjs +0 -6
- package/dist/lib/validation/schema-validator.mjs.map +1 -1
- package/dist/lib/validation/sync-creatives.mjs +0 -6
- package/dist/lib/validation/sync-creatives.mjs.map +1 -1
- package/dist/lib/version.d.mts +3 -3
- package/dist/lib/version.d.ts +3 -3
- package/dist/lib/version.js +3 -3
- package/dist/lib/version.js.map +1 -1
- package/dist/lib/version.mjs +3 -9
- package/dist/lib/version.mjs.map +1 -1
- package/dist/lib/webhooks/index.mjs +0 -6
- package/dist/lib/webhooks/index.mjs.map +1 -1
- package/dist/lib/wholesale-feed-sync/index.mjs +0 -6
- package/dist/lib/wholesale-feed-sync/index.mjs.map +1 -1
- package/dist/lib/wholesale-feed-sync/sync.mjs +0 -6
- package/dist/lib/wholesale-feed-sync/sync.mjs.map +1 -1
- package/dist/lib/wholesale-feed-sync/types.mjs +0 -6
- package/dist/lib/wholesale-feed-sync/webhook-notification.mjs +0 -6
- package/dist/lib/wholesale-feed-sync/webhook-notification.mjs.map +1 -1
- package/package.json +2 -1
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
import { AdcpError } from "./async-outcome.mjs";
|
|
8
2
|
import {
|
|
9
3
|
PackageNotFoundError,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/lib/server/decisioning/index.ts"],"sourcesContent":["/**\n * DecisioningPlatform v1.0 — preview surface for the v6.0 architecture.\n *\n * Status: PREVIEW. Types only; not yet wired into the framework. Subject\n * to change before 6.0 ships. Don't build production adapters against this\n * yet — the framework still routes through the v5.x handler-style API.\n *\n * Design proposal: `.context/proposals/specialism-platform-interfaces-v3.md`\n *\n * @packageDocumentation\n */\n\n// Adopter-facing structured-error primitive.\n//\n// `AdcpError` is the canonical throwable for structured rejection. Specialism\n// methods return plain `T` for success or `throw new AdcpError(...)` to project\n// to the wire `adcp_error` envelope.\n//\n// HITL is expressed in the type system via the dual-method shape on each\n// spec-HITL tool (`xxx` for sync, `xxxTask` for HITL). No adopter-facing\n// task primitives — the framework owns task lifecycle and dispatches the\n// `*Task` method in the background.\nexport { type AdcpStructuredError, type ErrorCode, AdcpError } from './async-outcome';\nexport type { TaskHandoffOptions } from './async-outcome';\nexport type { ServerPayload } from '../../types/server-payload';\n\n// Typed `AdcpError` subclasses — adopter convenience for the highest-traffic\n// error codes. Each class encodes the canonical code/recovery/field shape.\n// LLM-generated platforms get autocomplete on the import; humans skim the\n// list to find the right class. See `errors-typed.ts`.\nexport {\n PackageNotFoundError,\n MediaBuyNotFoundError,\n ProductNotFoundError,\n CreativeNotFoundError,\n ProductUnavailableError,\n CreativeRejectedError,\n BudgetTooLowError,\n BudgetExhaustedError,\n IdempotencyConflictError,\n InvalidRequestError,\n InvalidStateError,\n BackwardsTimeRangeError,\n AuthMissingError,\n AuthInvalidError,\n AuthRequiredError,\n PermissionDeniedError,\n RateLimitedError,\n ServiceUnavailableError,\n UnsupportedFeatureError,\n ComplianceUnsatisfiedError,\n GovernanceDeniedError,\n PolicyViolationError,\n} from './errors-typed';\n\n// Cursor pagination\nexport type { CursorPage, CursorRequest } from './pagination';\n\n// Status-change event bus — adopter-facing primitive for spec-native\n// lifecycle channels (media_buy / creative / audience / signal / proposal /\n// plan / rights_grant / delivery_report). Module-level so adopters can\n// publish from webhook handlers, crons, in-process workers without holding\n// a server reference.\nexport {\n publishStatusChange,\n setStatusChangeBus,\n getStatusChangeBus,\n createInMemoryStatusChangeBus,\n type StatusChange,\n type StatusChangeBus,\n type StatusChangeResourceType,\n type StatusChangeListener,\n type PublishStatusChangeOpts,\n} from './status-changes';\n\n// Capabilities (single source of truth for get_adcp_capabilities)\nexport type {\n DecisioningCapabilities,\n ComplianceTestingCapabilities,\n CreativeAgentRef,\n TargetingCapabilities,\n TargetingPostalAreaSupport,\n ReportingCapabilities,\n} from './capabilities';\nexport { normalizePostalAreaSupport, normalizeTargetingCapabilities } from './capabilities';\n\n// Account model\nexport type {\n Account,\n AuthPrincipal,\n AccountStore,\n AccountFilter,\n ListAccountsPayload,\n SyncAccountsPayload,\n SyncAccountsSuccessPayload,\n SyncAccountsRow,\n SyncAccountsResultRow,\n SyncGovernancePayload,\n SyncGovernanceSuccessPayload,\n SyncGovernanceRow,\n ReportUsagePayload,\n GetAccountFinancialsPayload,\n GetAccountFinancialsSuccessPayload,\n ListAccountsHandlerResult,\n SyncAccountsHandlerResult,\n SyncGovernanceHandlerResult,\n ReportUsageHandlerResult,\n GetAccountFinancialsHandlerResult,\n AdcpAccountStatus,\n ResolveContext,\n AccountToolContext,\n ResolvedAuthInfo,\n} from './account';\n\nexport { AccountNotFoundError, refAccountId } from './account';\n\n// Multi-tenant AccountStore builder. Bakes in the two-path resolution\n// (operator-routed + auth-derived) and the per-entry tenant-isolation gate\n// that adopters historically had to hand-write — and silently fail to\n// hand-write — on `accounts.upsert` / `accounts.syncGovernance`.\nexport { createTenantStore, narrowAccountRef } from './tenant-store';\nexport type { TenantStoreConfig } from './tenant-store';\n\n// Buyer-agent identity surface — Phase 1 of #1269. Durable commercial\n// relationship records keyed off the request credential. Factory-pattern\n// registry (signing-only / bearer-only / mixed) encodes the implementer\n// posture at construction; framework calls `BuyerAgentRegistry.resolve`\n// once per request before `accounts.resolve`. Phase 1 ships the shape and\n// resolution; framework-level billing-capability enforcement and the\n// AdCP-3.1 error-code emission land in Phase 2 (#1292).\nexport type {\n BuyerAgent,\n BuyerAgentBillingMode,\n BuyerAgentStatus,\n BuyerAgentRegistry as BuyerAgentRegistryProtocol,\n BuyerAgentResolveInput,\n BuyerAgentCacheOptions,\n CachedBuyerAgentRegistry,\n AdcpCredential,\n ResolveBuyerAgentByAgentUrl,\n ResolveBuyerAgentByCredential,\n} from './buyer-agent';\nexport { BuyerAgentRegistry } from './buyer-agent';\n\n// Native status mapping\nexport type { StatusMappers, AdcpMediaBuyStatus, AdcpCreativeStatus, AdcpPlanStatus } from './status-mappers';\nexport { identityStatusMappers } from './status-mappers';\n\n// Request context (state + resolve)\nexport type {\n RequestContext,\n WorkflowStateReader,\n ResourceResolver,\n WorkflowObjectType,\n WorkflowStep,\n Proposal,\n GovernanceContextJWS,\n} from './context';\n\n// Top-level platform + compile-time capability enforcement\nexport type { DecisioningPlatform, RequiredPlatformsFor, RequiredCapabilitiesFor } from './platform';\n\n// Method-level composition (closes #1314) — wrap individual platform methods\n// with `before` / `after` hooks for short-circuit + enrichment patterns.\nexport { composeMethod } from './compose';\nexport type { ComposeHooks, ComposeShortCircuit } from './compose';\n\n// `accounts.resolve` security presets (closes #1339) — canonical post-resolve\n// guards that standardize the multi-tenant authorization pattern instead of\n// every adopter rolling their own.\nexport { requireAccountMatch, requireAdvertiserMatch, requireOrgScope } from './resolve-presets';\nexport type { ResolveAccountHooks, ResolveGuardOptions } from './resolve-presets';\n\n// Specialism interfaces (v1.0)\nexport type {\n CreativeBuilderPlatform,\n BuildCreativeReturn,\n BuildCreativePayload,\n BuildCreativeMultiPayload,\n PreviewCreativePayload as CreativePreviewCreativePayload,\n ListCreativeFormatsPayload as CreativeListCreativeFormatsPayload,\n // Deprecated aliases — kept for one-release source compat. Both\n // resolve to CreativeBuilderPlatform; see specialisms/creative.ts.\n CreativeTemplatePlatform,\n CreativeGenerativePlatform,\n RefinementMessage,\n SyncCreativesRow,\n} from './specialisms/creative';\n\nexport type {\n CreativeAdServerPlatform,\n BuildCreativeReturn as CreativeAdServerBuildCreativeReturn,\n BuildCreativePayload as CreativeAdServerBuildCreativePayload,\n BuildCreativeMultiPayload as CreativeAdServerBuildCreativeMultiPayload,\n PreviewCreativePayload as CreativeAdServerPreviewCreativePayload,\n ListCreativeFormatsPayload as CreativeAdServerListCreativeFormatsPayload,\n ListCreativesPayload as CreativeAdServerListCreativesPayload,\n GetCreativeDeliveryPayload as CreativeAdServerGetCreativeDeliveryPayload,\n} from './specialisms/creative-ad-server';\n\nexport type {\n CampaignGovernancePlatform,\n CheckGovernancePayload,\n SyncPlansPayload,\n ReportPlanOutcomePayload,\n GetPlanAuditLogsPayload,\n} from './specialisms/campaign-governance';\n\nexport type {\n ContentStandardsPlatform,\n ListContentStandardsPayload,\n GetContentStandardsPayload,\n CreateContentStandardsPayload,\n UpdateContentStandardsPayload,\n CalibrateContentPayload,\n ValidateContentDeliveryPayload,\n GetMediaBuyArtifactsPayload,\n GetCreativeFeaturesPayload,\n} from './specialisms/content-standards';\n\nexport type {\n PropertyListsPlatform,\n CollectionListsPlatform,\n CreatePropertyListPayload,\n UpdatePropertyListPayload,\n GetPropertyListPayload,\n ListPropertyListsPayload,\n DeletePropertyListPayload,\n CreateCollectionListPayload,\n UpdateCollectionListPayload,\n GetCollectionListPayload,\n ListCollectionListsPayload,\n DeleteCollectionListPayload,\n} from './specialisms/lists';\n\nexport type {\n SalesPlatform,\n SalesCorePlatform,\n SalesIngestionPlatform,\n GetProductsPayload,\n GetProductsHandlerResult,\n CreateMediaBuyPayload,\n CreateMediaBuyHandlerResult,\n UpdateMediaBuyPayload,\n GetMediaBuyDeliveryPayload,\n GetMediaBuysPayload,\n ProvidePerformanceFeedbackPayload,\n ListCreativeFormatsPayload,\n ListCreativesPayload,\n SyncCreativesPayload,\n SyncCreativesHandlerResult,\n SyncCatalogsPayload,\n LogEventPayload,\n SyncEventSourcesPayload,\n} from './specialisms/sales';\n\nexport type {\n AudiencePlatform,\n Audience,\n SyncAudiencesPayload,\n SyncAudiencesRow,\n SyncAudiencesHandlerResult,\n AudienceStatus,\n} from './specialisms/audiences';\n\nexport type {\n SignalsPlatform,\n GetSignalsPayload,\n GetSignalsHandlerResult,\n ActivateSignalPayload,\n} from './specialisms/signals';\n\nexport type {\n SponsoredIntelligencePlatform,\n SIGetOfferingPayload,\n SIInitiateSessionPayload,\n SISendMessagePayload,\n SITerminateSessionPayload,\n} from './specialisms/sponsored-intelligence';\n\nexport type {\n BrandRightsPlatform,\n GetBrandIdentityPayload,\n GetRightsPayload,\n AcquireRightsAcquiredPayload,\n AcquireRightsPendingApprovalPayload,\n AcquireRightsRejectedPayload,\n AcquireRightsPayload,\n UpdateRightsPayload,\n CreativeApprovedPayload,\n CreativeRejectedPayload,\n CreativePendingReviewPayload,\n CreativeApprovalPayload,\n} from './specialisms/brand-rights';\n\n// Brand-rights wire types — re-exported from `@adcp/sdk/server/decisioning`\n// because brand-rights is the only specialism whose wire types live in\n// `core.generated` (not `tools.generated`), and the public `@adcp/sdk/types`\n// barrel doesn't surface them. Adopters typing their own helper functions\n// import these from here, NOT from the deep `core.generated` path.\nexport type {\n GetBrandIdentityRequest,\n GetBrandIdentitySuccess,\n GetRightsRequest,\n GetRightsSuccess,\n AcquireRightsRequest,\n AcquireRightsAcquired,\n AcquireRightsPendingApproval,\n AcquireRightsRejected,\n AcquireRightsError,\n RightUse,\n RightType,\n RightsConstraint,\n RightsTerms,\n RightsPricingOption,\n GenerationCredential,\n} from '../../types/core.generated';\n\n// Runtime (v6.0 alpha) — preview surface for adopters spiking against the\n// new shape. Subject to change before 6.0 GA.\nexport {\n createAdcpServerFromPlatform,\n getAllAdcpMigrations,\n type CreateAdcpServerFromPlatformOptions,\n type RequiredOptsFor,\n type DecisioningAdcpServer,\n type DecisioningObservabilityHooks,\n} from './runtime/from-platform';\nexport { PlatformConfigError, validatePlatform } from './runtime/validate-platform';\nexport {\n createInMemoryTaskRegistry,\n type TaskRegistry,\n type TaskRecord,\n type TaskStatus,\n} from './runtime/task-registry';\nexport {\n createPostgresTaskRegistry,\n getDecisioningTaskRegistryMigration,\n type CreatePostgresTaskRegistryOptions,\n type PgQueryable,\n} from './runtime/postgres-task-registry';\n\n// Multi-tenant deployment helper — wraps createAdcpServerFromPlatform with\n// per-tenant config, health states (healthy/unverified/disabled), and JWKS\n// validation. Composes with the existing serve() host-routing surface.\nexport {\n createTenantRegistry,\n createDefaultJwksValidator,\n createSelfSignedTenantKey,\n createNoopJwksValidator,\n type TenantRegistry,\n type TenantConfig,\n type TenantSigningKey,\n type TenantStatus,\n type TenantHealth,\n type TenantRegistryOptions,\n type JwksValidator,\n type JwksValidationResult,\n} from './tenant-registry';\n\n// Manifest helpers — typed accessors for creative_manifest.assets values.\n// Save adopters from writing the same null-check + discriminator-check\n// boilerplate per call.\nexport { getAsset, requireAsset } from './manifest-helpers';\n\n// List helpers — wrap row arrays + pagination into the heavier wire shapes\n// (today: list_creatives, which carries query_summary alongside the rows).\nexport { buildListCreativesResponse, type BuildListCreativesResponseOpts } from './list-helpers';\n\n// Start-time helper — normalize the wire `start_time` union into a Date,\n// with platform-aware ASAP lead-time injection.\nexport { resolveStartTime, type ResolveStartTimeOptions } from './start-time';\n\n// Admin Express router for ops visibility into the TenantRegistry.\n// Mount on a separate port/path with operator auth.\nexport {\n createTenantAdminRouter,\n createTenantAdminHandlers,\n mountTenantAdmin,\n type TenantAdminHandlers,\n type RouterLike,\n} from './admin-router';\n\n// Adopter helpers — batchPoll, validationError, upstreamError, RequestShape.\n// All opt-in convenience; nothing in the framework calls these internally.\nexport { batchPoll, validationError, upstreamError } from './helpers';\nexport type { RequestShape } from './helpers';\n\n// Platform identity helpers — fix TypeScript's contextual-typing gap when\n// building a DecisioningPlatform (or sub-interface) as an object literal.\n// Without these, `createAdcpServerFromPlatform({ sales: { syncEventSources:\n// async (req, ctx) => {...} } })` gives `req: unknown` because the generic\n// `P extends DecisioningPlatform<any,any>` is inferred, not declared.\n// Wrapping the sub-object with e.g. `defineSalesPlatform<MyMeta>({...})`\n// forces the concrete type annotation TypeScript needs. The helpers are\n// pure identity functions — zero runtime cost.\nexport {\n definePlatform,\n defineSalesPlatform,\n defineSalesCorePlatform,\n defineSalesIngestionPlatform,\n defineAudiencePlatform,\n defineSignalsPlatform,\n defineSponsoredIntelligencePlatform,\n defineCreativeBuilderPlatform,\n defineCreativeAdServerPlatform,\n defineCampaignGovernancePlatform,\n defineContentStandardsPlatform,\n definePropertyListsPlatform,\n defineCollectionListsPlatform,\n defineBrandRightsPlatform,\n definePlatformWithCompliance,\n} from './platform-helpers';\n\n// ProposalManager — primitives for the two-platform composition (port of\n// adcp-client-python PRs #504 + #550). Splits proposal assembly from\n// media-buy execution; either side can be mock-backed independently.\n// Framework dispatch wiring lands in a follow-up release.\nexport type {\n ProposalManager,\n ProposalCapabilities,\n ProposalSalesSpecialism,\n Recipe,\n CapabilityOverlap,\n FinalizeProposalRequest,\n FinalizeProposalSuccess,\n ProposalState,\n ProposalRecord,\n ProposalStore,\n InMemoryProposalStoreOptions,\n MockProposalManagerOptions,\n} from './proposal';\nexport {\n validateProposalCapabilities,\n InMemoryProposalStore,\n MockProposalManager,\n enforceProposalExpiry,\n validateCapabilityOverlap,\n validateOverlapSubsetOfWire,\n detectFinalizeAction,\n setProposalLifecycleLogger,\n maybeInterceptFinalize,\n maybePersistDraftAfterGetProducts,\n maybeReserveProposalForCreateMediaBuy,\n finalizeProposalConsumption,\n releaseProposalReservation,\n maybeHydrateRecipesForMediaBuyId,\n} from './proposal';\nexport type { FinalizeActionRef, ProposalLifecycleLogger, FinalizeInterceptResult, ReservedProposal } from './proposal';\n\n// Wire-shape assembly helpers — emit correct Product / PricingOption /\n// package shapes from intent-shaped input. Reduces 30+ lines of wire\n// boilerplate per resource. Used in slim skill examples so LLMs scaffold\n// correct shapes from first attempt.\nexport { buildProduct, buildPricingOption, buildPackage } from './assembly-helpers';\nexport type { BuildProductInput, BuildPricingOptionInput, BuildPackageInput } from './assembly-helpers';\n"],"mappings":";;;;;;AAsBA,SAAmD,iBAAiB;AAQpE;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAUP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OAMK;AAWP,SAAS,4BAA4B,sCAAsC;AA8B3E,SAAS,sBAAsB,oBAAoB;AAMnD,SAAS,mBAAmB,wBAAwB;AAsBpD,SAAS,0BAA0B;AAInC,SAAS,6BAA6B;AAkBtC,SAAS,qBAAqB;AAM9B,SAAS,qBAAqB,wBAAwB,uBAAuB;AAsJ7E;AAAA,EACE;AAAA,EACA;AAAA,OAKK;AACP,SAAS,qBAAqB,wBAAwB;AACtD;AAAA,EACE;AAAA,OAIK;AACP;AAAA,EACE;AAAA,EACA;AAAA,OAGK;AAKP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OASK;AAKP,SAAS,UAAU,oBAAoB;AAIvC,SAAS,kCAAuE;AAIhF,SAAS,wBAAsD;AAI/D;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,OAGK;AAIP,SAAS,WAAW,iBAAiB,qBAAqB;AAW1D;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAoBP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAOP,SAAS,cAAc,oBAAoB,oBAAoB;","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../../../src/lib/server/decisioning/index.ts"],"sourcesContent":["/**\n * DecisioningPlatform v1.0 — preview surface for the v6.0 architecture.\n *\n * Status: PREVIEW. Types only; not yet wired into the framework. Subject\n * to change before 6.0 ships. Don't build production adapters against this\n * yet — the framework still routes through the v5.x handler-style API.\n *\n * Design proposal: `.context/proposals/specialism-platform-interfaces-v3.md`\n *\n * @packageDocumentation\n */\n\n// Adopter-facing structured-error primitive.\n//\n// `AdcpError` is the canonical throwable for structured rejection. Specialism\n// methods return plain `T` for success or `throw new AdcpError(...)` to project\n// to the wire `adcp_error` envelope.\n//\n// HITL is expressed in the type system via the dual-method shape on each\n// spec-HITL tool (`xxx` for sync, `xxxTask` for HITL). No adopter-facing\n// task primitives — the framework owns task lifecycle and dispatches the\n// `*Task` method in the background.\nexport { type AdcpStructuredError, type ErrorCode, AdcpError } from './async-outcome';\nexport type { TaskHandoffOptions } from './async-outcome';\nexport type { ServerPayload } from '../../types/server-payload';\n\n// Typed `AdcpError` subclasses — adopter convenience for the highest-traffic\n// error codes. Each class encodes the canonical code/recovery/field shape.\n// LLM-generated platforms get autocomplete on the import; humans skim the\n// list to find the right class. See `errors-typed.ts`.\nexport {\n PackageNotFoundError,\n MediaBuyNotFoundError,\n ProductNotFoundError,\n CreativeNotFoundError,\n ProductUnavailableError,\n CreativeRejectedError,\n BudgetTooLowError,\n BudgetExhaustedError,\n IdempotencyConflictError,\n InvalidRequestError,\n InvalidStateError,\n BackwardsTimeRangeError,\n AuthMissingError,\n AuthInvalidError,\n AuthRequiredError,\n PermissionDeniedError,\n RateLimitedError,\n ServiceUnavailableError,\n UnsupportedFeatureError,\n ComplianceUnsatisfiedError,\n GovernanceDeniedError,\n PolicyViolationError,\n} from './errors-typed';\n\n// Cursor pagination\nexport type { CursorPage, CursorRequest } from './pagination';\n\n// Status-change event bus — adopter-facing primitive for spec-native\n// lifecycle channels (media_buy / creative / audience / signal / proposal /\n// plan / rights_grant / delivery_report). Module-level so adopters can\n// publish from webhook handlers, crons, in-process workers without holding\n// a server reference.\nexport {\n publishStatusChange,\n setStatusChangeBus,\n getStatusChangeBus,\n createInMemoryStatusChangeBus,\n type StatusChange,\n type StatusChangeBus,\n type StatusChangeResourceType,\n type StatusChangeListener,\n type PublishStatusChangeOpts,\n} from './status-changes';\n\n// Capabilities (single source of truth for get_adcp_capabilities)\nexport type {\n DecisioningCapabilities,\n ComplianceTestingCapabilities,\n CreativeAgentRef,\n TargetingCapabilities,\n TargetingPostalAreaSupport,\n ReportingCapabilities,\n} from './capabilities';\nexport { normalizePostalAreaSupport, normalizeTargetingCapabilities } from './capabilities';\n\n// Account model\nexport type {\n Account,\n AuthPrincipal,\n AccountStore,\n AccountFilter,\n ListAccountsPayload,\n SyncAccountsPayload,\n SyncAccountsSuccessPayload,\n SyncAccountsRow,\n SyncAccountsResultRow,\n SyncGovernancePayload,\n SyncGovernanceSuccessPayload,\n SyncGovernanceRow,\n ReportUsagePayload,\n GetAccountFinancialsPayload,\n GetAccountFinancialsSuccessPayload,\n ListAccountsHandlerResult,\n SyncAccountsHandlerResult,\n SyncGovernanceHandlerResult,\n ReportUsageHandlerResult,\n GetAccountFinancialsHandlerResult,\n AdcpAccountStatus,\n ResolveContext,\n AccountToolContext,\n ResolvedAuthInfo,\n} from './account';\n\nexport { AccountNotFoundError, refAccountId } from './account';\n\n// Multi-tenant AccountStore builder. Bakes in the two-path resolution\n// (operator-routed + auth-derived) and the per-entry tenant-isolation gate\n// that adopters historically had to hand-write — and silently fail to\n// hand-write — on `accounts.upsert` / `accounts.syncGovernance`.\nexport { createTenantStore, narrowAccountRef } from './tenant-store';\nexport type { TenantStoreConfig } from './tenant-store';\n\n// Buyer-agent identity surface — Phase 1 of #1269. Durable commercial\n// relationship records keyed off the request credential. Factory-pattern\n// registry (signing-only / bearer-only / mixed) encodes the implementer\n// posture at construction; framework calls `BuyerAgentRegistry.resolve`\n// once per request before `accounts.resolve`. Phase 1 ships the shape and\n// resolution; framework-level billing-capability enforcement and the\n// AdCP-3.1 error-code emission land in Phase 2 (#1292).\nexport type {\n BuyerAgent,\n BuyerAgentBillingMode,\n BuyerAgentStatus,\n BuyerAgentRegistry as BuyerAgentRegistryProtocol,\n BuyerAgentResolveInput,\n BuyerAgentCacheOptions,\n CachedBuyerAgentRegistry,\n AdcpCredential,\n ResolveBuyerAgentByAgentUrl,\n ResolveBuyerAgentByCredential,\n} from './buyer-agent';\nexport { BuyerAgentRegistry } from './buyer-agent';\n\n// Native status mapping\nexport type { StatusMappers, AdcpMediaBuyStatus, AdcpCreativeStatus, AdcpPlanStatus } from './status-mappers';\nexport { identityStatusMappers } from './status-mappers';\n\n// Request context (state + resolve)\nexport type {\n RequestContext,\n WorkflowStateReader,\n ResourceResolver,\n WorkflowObjectType,\n WorkflowStep,\n Proposal,\n GovernanceContextJWS,\n} from './context';\n\n// Top-level platform + compile-time capability enforcement\nexport type { DecisioningPlatform, RequiredPlatformsFor, RequiredCapabilitiesFor } from './platform';\n\n// Method-level composition (closes #1314) — wrap individual platform methods\n// with `before` / `after` hooks for short-circuit + enrichment patterns.\nexport { composeMethod } from './compose';\nexport type { ComposeHooks, ComposeShortCircuit } from './compose';\n\n// `accounts.resolve` security presets (closes #1339) — canonical post-resolve\n// guards that standardize the multi-tenant authorization pattern instead of\n// every adopter rolling their own.\nexport { requireAccountMatch, requireAdvertiserMatch, requireOrgScope } from './resolve-presets';\nexport type { ResolveAccountHooks, ResolveGuardOptions } from './resolve-presets';\n\n// Specialism interfaces (v1.0)\nexport type {\n CreativeBuilderPlatform,\n BuildCreativeReturn,\n BuildCreativePayload,\n BuildCreativeMultiPayload,\n PreviewCreativePayload as CreativePreviewCreativePayload,\n ListCreativeFormatsPayload as CreativeListCreativeFormatsPayload,\n // Deprecated aliases — kept for one-release source compat. Both\n // resolve to CreativeBuilderPlatform; see specialisms/creative.ts.\n CreativeTemplatePlatform,\n CreativeGenerativePlatform,\n RefinementMessage,\n SyncCreativesRow,\n} from './specialisms/creative';\n\nexport type {\n CreativeAdServerPlatform,\n BuildCreativeReturn as CreativeAdServerBuildCreativeReturn,\n BuildCreativePayload as CreativeAdServerBuildCreativePayload,\n BuildCreativeMultiPayload as CreativeAdServerBuildCreativeMultiPayload,\n PreviewCreativePayload as CreativeAdServerPreviewCreativePayload,\n ListCreativeFormatsPayload as CreativeAdServerListCreativeFormatsPayload,\n ListCreativesPayload as CreativeAdServerListCreativesPayload,\n GetCreativeDeliveryPayload as CreativeAdServerGetCreativeDeliveryPayload,\n} from './specialisms/creative-ad-server';\n\nexport type {\n CampaignGovernancePlatform,\n CheckGovernancePayload,\n SyncPlansPayload,\n ReportPlanOutcomePayload,\n GetPlanAuditLogsPayload,\n} from './specialisms/campaign-governance';\n\nexport type {\n ContentStandardsPlatform,\n ListContentStandardsPayload,\n GetContentStandardsPayload,\n CreateContentStandardsPayload,\n UpdateContentStandardsPayload,\n CalibrateContentPayload,\n ValidateContentDeliveryPayload,\n GetMediaBuyArtifactsPayload,\n GetCreativeFeaturesPayload,\n} from './specialisms/content-standards';\n\nexport type {\n PropertyListsPlatform,\n CollectionListsPlatform,\n CreatePropertyListPayload,\n UpdatePropertyListPayload,\n GetPropertyListPayload,\n ListPropertyListsPayload,\n DeletePropertyListPayload,\n CreateCollectionListPayload,\n UpdateCollectionListPayload,\n GetCollectionListPayload,\n ListCollectionListsPayload,\n DeleteCollectionListPayload,\n} from './specialisms/lists';\n\nexport type {\n SalesPlatform,\n SalesCorePlatform,\n SalesIngestionPlatform,\n GetProductsPayload,\n GetProductsHandlerResult,\n CreateMediaBuyPayload,\n CreateMediaBuyHandlerResult,\n UpdateMediaBuyPayload,\n GetMediaBuyDeliveryPayload,\n GetMediaBuysPayload,\n ProvidePerformanceFeedbackPayload,\n ListCreativeFormatsPayload,\n ListCreativesPayload,\n SyncCreativesPayload,\n SyncCreativesHandlerResult,\n SyncCatalogsPayload,\n LogEventPayload,\n SyncEventSourcesPayload,\n} from './specialisms/sales';\n\nexport type {\n AudiencePlatform,\n Audience,\n SyncAudiencesPayload,\n SyncAudiencesRow,\n SyncAudiencesHandlerResult,\n AudienceStatus,\n} from './specialisms/audiences';\n\nexport type {\n SignalsPlatform,\n GetSignalsPayload,\n GetSignalsHandlerResult,\n ActivateSignalPayload,\n} from './specialisms/signals';\n\nexport type {\n SponsoredIntelligencePlatform,\n SIGetOfferingPayload,\n SIInitiateSessionPayload,\n SISendMessagePayload,\n SITerminateSessionPayload,\n} from './specialisms/sponsored-intelligence';\n\nexport type {\n BrandRightsPlatform,\n GetBrandIdentityPayload,\n GetRightsPayload,\n AcquireRightsAcquiredPayload,\n AcquireRightsPendingApprovalPayload,\n AcquireRightsRejectedPayload,\n AcquireRightsPayload,\n UpdateRightsPayload,\n CreativeApprovedPayload,\n CreativeRejectedPayload,\n CreativePendingReviewPayload,\n CreativeApprovalPayload,\n} from './specialisms/brand-rights';\n\n// Brand-rights wire types — re-exported from `@adcp/sdk/server/decisioning`\n// because brand-rights is the only specialism whose wire types live in\n// `core.generated` (not `tools.generated`), and the public `@adcp/sdk/types`\n// barrel doesn't surface them. Adopters typing their own helper functions\n// import these from here, NOT from the deep `core.generated` path.\nexport type {\n GetBrandIdentityRequest,\n GetBrandIdentitySuccess,\n GetRightsRequest,\n GetRightsSuccess,\n AcquireRightsRequest,\n AcquireRightsAcquired,\n AcquireRightsPendingApproval,\n AcquireRightsRejected,\n AcquireRightsError,\n RightUse,\n RightType,\n RightsConstraint,\n RightsTerms,\n RightsPricingOption,\n GenerationCredential,\n} from '../../types/core.generated';\n\n// Runtime (v6.0 alpha) — preview surface for adopters spiking against the\n// new shape. Subject to change before 6.0 GA.\nexport {\n createAdcpServerFromPlatform,\n getAllAdcpMigrations,\n type CreateAdcpServerFromPlatformOptions,\n type RequiredOptsFor,\n type DecisioningAdcpServer,\n type DecisioningObservabilityHooks,\n} from './runtime/from-platform';\nexport { PlatformConfigError, validatePlatform } from './runtime/validate-platform';\nexport {\n createInMemoryTaskRegistry,\n type TaskRegistry,\n type TaskRecord,\n type TaskStatus,\n} from './runtime/task-registry';\nexport {\n createPostgresTaskRegistry,\n getDecisioningTaskRegistryMigration,\n type CreatePostgresTaskRegistryOptions,\n type PgQueryable,\n} from './runtime/postgres-task-registry';\n\n// Multi-tenant deployment helper — wraps createAdcpServerFromPlatform with\n// per-tenant config, health states (healthy/unverified/disabled), and JWKS\n// validation. Composes with the existing serve() host-routing surface.\nexport {\n createTenantRegistry,\n createDefaultJwksValidator,\n createSelfSignedTenantKey,\n createNoopJwksValidator,\n type TenantRegistry,\n type TenantConfig,\n type TenantSigningKey,\n type TenantStatus,\n type TenantHealth,\n type TenantRegistryOptions,\n type JwksValidator,\n type JwksValidationResult,\n} from './tenant-registry';\n\n// Manifest helpers — typed accessors for creative_manifest.assets values.\n// Save adopters from writing the same null-check + discriminator-check\n// boilerplate per call.\nexport { getAsset, requireAsset } from './manifest-helpers';\n\n// List helpers — wrap row arrays + pagination into the heavier wire shapes\n// (today: list_creatives, which carries query_summary alongside the rows).\nexport { buildListCreativesResponse, type BuildListCreativesResponseOpts } from './list-helpers';\n\n// Start-time helper — normalize the wire `start_time` union into a Date,\n// with platform-aware ASAP lead-time injection.\nexport { resolveStartTime, type ResolveStartTimeOptions } from './start-time';\n\n// Admin Express router for ops visibility into the TenantRegistry.\n// Mount on a separate port/path with operator auth.\nexport {\n createTenantAdminRouter,\n createTenantAdminHandlers,\n mountTenantAdmin,\n type TenantAdminHandlers,\n type RouterLike,\n} from './admin-router';\n\n// Adopter helpers — batchPoll, validationError, upstreamError, RequestShape.\n// All opt-in convenience; nothing in the framework calls these internally.\nexport { batchPoll, validationError, upstreamError } from './helpers';\nexport type { RequestShape } from './helpers';\n\n// Platform identity helpers — fix TypeScript's contextual-typing gap when\n// building a DecisioningPlatform (or sub-interface) as an object literal.\n// Without these, `createAdcpServerFromPlatform({ sales: { syncEventSources:\n// async (req, ctx) => {...} } })` gives `req: unknown` because the generic\n// `P extends DecisioningPlatform<any,any>` is inferred, not declared.\n// Wrapping the sub-object with e.g. `defineSalesPlatform<MyMeta>({...})`\n// forces the concrete type annotation TypeScript needs. The helpers are\n// pure identity functions — zero runtime cost.\nexport {\n definePlatform,\n defineSalesPlatform,\n defineSalesCorePlatform,\n defineSalesIngestionPlatform,\n defineAudiencePlatform,\n defineSignalsPlatform,\n defineSponsoredIntelligencePlatform,\n defineCreativeBuilderPlatform,\n defineCreativeAdServerPlatform,\n defineCampaignGovernancePlatform,\n defineContentStandardsPlatform,\n definePropertyListsPlatform,\n defineCollectionListsPlatform,\n defineBrandRightsPlatform,\n definePlatformWithCompliance,\n} from './platform-helpers';\n\n// ProposalManager — primitives for the two-platform composition (port of\n// adcp-client-python PRs #504 + #550). Splits proposal assembly from\n// media-buy execution; either side can be mock-backed independently.\n// Framework dispatch wiring lands in a follow-up release.\nexport type {\n ProposalManager,\n ProposalCapabilities,\n ProposalSalesSpecialism,\n Recipe,\n CapabilityOverlap,\n FinalizeProposalRequest,\n FinalizeProposalSuccess,\n ProposalState,\n ProposalRecord,\n ProposalStore,\n InMemoryProposalStoreOptions,\n MockProposalManagerOptions,\n} from './proposal';\nexport {\n validateProposalCapabilities,\n InMemoryProposalStore,\n MockProposalManager,\n enforceProposalExpiry,\n validateCapabilityOverlap,\n validateOverlapSubsetOfWire,\n detectFinalizeAction,\n setProposalLifecycleLogger,\n maybeInterceptFinalize,\n maybePersistDraftAfterGetProducts,\n maybeReserveProposalForCreateMediaBuy,\n finalizeProposalConsumption,\n releaseProposalReservation,\n maybeHydrateRecipesForMediaBuyId,\n} from './proposal';\nexport type { FinalizeActionRef, ProposalLifecycleLogger, FinalizeInterceptResult, ReservedProposal } from './proposal';\n\n// Wire-shape assembly helpers — emit correct Product / PricingOption /\n// package shapes from intent-shaped input. Reduces 30+ lines of wire\n// boilerplate per resource. Used in slim skill examples so LLMs scaffold\n// correct shapes from first attempt.\nexport { buildProduct, buildPricingOption, buildPackage } from './assembly-helpers';\nexport type { BuildProductInput, BuildPricingOptionInput, BuildPackageInput } from './assembly-helpers';\n"],"mappings":"AAsBA,SAAmD,iBAAiB;AAQpE;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAUP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OAMK;AAWP,SAAS,4BAA4B,sCAAsC;AA8B3E,SAAS,sBAAsB,oBAAoB;AAMnD,SAAS,mBAAmB,wBAAwB;AAsBpD,SAAS,0BAA0B;AAInC,SAAS,6BAA6B;AAkBtC,SAAS,qBAAqB;AAM9B,SAAS,qBAAqB,wBAAwB,uBAAuB;AAsJ7E;AAAA,EACE;AAAA,EACA;AAAA,OAKK;AACP,SAAS,qBAAqB,wBAAwB;AACtD;AAAA,EACE;AAAA,OAIK;AACP;AAAA,EACE;AAAA,EACA;AAAA,OAGK;AAKP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OASK;AAKP,SAAS,UAAU,oBAAoB;AAIvC,SAAS,kCAAuE;AAIhF,SAAS,wBAAsD;AAI/D;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,OAGK;AAIP,SAAS,WAAW,iBAAiB,qBAAqB;AAW1D;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAoBP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAOP,SAAS,cAAc,oBAAoB,oBAAoB;","names":[]}
|
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
function buildListCreativesResponse(opts) {
|
|
8
2
|
const { request, creatives, pagination, totalMatching } = opts;
|
|
9
3
|
const filters = request.filters;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/lib/server/decisioning/list-helpers.ts"],"sourcesContent":["/**\n * Helpers for building paginated list responses.\n *\n * `list_creatives` is the heaviest of the read tools: its response wraps the\n * row array in `query_summary` (`total_matching`, `returned`, `filters_applied`,\n * `sort_applied`) AND `pagination` (`has_more`, `cursor`, `total_count`).\n * Adopters writing the wrapper by hand re-derive the same fields per call;\n * this helper threads a row array + pagination cursor + the original request\n * into the wire shape.\n *\n * `list_property_lists`, `list_collection_lists`, and other governance reads\n * use a simpler `{ lists: [...] }` wrapper that the framework's response\n * builders already cover — those don't need a row helper.\n *\n * Status: Preview / 6.0.\n *\n * @public\n */\n\nimport type { ListCreativesRequest, ListCreativesResponse, PaginationResponse } from '../../types/tools.generated';\nimport type { ServerPayload } from '../../types/server-payload';\n\nexport interface BuildListCreativesResponseOpts {\n /** Original request — used to surface `filters_applied` + `sort_applied` summaries. */\n request: ListCreativesRequest;\n /** The page of creative rows. Length determines `query_summary.returned`. */\n creatives: ServerPayload<ListCreativesResponse>['creatives'];\n /** Pagination cursor for the next page. Required — pass `{ has_more: false }` when this is the last page. */\n pagination: PaginationResponse;\n /**\n * Total count across all pages. When omitted, defaults to\n * `pagination.total_count` if present, else `creatives.length` (last-page\n * approximation). Set explicitly when your backend can compute the true\n * total.\n */\n totalMatching?: number;\n}\n\n/**\n * Build a `ListCreativesResponse` from a row array + pagination + the\n * original request. Computes `query_summary.filters_applied` from\n * `request.filters` and threads `request.sort` into `sort_applied`.\n *\n * ```ts\n * listCreatives: async (req, ctx) => {\n * const rows = await this.db.queryCreatives(req);\n * const cursor = rows.length === req.pagination?.limit ? this.nextCursor(rows) : undefined;\n * return buildListCreativesResponse({\n * request: req,\n * creatives: rows,\n * pagination: { has_more: cursor != null, cursor, total_count: rows.totalCount },\n * });\n * }\n * ```\n */\nexport function buildListCreativesResponse(opts: BuildListCreativesResponseOpts): ServerPayload<ListCreativesResponse> {\n const { request, creatives, pagination, totalMatching } = opts;\n\n const filters = request.filters;\n const filtersApplied: string[] = [];\n if (filters) {\n if (filters.accounts?.length) filtersApplied.push('accounts');\n if (filters.statuses?.length) filtersApplied.push('statuses');\n if (filters.tags?.length) filtersApplied.push('tags');\n if (filters.tags_any?.length) filtersApplied.push('tags_any');\n if (filters.name_contains) filtersApplied.push('name_contains');\n if (filters.creative_ids?.length) filtersApplied.push('creative_ids');\n if (filters.created_after) filtersApplied.push('created_after');\n if (filters.created_before) filtersApplied.push('created_before');\n if (filters.updated_after) filtersApplied.push('updated_after');\n if (filters.updated_before) filtersApplied.push('updated_before');\n if (filters.assigned_to_packages?.length) filtersApplied.push('assigned_to_packages');\n if (filters.media_buy_ids?.length) filtersApplied.push('media_buy_ids');\n if (filters.unassigned !== undefined) filtersApplied.push('unassigned');\n if (filters.has_served !== undefined) filtersApplied.push('has_served');\n if (filters.concept_ids?.length) filtersApplied.push('concept_ids');\n if (filters.format_ids?.length) filtersApplied.push('format_ids');\n if (filters.has_variables !== undefined) filtersApplied.push('has_variables');\n }\n\n const summary: ServerPayload<ListCreativesResponse>['query_summary'] = {\n total_matching: totalMatching ?? pagination.total_count ?? creatives.length,\n returned: creatives.length,\n ...(filtersApplied.length > 0 && { filters_applied: filtersApplied }),\n ...(request.sort && {\n sort_applied: {\n ...(request.sort.field !== undefined && { field: request.sort.field }),\n ...(request.sort.direction !== undefined && { direction: request.sort.direction }),\n },\n }),\n };\n\n return {\n query_summary: summary,\n pagination,\n creatives,\n };\n}\n"],"mappings":"
|
|
1
|
+
{"version":3,"sources":["../../../../src/lib/server/decisioning/list-helpers.ts"],"sourcesContent":["/**\n * Helpers for building paginated list responses.\n *\n * `list_creatives` is the heaviest of the read tools: its response wraps the\n * row array in `query_summary` (`total_matching`, `returned`, `filters_applied`,\n * `sort_applied`) AND `pagination` (`has_more`, `cursor`, `total_count`).\n * Adopters writing the wrapper by hand re-derive the same fields per call;\n * this helper threads a row array + pagination cursor + the original request\n * into the wire shape.\n *\n * `list_property_lists`, `list_collection_lists`, and other governance reads\n * use a simpler `{ lists: [...] }` wrapper that the framework's response\n * builders already cover — those don't need a row helper.\n *\n * Status: Preview / 6.0.\n *\n * @public\n */\n\nimport type { ListCreativesRequest, ListCreativesResponse, PaginationResponse } from '../../types/tools.generated';\nimport type { ServerPayload } from '../../types/server-payload';\n\nexport interface BuildListCreativesResponseOpts {\n /** Original request — used to surface `filters_applied` + `sort_applied` summaries. */\n request: ListCreativesRequest;\n /** The page of creative rows. Length determines `query_summary.returned`. */\n creatives: ServerPayload<ListCreativesResponse>['creatives'];\n /** Pagination cursor for the next page. Required — pass `{ has_more: false }` when this is the last page. */\n pagination: PaginationResponse;\n /**\n * Total count across all pages. When omitted, defaults to\n * `pagination.total_count` if present, else `creatives.length` (last-page\n * approximation). Set explicitly when your backend can compute the true\n * total.\n */\n totalMatching?: number;\n}\n\n/**\n * Build a `ListCreativesResponse` from a row array + pagination + the\n * original request. Computes `query_summary.filters_applied` from\n * `request.filters` and threads `request.sort` into `sort_applied`.\n *\n * ```ts\n * listCreatives: async (req, ctx) => {\n * const rows = await this.db.queryCreatives(req);\n * const cursor = rows.length === req.pagination?.limit ? this.nextCursor(rows) : undefined;\n * return buildListCreativesResponse({\n * request: req,\n * creatives: rows,\n * pagination: { has_more: cursor != null, cursor, total_count: rows.totalCount },\n * });\n * }\n * ```\n */\nexport function buildListCreativesResponse(opts: BuildListCreativesResponseOpts): ServerPayload<ListCreativesResponse> {\n const { request, creatives, pagination, totalMatching } = opts;\n\n const filters = request.filters;\n const filtersApplied: string[] = [];\n if (filters) {\n if (filters.accounts?.length) filtersApplied.push('accounts');\n if (filters.statuses?.length) filtersApplied.push('statuses');\n if (filters.tags?.length) filtersApplied.push('tags');\n if (filters.tags_any?.length) filtersApplied.push('tags_any');\n if (filters.name_contains) filtersApplied.push('name_contains');\n if (filters.creative_ids?.length) filtersApplied.push('creative_ids');\n if (filters.created_after) filtersApplied.push('created_after');\n if (filters.created_before) filtersApplied.push('created_before');\n if (filters.updated_after) filtersApplied.push('updated_after');\n if (filters.updated_before) filtersApplied.push('updated_before');\n if (filters.assigned_to_packages?.length) filtersApplied.push('assigned_to_packages');\n if (filters.media_buy_ids?.length) filtersApplied.push('media_buy_ids');\n if (filters.unassigned !== undefined) filtersApplied.push('unassigned');\n if (filters.has_served !== undefined) filtersApplied.push('has_served');\n if (filters.concept_ids?.length) filtersApplied.push('concept_ids');\n if (filters.format_ids?.length) filtersApplied.push('format_ids');\n if (filters.has_variables !== undefined) filtersApplied.push('has_variables');\n }\n\n const summary: ServerPayload<ListCreativesResponse>['query_summary'] = {\n total_matching: totalMatching ?? pagination.total_count ?? creatives.length,\n returned: creatives.length,\n ...(filtersApplied.length > 0 && { filters_applied: filtersApplied }),\n ...(request.sort && {\n sort_applied: {\n ...(request.sort.field !== undefined && { field: request.sort.field }),\n ...(request.sort.direction !== undefined && { direction: request.sort.direction }),\n },\n }),\n };\n\n return {\n query_summary: summary,\n pagination,\n creatives,\n };\n}\n"],"mappings":"AAuDO,SAAS,2BAA2B,MAA4E;AACrH,QAAM,EAAE,SAAS,WAAW,YAAY,cAAc,IAAI;AAE1D,QAAM,UAAU,QAAQ;AACxB,QAAM,iBAA2B,CAAC;AAClC,MAAI,SAAS;AACX,QAAI,QAAQ,UAAU,OAAQ,gBAAe,KAAK,UAAU;AAC5D,QAAI,QAAQ,UAAU,OAAQ,gBAAe,KAAK,UAAU;AAC5D,QAAI,QAAQ,MAAM,OAAQ,gBAAe,KAAK,MAAM;AACpD,QAAI,QAAQ,UAAU,OAAQ,gBAAe,KAAK,UAAU;AAC5D,QAAI,QAAQ,cAAe,gBAAe,KAAK,eAAe;AAC9D,QAAI,QAAQ,cAAc,OAAQ,gBAAe,KAAK,cAAc;AACpE,QAAI,QAAQ,cAAe,gBAAe,KAAK,eAAe;AAC9D,QAAI,QAAQ,eAAgB,gBAAe,KAAK,gBAAgB;AAChE,QAAI,QAAQ,cAAe,gBAAe,KAAK,eAAe;AAC9D,QAAI,QAAQ,eAAgB,gBAAe,KAAK,gBAAgB;AAChE,QAAI,QAAQ,sBAAsB,OAAQ,gBAAe,KAAK,sBAAsB;AACpF,QAAI,QAAQ,eAAe,OAAQ,gBAAe,KAAK,eAAe;AACtE,QAAI,QAAQ,eAAe,OAAW,gBAAe,KAAK,YAAY;AACtE,QAAI,QAAQ,eAAe,OAAW,gBAAe,KAAK,YAAY;AACtE,QAAI,QAAQ,aAAa,OAAQ,gBAAe,KAAK,aAAa;AAClE,QAAI,QAAQ,YAAY,OAAQ,gBAAe,KAAK,YAAY;AAChE,QAAI,QAAQ,kBAAkB,OAAW,gBAAe,KAAK,eAAe;AAAA,EAC9E;AAEA,QAAM,UAAiE;AAAA,IACrE,gBAAgB,iBAAiB,WAAW,eAAe,UAAU;AAAA,IACrE,UAAU,UAAU;AAAA,IACpB,GAAI,eAAe,SAAS,KAAK,EAAE,iBAAiB,eAAe;AAAA,IACnE,GAAI,QAAQ,QAAQ;AAAA,MAClB,cAAc;AAAA,QACZ,GAAI,QAAQ,KAAK,UAAU,UAAa,EAAE,OAAO,QAAQ,KAAK,MAAM;AAAA,QACpE,GAAI,QAAQ,KAAK,cAAc,UAAa,EAAE,WAAW,QAAQ,KAAK,UAAU;AAAA,MAClF;AAAA,IACF;AAAA,EACF;AAEA,SAAO;AAAA,IACL,eAAe;AAAA,IACf;AAAA,IACA;AAAA,EACF;AACF;","names":[]}
|
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
import { AdcpError } from "./async-outcome.mjs";
|
|
8
2
|
function getAsset(manifest, assetId, assetType) {
|
|
9
3
|
const slot = manifest?.assets?.[assetId];
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/lib/server/decisioning/manifest-helpers.ts"],"sourcesContent":["/**\n * Helpers for reading typed assets out of `creative_manifest.assets`.\n *\n * `creative_manifest.assets` is a keyed map (`{ [asset_id]: AssetInstance }`)\n * where each value is a discriminated union by `asset_type`. Adopters\n * narrowing per-call write the same null-check + discriminator-check\n * boilerplate over and over. These helpers replace that boilerplate\n * without compromising the discriminator-narrowing story.\n *\n * Status: Preview / 6.0.\n *\n * @public\n */\n\nimport type { CreativeManifest } from '../../types/tools.generated';\nimport type { AssetInstance, AssetInstanceType } from '../../types/asset-instances';\nimport { AdcpError } from './async-outcome';\n\n/**\n * Type-narrowed asset accessor by asset_id and expected asset_type.\n *\n * Returns the asset narrowed to the matching variant, or `undefined` if the\n * asset is missing or the asset_type doesn't match. Use when you want a\n * silent skip for the wrong-type case (e.g., processing a heterogeneous\n * batch where some entries don't apply to your transform).\n *\n * ```ts\n * const audio = getAsset(req.creative_manifest, 'rendered_audio', 'audio');\n * // audio is `AudioAsset | undefined` — narrowed by the discriminator\n * if (audio) {\n * const url = audio.url; // typed access\n * const ms = audio.duration_ms;\n * }\n * ```\n *\n * For the require-or-throw flavor, see {@link requireAsset}.\n */\nexport function getAsset<T extends AssetInstanceType>(\n manifest: CreativeManifest | undefined,\n assetId: string,\n assetType: T\n): Extract<AssetInstance, { asset_type: T }> | undefined {\n // AdCP 3.1.0-beta.2 widened each slot from `AssetVariant` to\n // `AssetVariant | AssetVariant[]` so carousel `cards` and\n // responsive_creative `headlines` can carry multiple assets per slot.\n // For single-slot callers, take the first array element — preserves the\n // pre-3.1 behavior. Multi-asset slots use {@link getAssetSlot}.\n const slot = manifest?.assets?.[assetId];\n const asset = Array.isArray(slot) ? slot[0] : slot;\n if (!asset || asset.asset_type !== assetType) return undefined;\n return asset as Extract<AssetInstance, { asset_type: T }>;\n}\n\n/**\n * Type-narrowed asset slot accessor for multi-element slots (carousel\n * `cards`, responsive_creative `headlines`, etc.). Returns the full\n * array — every element must match `assetType`; mixed-type slots are\n * the adopter's responsibility to discriminate per-element.\n *\n * Returns `undefined` only when the slot is missing from the manifest\n * (`manifest.assets[assetId]` is absent). Returns `[]` when the slot\n * is present but empty, or present and non-empty with no elements\n * matching `assetType`. Empty arrays are spec-invalid per the\n * `minItems: 1` constraint on slot arrays, but the helper accepts\n * malformed input defensively — returning `[]` is more consistent\n * with the \"filter result on the slot\" contract than collapsing it\n * to `undefined`.\n *\n * @since AdCP 3.1.0-beta.2 (slot widening to `AssetVariant | AssetVariant[]`).\n */\nexport function getAssetSlot<T extends AssetInstanceType>(\n manifest: CreativeManifest | undefined,\n assetId: string,\n assetType: T\n): Array<Extract<AssetInstance, { asset_type: T }>> | undefined {\n const slot = manifest?.assets?.[assetId];\n if (!slot) return undefined;\n const arr = Array.isArray(slot) ? slot : [slot];\n return arr.filter(a => a.asset_type === assetType) as Array<Extract<AssetInstance, { asset_type: T }>>;\n}\n\n/**\n * Same as {@link getAsset} but throws `AdcpError('INVALID_REQUEST')` when\n * the asset is missing or the wrong type. Use when the asset is required\n * for the platform method to proceed (the typical creative-template case).\n *\n * Throws with a precomposed `field` path so the buyer sees actionable\n * feedback. Customize the message via the `messageOverride` arg if the\n * default doesn't fit.\n *\n * ```ts\n * const script = requireAsset(req.creative_manifest, 'script', 'text');\n * // script is `TextAsset` — never undefined past this line\n * await audioStackClient.synthesize({ text: script.content });\n * ```\n */\nexport function requireAsset<T extends AssetInstanceType>(\n manifest: CreativeManifest | undefined,\n assetId: string,\n assetType: T,\n messageOverride?: string\n): Extract<AssetInstance, { asset_type: T }> {\n // Slot widening (3.1.0-beta.2): unwrap array slots to the first element\n // for single-asset callers. Multi-element slots go through getAssetSlot.\n const slot = manifest?.assets?.[assetId];\n const asset = Array.isArray(slot) ? slot[0] : slot;\n if (!asset) {\n throw new AdcpError('INVALID_REQUEST', {\n message: messageOverride ?? `creative_manifest.assets.${assetId} is required`,\n field: `creative_manifest.assets.${assetId}`,\n });\n }\n if (asset.asset_type !== assetType) {\n throw new AdcpError('INVALID_REQUEST', {\n message:\n messageOverride ??\n `creative_manifest.assets.${assetId} must be a ${assetType} asset (got asset_type='${asset.asset_type}')`,\n field: `creative_manifest.assets.${assetId}.asset_type`,\n });\n }\n return asset as Extract<AssetInstance, { asset_type: T }>;\n}\n"],"mappings":"
|
|
1
|
+
{"version":3,"sources":["../../../../src/lib/server/decisioning/manifest-helpers.ts"],"sourcesContent":["/**\n * Helpers for reading typed assets out of `creative_manifest.assets`.\n *\n * `creative_manifest.assets` is a keyed map (`{ [asset_id]: AssetInstance }`)\n * where each value is a discriminated union by `asset_type`. Adopters\n * narrowing per-call write the same null-check + discriminator-check\n * boilerplate over and over. These helpers replace that boilerplate\n * without compromising the discriminator-narrowing story.\n *\n * Status: Preview / 6.0.\n *\n * @public\n */\n\nimport type { CreativeManifest } from '../../types/tools.generated';\nimport type { AssetInstance, AssetInstanceType } from '../../types/asset-instances';\nimport { AdcpError } from './async-outcome';\n\n/**\n * Type-narrowed asset accessor by asset_id and expected asset_type.\n *\n * Returns the asset narrowed to the matching variant, or `undefined` if the\n * asset is missing or the asset_type doesn't match. Use when you want a\n * silent skip for the wrong-type case (e.g., processing a heterogeneous\n * batch where some entries don't apply to your transform).\n *\n * ```ts\n * const audio = getAsset(req.creative_manifest, 'rendered_audio', 'audio');\n * // audio is `AudioAsset | undefined` — narrowed by the discriminator\n * if (audio) {\n * const url = audio.url; // typed access\n * const ms = audio.duration_ms;\n * }\n * ```\n *\n * For the require-or-throw flavor, see {@link requireAsset}.\n */\nexport function getAsset<T extends AssetInstanceType>(\n manifest: CreativeManifest | undefined,\n assetId: string,\n assetType: T\n): Extract<AssetInstance, { asset_type: T }> | undefined {\n // AdCP 3.1.0-beta.2 widened each slot from `AssetVariant` to\n // `AssetVariant | AssetVariant[]` so carousel `cards` and\n // responsive_creative `headlines` can carry multiple assets per slot.\n // For single-slot callers, take the first array element — preserves the\n // pre-3.1 behavior. Multi-asset slots use {@link getAssetSlot}.\n const slot = manifest?.assets?.[assetId];\n const asset = Array.isArray(slot) ? slot[0] : slot;\n if (!asset || asset.asset_type !== assetType) return undefined;\n return asset as Extract<AssetInstance, { asset_type: T }>;\n}\n\n/**\n * Type-narrowed asset slot accessor for multi-element slots (carousel\n * `cards`, responsive_creative `headlines`, etc.). Returns the full\n * array — every element must match `assetType`; mixed-type slots are\n * the adopter's responsibility to discriminate per-element.\n *\n * Returns `undefined` only when the slot is missing from the manifest\n * (`manifest.assets[assetId]` is absent). Returns `[]` when the slot\n * is present but empty, or present and non-empty with no elements\n * matching `assetType`. Empty arrays are spec-invalid per the\n * `minItems: 1` constraint on slot arrays, but the helper accepts\n * malformed input defensively — returning `[]` is more consistent\n * with the \"filter result on the slot\" contract than collapsing it\n * to `undefined`.\n *\n * @since AdCP 3.1.0-beta.2 (slot widening to `AssetVariant | AssetVariant[]`).\n */\nexport function getAssetSlot<T extends AssetInstanceType>(\n manifest: CreativeManifest | undefined,\n assetId: string,\n assetType: T\n): Array<Extract<AssetInstance, { asset_type: T }>> | undefined {\n const slot = manifest?.assets?.[assetId];\n if (!slot) return undefined;\n const arr = Array.isArray(slot) ? slot : [slot];\n return arr.filter(a => a.asset_type === assetType) as Array<Extract<AssetInstance, { asset_type: T }>>;\n}\n\n/**\n * Same as {@link getAsset} but throws `AdcpError('INVALID_REQUEST')` when\n * the asset is missing or the wrong type. Use when the asset is required\n * for the platform method to proceed (the typical creative-template case).\n *\n * Throws with a precomposed `field` path so the buyer sees actionable\n * feedback. Customize the message via the `messageOverride` arg if the\n * default doesn't fit.\n *\n * ```ts\n * const script = requireAsset(req.creative_manifest, 'script', 'text');\n * // script is `TextAsset` — never undefined past this line\n * await audioStackClient.synthesize({ text: script.content });\n * ```\n */\nexport function requireAsset<T extends AssetInstanceType>(\n manifest: CreativeManifest | undefined,\n assetId: string,\n assetType: T,\n messageOverride?: string\n): Extract<AssetInstance, { asset_type: T }> {\n // Slot widening (3.1.0-beta.2): unwrap array slots to the first element\n // for single-asset callers. Multi-element slots go through getAssetSlot.\n const slot = manifest?.assets?.[assetId];\n const asset = Array.isArray(slot) ? slot[0] : slot;\n if (!asset) {\n throw new AdcpError('INVALID_REQUEST', {\n message: messageOverride ?? `creative_manifest.assets.${assetId} is required`,\n field: `creative_manifest.assets.${assetId}`,\n });\n }\n if (asset.asset_type !== assetType) {\n throw new AdcpError('INVALID_REQUEST', {\n message:\n messageOverride ??\n `creative_manifest.assets.${assetId} must be a ${assetType} asset (got asset_type='${asset.asset_type}')`,\n field: `creative_manifest.assets.${assetId}.asset_type`,\n });\n }\n return asset as Extract<AssetInstance, { asset_type: T }>;\n}\n"],"mappings":"AAgBA,SAAS,iBAAiB;AAqBnB,SAAS,SACd,UACA,SACA,WACuD;AAMvD,QAAM,OAAO,UAAU,SAAS,OAAO;AACvC,QAAM,QAAQ,MAAM,QAAQ,IAAI,IAAI,KAAK,CAAC,IAAI;AAC9C,MAAI,CAAC,SAAS,MAAM,eAAe,UAAW,QAAO;AACrD,SAAO;AACT;AAmBO,SAAS,aACd,UACA,SACA,WAC8D;AAC9D,QAAM,OAAO,UAAU,SAAS,OAAO;AACvC,MAAI,CAAC,KAAM,QAAO;AAClB,QAAM,MAAM,MAAM,QAAQ,IAAI,IAAI,OAAO,CAAC,IAAI;AAC9C,SAAO,IAAI,OAAO,OAAK,EAAE,eAAe,SAAS;AACnD;AAiBO,SAAS,aACd,UACA,SACA,WACA,iBAC2C;AAG3C,QAAM,OAAO,UAAU,SAAS,OAAO;AACvC,QAAM,QAAQ,MAAM,QAAQ,IAAI,IAAI,KAAK,CAAC,IAAI;AAC9C,MAAI,CAAC,OAAO;AACV,UAAM,IAAI,UAAU,mBAAmB;AAAA,MACrC,SAAS,mBAAmB,4BAA4B,OAAO;AAAA,MAC/D,OAAO,4BAA4B,OAAO;AAAA,IAC5C,CAAC;AAAA,EACH;AACA,MAAI,MAAM,eAAe,WAAW;AAClC,UAAM,IAAI,UAAU,mBAAmB;AAAA,MACrC,SACE,mBACA,4BAA4B,OAAO,cAAc,SAAS,2BAA2B,MAAM,UAAU;AAAA,MACvG,OAAO,4BAA4B,OAAO;AAAA,IAC5C,CAAC;AAAA,EACH;AACA,SAAO;AACT;","names":[]}
|
|
@@ -1,7 +1 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
//# sourceMappingURL=pagination.mjs.map
|
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
function definePlatform(platform) {
|
|
8
2
|
return platform;
|
|
9
3
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/lib/server/decisioning/platform-helpers.ts"],"sourcesContent":["/**\n * Identity helpers for `createAdcpServerFromPlatform` adopters who build their\n * platform as an object literal rather than a class.\n *\n * **The problem they solve:**\n *\n * `createAdcpServerFromPlatform<P extends DecisioningPlatform<any, any>>(platform: P)`\n * infers `P` from the argument, which defeats TypeScript's contextual typing for\n * method parameters inside nested object literals. Without an explicit type annotation,\n * a handler like `syncEventSources: async (req, ctx) => {...}` gets `req: unknown`.\n *\n * These helpers force a concrete `DecisioningPlatform<TConfig, TCtxMeta>` (or\n * per-specialism sub-interface) as the argument type, giving TypeScript the\n * annotation it needs to flow types into nested method bodies:\n *\n * ```ts\n * // Without helper — req: unknown\n * createAdcpServerFromPlatform({\n * sales: { syncEventSources: async (req, ctx) => { req.event_sources } }\n * }, opts);\n *\n * // With defineSalesPlatform — req: SyncEventSourcesRequest ✓\n * createAdcpServerFromPlatform({\n * sales: defineSalesPlatform<MyMeta>({\n * syncEventSources: async (req, ctx) => { req.event_sources }\n * })\n * }, opts);\n * ```\n *\n * Alternatively, the class pattern with explicit property-type annotations achieves\n * the same result without helpers:\n *\n * ```ts\n * class MySeller implements DecisioningPlatform<Config, MyMeta> {\n * sales: SalesPlatform<MyMeta> = {\n * syncEventSources: async (req, ctx) => { req.event_sources } // req typed ✓\n * };\n * }\n * ```\n *\n * Use whichever pattern fits your codebase.\n *\n * @public\n */\n\nimport type { DecisioningPlatform } from './platform';\nimport type { ComplianceTestingCapabilities } from './capabilities';\nimport type { SalesPlatform, SalesCorePlatform, SalesIngestionPlatform } from './specialisms/sales';\nimport type { AudiencePlatform } from './specialisms/audiences';\nimport type { SignalsPlatform } from './specialisms/signals';\nimport type { SponsoredIntelligencePlatform } from './specialisms/sponsored-intelligence';\nimport type { CreativeBuilderPlatform } from './specialisms/creative';\nimport type { CreativeAdServerPlatform } from './specialisms/creative-ad-server';\nimport type { CampaignGovernancePlatform } from './specialisms/campaign-governance';\nimport type { ContentStandardsPlatform } from './specialisms/content-standards';\nimport type { BrandRightsPlatform } from './specialisms/brand-rights';\nimport type { PropertyListsPlatform, CollectionListsPlatform } from './specialisms/lists';\n\n/**\n * Type-level identity for a full `DecisioningPlatform` object literal.\n *\n * Fixes TypeScript's contextual-typing gap when passing an object literal\n * directly to `createAdcpServerFromPlatform`. Wrap your platform object with\n * this helper to get typed `req` and `ctx` parameters in every handler body.\n *\n * @example\n * ```ts\n * import { createAdcpServerFromPlatform, definePlatform } from '@adcp/sdk/server';\n *\n * interface MyMeta { advertiserId: string }\n *\n * const server = createAdcpServerFromPlatform(\n * definePlatform<{ networkId: string }, MyMeta>({\n * capabilities: { specialisms: ['sales-non-guaranteed'], ... },\n * accounts: { resolve: async (ref) => ... },\n * sales: {\n * getProducts: async (req, ctx) => {\n * // req: GetProductsRequest ✓ ctx.account.ctx_metadata: MyMeta ✓\n * },\n * },\n * }),\n * { name: 'my-seller', version: '1.0.0' }\n * );\n * ```\n */\nexport function definePlatform<TConfig = unknown, TCtxMeta = Record<string, unknown>>(\n platform: DecisioningPlatform<TConfig, TCtxMeta>\n): DecisioningPlatform<TConfig, TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `SalesPlatform` sub-object.\n *\n * Use this to type-annotate the `sales` property when building inline rather\n * than with a class. Every handler method (`getProducts`, `createMediaBuy`,\n * `syncEventSources`, etc.) gets its proper typed `req` parameter.\n *\n * @example\n * ```ts\n * import { createAdcpServerFromPlatform, defineSalesPlatform } from '@adcp/sdk/server';\n *\n * interface SocialMeta { advertiserId: string; pixelId: string }\n *\n * const server = createAdcpServerFromPlatform({\n * capabilities: { specialisms: ['sales-social', 'sales-non-guaranteed'], ... },\n * accounts: { resolve: async (ref) => ... },\n * sales: defineSalesPlatform<SocialMeta>({\n * getProducts: async (req, ctx) => { ... },\n * createMediaBuy: async (req, ctx) => { ... },\n * // req is fully typed throughout ✓\n * syncEventSources: async (req, ctx) => {\n * const sources = req.event_sources ?? []; // no cast needed\n * },\n * }),\n * }, { name: 'social-seller', version: '1.0.0' });\n * ```\n */\nexport function defineSalesPlatform<TCtxMeta = Record<string, unknown>>(\n platform: SalesPlatform<TCtxMeta>\n): SalesPlatform<TCtxMeta> {\n // Identity helper — return type matches the input parameter type.\n //\n // **Post-#1341 caveat.** `SalesPlatform` methods are now optional\n // individually, so this helper's return type is effectively all-optional\n // even when the adopter passes all five core methods. Adopters claiming\n // a sales specialism with `RequiredPlatformsFor<S>`-narrowed core methods\n // (`sales-guaranteed`, `sales-non-guaranteed`, `sales-broadcast-tv`,\n // `sales-catalog-driven`) need the closed shape on the way out — this\n // helper doesn't preserve it. Two ways to keep the per-specialism type\n // narrowing under #1341:\n //\n // 1. Drop `defineSalesPlatform` and write the platform field with an\n // explicit `: SalesCorePlatform<Meta> & SalesIngestionPlatform<Meta>`\n // annotation. The TS compiler flows the contextual type into the\n // literal and `RequiredPlatformsFor<S>` enforcement holds.\n // 2. Use the new {@link defineSalesCorePlatform} for the core methods\n // and {@link defineSalesIngestionPlatform} for ingestion methods,\n // spreading both onto the `sales` field.\n //\n // Pure source-compat for adopters claiming `sales-social` (ingestion-only)\n // who don't need the per-specialism core narrowing — the helper still\n // pins TCtxMeta on the parameter so handler `ctx` is typed correctly.\n return platform;\n}\n\n/**\n * Type-level identity for the **core** sales surface — bidding +\n * media-buy lifecycle (`getProducts`, `createMediaBuy`, `updateMediaBuy`,\n * `getMediaBuyDelivery`, `getMediaBuys`). Use when claiming `sales-non-\n * guaranteed` / `sales-guaranteed` / `sales-broadcast-tv` /\n * `sales-catalog-driven` and you want compile-time enforcement of the\n * lifecycle methods without dragging in optional ingestion methods.\n *\n * Pair with {@link defineSalesIngestionPlatform} when also implementing\n * ingestion surfaces (sync_creatives, log_event, etc.) — spread the two\n * onto the platform's `sales` field.\n *\n * @example\n * ```ts\n * sales: { ...defineSalesCorePlatform<MyMeta>({\n * getProducts: async (req, ctx) => { ... },\n * createMediaBuy: async (req, ctx) => { ... },\n * updateMediaBuy: async (id, patch, ctx) => { ... },\n * getMediaBuyDelivery: async (filter, ctx) => { ... },\n * getMediaBuys: async (req, ctx) => { ... },\n * }) },\n * ```\n */\nexport function defineSalesCorePlatform<TCtxMeta = Record<string, unknown>>(\n platform: SalesCorePlatform<TCtxMeta>\n): SalesCorePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for the **ingestion** sales surface — sync surfaces\n * (`syncCreatives`, `syncCatalogs`, `syncEventSources`, `logEvent`) +\n * read/feedback (`listCreativeFormats`, `listCreatives`,\n * `providePerformanceFeedback`). Walled-garden specialisms whose value\n * surface is asset push (Meta CAPI, Snap CAPI, retail-media catalogs)\n * use this without claiming the core media-buy lifecycle. Every method\n * is optional individually — implement what your specialism's storyboard\n * exercises.\n *\n * Use this when claiming `sales-social` (no `sales-non-guaranteed`)\n * or composing `audience-sync` ingestion onto a non-media-buy seller.\n * Adopters who also accept inbound media buys spread\n * {@link defineSalesCorePlatform}'s output alongside.\n *\n * @example\n * ```ts\n * // Pure sales-social adopter — no media buys, just events + creatives.\n * sales: defineSalesIngestionPlatform<SocialMeta>({\n * syncCreatives: async (creatives, ctx) => { ... },\n * syncEventSources: async (req, ctx) => { ... },\n * logEvent: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineSalesIngestionPlatform<TCtxMeta = Record<string, unknown>>(\n platform: SalesIngestionPlatform<TCtxMeta>\n): SalesIngestionPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for an `AudiencePlatform` sub-object.\n *\n * Use when the `audiences` field is built inline. Ensures `audiences` and\n * `audienceIds` parameters are typed rather than inferred as `unknown`.\n *\n * @example\n * ```ts\n * audiences: defineAudiencePlatform<SocialMeta>({\n * syncAudiences: async (audiences, ctx) => {\n * // audiences: Audience[] ✓ ctx.account.ctx_metadata: SocialMeta ✓\n * },\n * pollAudienceStatuses: async (audienceIds, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineAudiencePlatform<TCtxMeta = Record<string, unknown>>(\n platform: AudiencePlatform<TCtxMeta>\n): AudiencePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `SignalsPlatform` sub-object.\n *\n * @example\n * ```ts\n * signals: defineSignalsPlatform<SignalsMeta>({\n * getSignals: async (req, ctx) => { ... },\n * activateSignal: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineSignalsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: SignalsPlatform<TCtxMeta>\n): SignalsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `SponsoredIntelligencePlatform` sub-object.\n * SI is both a protocol-bundle surface and an AdCP 3.1 specialism.\n * Adopters declare the implementation here; when they claim the\n * `sponsored-intelligence` specialism, the framework auto-derives\n * `'sponsored_intelligence'` into the wire-side `supported_protocols`.\n *\n * @example\n * ```ts\n * sponsoredIntelligence: defineSponsoredIntelligencePlatform<BrandMeta>({\n * getOffering: async (req, ctx) => { ... },\n * initiateSession: async (req, ctx) => { ... },\n * sendMessage: async (req, ctx) => { ... },\n * terminateSession: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineSponsoredIntelligencePlatform<TCtxMeta = Record<string, unknown>>(\n platform: SponsoredIntelligencePlatform<TCtxMeta>\n): SponsoredIntelligencePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CreativeBuilderPlatform` sub-object.\n *\n * @example\n * ```ts\n * creative: defineCreativeBuilderPlatform<CreativeMeta>({\n * buildCreative: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineCreativeBuilderPlatform<TCtxMeta = Record<string, unknown>>(\n platform: CreativeBuilderPlatform<TCtxMeta>\n): CreativeBuilderPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CreativeAdServerPlatform` sub-object.\n */\nexport function defineCreativeAdServerPlatform<TCtxMeta = Record<string, unknown>>(\n platform: CreativeAdServerPlatform<TCtxMeta>\n): CreativeAdServerPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CampaignGovernancePlatform` sub-object.\n */\nexport function defineCampaignGovernancePlatform<TCtxMeta = Record<string, unknown>>(\n platform: CampaignGovernancePlatform<TCtxMeta>\n): CampaignGovernancePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `ContentStandardsPlatform` sub-object.\n */\nexport function defineContentStandardsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: ContentStandardsPlatform<TCtxMeta>\n): ContentStandardsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `PropertyListsPlatform` sub-object.\n */\nexport function definePropertyListsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: PropertyListsPlatform<TCtxMeta>\n): PropertyListsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CollectionListsPlatform` sub-object.\n */\nexport function defineCollectionListsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: CollectionListsPlatform<TCtxMeta>\n): CollectionListsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `BrandRightsPlatform` sub-object.\n */\nexport function defineBrandRightsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: BrandRightsPlatform<TCtxMeta>\n): BrandRightsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a full `DecisioningPlatform` that wires\n * `comply_test_controller`. Requires `capabilities.compliance_testing`\n * to be present in the platform object, enforcing the cap/adapter\n * pairing at compile time.\n *\n * When the returned platform is passed to `createAdcpServerFromPlatform`,\n * `RequiredOptsFor<P>` resolves to require `complyTest` in opts — so\n * both halves of the invariant are enforced without runtime-only feedback.\n *\n * @example\n * ```ts\n * import {\n * createAdcpServerFromPlatform,\n * definePlatformWithCompliance,\n * } from '@adcp/sdk/server';\n *\n * const server = createAdcpServerFromPlatform(\n * definePlatformWithCompliance<Config, Meta>({\n * capabilities: {\n * specialisms: ['sales-guaranteed'],\n * compliance_testing: {}, // required by this helper ✓\n * },\n * accounts: { resolve: async (ref) => ... },\n * sales: { ... },\n * }),\n * {\n * name: 'my-seller',\n * version: '1.0.0',\n * complyTest: { seed: { product: ... } }, // required by RequiredOptsFor<P> ✓\n * }\n * );\n * ```\n */\nexport function definePlatformWithCompliance<TConfig = unknown, TCtxMeta = Record<string, unknown>>(\n platform: DecisioningPlatform<TConfig, TCtxMeta> & {\n capabilities: { compliance_testing: ComplianceTestingCapabilities };\n }\n): DecisioningPlatform<TConfig, TCtxMeta> & {\n capabilities: { compliance_testing: ComplianceTestingCapabilities };\n} {\n return platform;\n}\n"],"mappings":";;;;;;AAqFO,SAAS,eACd,UACwC;AACxC,SAAO;AACT;AA6BO,SAAS,oBACd,UACyB;AAuBzB,SAAO;AACT;AAyBO,SAAS,wBACd,UAC6B;AAC7B,SAAO;AACT;AA2BO,SAAS,6BACd,UACkC;AAClC,SAAO;AACT;AAkBO,SAAS,uBACd,UAC4B;AAC5B,SAAO;AACT;AAaO,SAAS,sBACd,UAC2B;AAC3B,SAAO;AACT;AAmBO,SAAS,oCACd,UACyC;AACzC,SAAO;AACT;AAYO,SAAS,8BACd,UACmC;AACnC,SAAO;AACT;AAKO,SAAS,+BACd,UACoC;AACpC,SAAO;AACT;AAKO,SAAS,iCACd,UACsC;AACtC,SAAO;AACT;AAKO,SAAS,+BACd,UACoC;AACpC,SAAO;AACT;AAKO,SAAS,4BACd,UACiC;AACjC,SAAO;AACT;AAKO,SAAS,8BACd,UACmC;AACnC,SAAO;AACT;AAKO,SAAS,0BACd,UAC+B;AAC/B,SAAO;AACT;AAoCO,SAAS,6BACd,UAKA;AACA,SAAO;AACT;","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../../../src/lib/server/decisioning/platform-helpers.ts"],"sourcesContent":["/**\n * Identity helpers for `createAdcpServerFromPlatform` adopters who build their\n * platform as an object literal rather than a class.\n *\n * **The problem they solve:**\n *\n * `createAdcpServerFromPlatform<P extends DecisioningPlatform<any, any>>(platform: P)`\n * infers `P` from the argument, which defeats TypeScript's contextual typing for\n * method parameters inside nested object literals. Without an explicit type annotation,\n * a handler like `syncEventSources: async (req, ctx) => {...}` gets `req: unknown`.\n *\n * These helpers force a concrete `DecisioningPlatform<TConfig, TCtxMeta>` (or\n * per-specialism sub-interface) as the argument type, giving TypeScript the\n * annotation it needs to flow types into nested method bodies:\n *\n * ```ts\n * // Without helper — req: unknown\n * createAdcpServerFromPlatform({\n * sales: { syncEventSources: async (req, ctx) => { req.event_sources } }\n * }, opts);\n *\n * // With defineSalesPlatform — req: SyncEventSourcesRequest ✓\n * createAdcpServerFromPlatform({\n * sales: defineSalesPlatform<MyMeta>({\n * syncEventSources: async (req, ctx) => { req.event_sources }\n * })\n * }, opts);\n * ```\n *\n * Alternatively, the class pattern with explicit property-type annotations achieves\n * the same result without helpers:\n *\n * ```ts\n * class MySeller implements DecisioningPlatform<Config, MyMeta> {\n * sales: SalesPlatform<MyMeta> = {\n * syncEventSources: async (req, ctx) => { req.event_sources } // req typed ✓\n * };\n * }\n * ```\n *\n * Use whichever pattern fits your codebase.\n *\n * @public\n */\n\nimport type { DecisioningPlatform } from './platform';\nimport type { ComplianceTestingCapabilities } from './capabilities';\nimport type { SalesPlatform, SalesCorePlatform, SalesIngestionPlatform } from './specialisms/sales';\nimport type { AudiencePlatform } from './specialisms/audiences';\nimport type { SignalsPlatform } from './specialisms/signals';\nimport type { SponsoredIntelligencePlatform } from './specialisms/sponsored-intelligence';\nimport type { CreativeBuilderPlatform } from './specialisms/creative';\nimport type { CreativeAdServerPlatform } from './specialisms/creative-ad-server';\nimport type { CampaignGovernancePlatform } from './specialisms/campaign-governance';\nimport type { ContentStandardsPlatform } from './specialisms/content-standards';\nimport type { BrandRightsPlatform } from './specialisms/brand-rights';\nimport type { PropertyListsPlatform, CollectionListsPlatform } from './specialisms/lists';\n\n/**\n * Type-level identity for a full `DecisioningPlatform` object literal.\n *\n * Fixes TypeScript's contextual-typing gap when passing an object literal\n * directly to `createAdcpServerFromPlatform`. Wrap your platform object with\n * this helper to get typed `req` and `ctx` parameters in every handler body.\n *\n * @example\n * ```ts\n * import { createAdcpServerFromPlatform, definePlatform } from '@adcp/sdk/server';\n *\n * interface MyMeta { advertiserId: string }\n *\n * const server = createAdcpServerFromPlatform(\n * definePlatform<{ networkId: string }, MyMeta>({\n * capabilities: { specialisms: ['sales-non-guaranteed'], ... },\n * accounts: { resolve: async (ref) => ... },\n * sales: {\n * getProducts: async (req, ctx) => {\n * // req: GetProductsRequest ✓ ctx.account.ctx_metadata: MyMeta ✓\n * },\n * },\n * }),\n * { name: 'my-seller', version: '1.0.0' }\n * );\n * ```\n */\nexport function definePlatform<TConfig = unknown, TCtxMeta = Record<string, unknown>>(\n platform: DecisioningPlatform<TConfig, TCtxMeta>\n): DecisioningPlatform<TConfig, TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `SalesPlatform` sub-object.\n *\n * Use this to type-annotate the `sales` property when building inline rather\n * than with a class. Every handler method (`getProducts`, `createMediaBuy`,\n * `syncEventSources`, etc.) gets its proper typed `req` parameter.\n *\n * @example\n * ```ts\n * import { createAdcpServerFromPlatform, defineSalesPlatform } from '@adcp/sdk/server';\n *\n * interface SocialMeta { advertiserId: string; pixelId: string }\n *\n * const server = createAdcpServerFromPlatform({\n * capabilities: { specialisms: ['sales-social', 'sales-non-guaranteed'], ... },\n * accounts: { resolve: async (ref) => ... },\n * sales: defineSalesPlatform<SocialMeta>({\n * getProducts: async (req, ctx) => { ... },\n * createMediaBuy: async (req, ctx) => { ... },\n * // req is fully typed throughout ✓\n * syncEventSources: async (req, ctx) => {\n * const sources = req.event_sources ?? []; // no cast needed\n * },\n * }),\n * }, { name: 'social-seller', version: '1.0.0' });\n * ```\n */\nexport function defineSalesPlatform<TCtxMeta = Record<string, unknown>>(\n platform: SalesPlatform<TCtxMeta>\n): SalesPlatform<TCtxMeta> {\n // Identity helper — return type matches the input parameter type.\n //\n // **Post-#1341 caveat.** `SalesPlatform` methods are now optional\n // individually, so this helper's return type is effectively all-optional\n // even when the adopter passes all five core methods. Adopters claiming\n // a sales specialism with `RequiredPlatformsFor<S>`-narrowed core methods\n // (`sales-guaranteed`, `sales-non-guaranteed`, `sales-broadcast-tv`,\n // `sales-catalog-driven`) need the closed shape on the way out — this\n // helper doesn't preserve it. Two ways to keep the per-specialism type\n // narrowing under #1341:\n //\n // 1. Drop `defineSalesPlatform` and write the platform field with an\n // explicit `: SalesCorePlatform<Meta> & SalesIngestionPlatform<Meta>`\n // annotation. The TS compiler flows the contextual type into the\n // literal and `RequiredPlatformsFor<S>` enforcement holds.\n // 2. Use the new {@link defineSalesCorePlatform} for the core methods\n // and {@link defineSalesIngestionPlatform} for ingestion methods,\n // spreading both onto the `sales` field.\n //\n // Pure source-compat for adopters claiming `sales-social` (ingestion-only)\n // who don't need the per-specialism core narrowing — the helper still\n // pins TCtxMeta on the parameter so handler `ctx` is typed correctly.\n return platform;\n}\n\n/**\n * Type-level identity for the **core** sales surface — bidding +\n * media-buy lifecycle (`getProducts`, `createMediaBuy`, `updateMediaBuy`,\n * `getMediaBuyDelivery`, `getMediaBuys`). Use when claiming `sales-non-\n * guaranteed` / `sales-guaranteed` / `sales-broadcast-tv` /\n * `sales-catalog-driven` and you want compile-time enforcement of the\n * lifecycle methods without dragging in optional ingestion methods.\n *\n * Pair with {@link defineSalesIngestionPlatform} when also implementing\n * ingestion surfaces (sync_creatives, log_event, etc.) — spread the two\n * onto the platform's `sales` field.\n *\n * @example\n * ```ts\n * sales: { ...defineSalesCorePlatform<MyMeta>({\n * getProducts: async (req, ctx) => { ... },\n * createMediaBuy: async (req, ctx) => { ... },\n * updateMediaBuy: async (id, patch, ctx) => { ... },\n * getMediaBuyDelivery: async (filter, ctx) => { ... },\n * getMediaBuys: async (req, ctx) => { ... },\n * }) },\n * ```\n */\nexport function defineSalesCorePlatform<TCtxMeta = Record<string, unknown>>(\n platform: SalesCorePlatform<TCtxMeta>\n): SalesCorePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for the **ingestion** sales surface — sync surfaces\n * (`syncCreatives`, `syncCatalogs`, `syncEventSources`, `logEvent`) +\n * read/feedback (`listCreativeFormats`, `listCreatives`,\n * `providePerformanceFeedback`). Walled-garden specialisms whose value\n * surface is asset push (Meta CAPI, Snap CAPI, retail-media catalogs)\n * use this without claiming the core media-buy lifecycle. Every method\n * is optional individually — implement what your specialism's storyboard\n * exercises.\n *\n * Use this when claiming `sales-social` (no `sales-non-guaranteed`)\n * or composing `audience-sync` ingestion onto a non-media-buy seller.\n * Adopters who also accept inbound media buys spread\n * {@link defineSalesCorePlatform}'s output alongside.\n *\n * @example\n * ```ts\n * // Pure sales-social adopter — no media buys, just events + creatives.\n * sales: defineSalesIngestionPlatform<SocialMeta>({\n * syncCreatives: async (creatives, ctx) => { ... },\n * syncEventSources: async (req, ctx) => { ... },\n * logEvent: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineSalesIngestionPlatform<TCtxMeta = Record<string, unknown>>(\n platform: SalesIngestionPlatform<TCtxMeta>\n): SalesIngestionPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for an `AudiencePlatform` sub-object.\n *\n * Use when the `audiences` field is built inline. Ensures `audiences` and\n * `audienceIds` parameters are typed rather than inferred as `unknown`.\n *\n * @example\n * ```ts\n * audiences: defineAudiencePlatform<SocialMeta>({\n * syncAudiences: async (audiences, ctx) => {\n * // audiences: Audience[] ✓ ctx.account.ctx_metadata: SocialMeta ✓\n * },\n * pollAudienceStatuses: async (audienceIds, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineAudiencePlatform<TCtxMeta = Record<string, unknown>>(\n platform: AudiencePlatform<TCtxMeta>\n): AudiencePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `SignalsPlatform` sub-object.\n *\n * @example\n * ```ts\n * signals: defineSignalsPlatform<SignalsMeta>({\n * getSignals: async (req, ctx) => { ... },\n * activateSignal: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineSignalsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: SignalsPlatform<TCtxMeta>\n): SignalsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `SponsoredIntelligencePlatform` sub-object.\n * SI is both a protocol-bundle surface and an AdCP 3.1 specialism.\n * Adopters declare the implementation here; when they claim the\n * `sponsored-intelligence` specialism, the framework auto-derives\n * `'sponsored_intelligence'` into the wire-side `supported_protocols`.\n *\n * @example\n * ```ts\n * sponsoredIntelligence: defineSponsoredIntelligencePlatform<BrandMeta>({\n * getOffering: async (req, ctx) => { ... },\n * initiateSession: async (req, ctx) => { ... },\n * sendMessage: async (req, ctx) => { ... },\n * terminateSession: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineSponsoredIntelligencePlatform<TCtxMeta = Record<string, unknown>>(\n platform: SponsoredIntelligencePlatform<TCtxMeta>\n): SponsoredIntelligencePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CreativeBuilderPlatform` sub-object.\n *\n * @example\n * ```ts\n * creative: defineCreativeBuilderPlatform<CreativeMeta>({\n * buildCreative: async (req, ctx) => { ... },\n * }),\n * ```\n */\nexport function defineCreativeBuilderPlatform<TCtxMeta = Record<string, unknown>>(\n platform: CreativeBuilderPlatform<TCtxMeta>\n): CreativeBuilderPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CreativeAdServerPlatform` sub-object.\n */\nexport function defineCreativeAdServerPlatform<TCtxMeta = Record<string, unknown>>(\n platform: CreativeAdServerPlatform<TCtxMeta>\n): CreativeAdServerPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CampaignGovernancePlatform` sub-object.\n */\nexport function defineCampaignGovernancePlatform<TCtxMeta = Record<string, unknown>>(\n platform: CampaignGovernancePlatform<TCtxMeta>\n): CampaignGovernancePlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `ContentStandardsPlatform` sub-object.\n */\nexport function defineContentStandardsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: ContentStandardsPlatform<TCtxMeta>\n): ContentStandardsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `PropertyListsPlatform` sub-object.\n */\nexport function definePropertyListsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: PropertyListsPlatform<TCtxMeta>\n): PropertyListsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `CollectionListsPlatform` sub-object.\n */\nexport function defineCollectionListsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: CollectionListsPlatform<TCtxMeta>\n): CollectionListsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a `BrandRightsPlatform` sub-object.\n */\nexport function defineBrandRightsPlatform<TCtxMeta = Record<string, unknown>>(\n platform: BrandRightsPlatform<TCtxMeta>\n): BrandRightsPlatform<TCtxMeta> {\n return platform;\n}\n\n/**\n * Type-level identity for a full `DecisioningPlatform` that wires\n * `comply_test_controller`. Requires `capabilities.compliance_testing`\n * to be present in the platform object, enforcing the cap/adapter\n * pairing at compile time.\n *\n * When the returned platform is passed to `createAdcpServerFromPlatform`,\n * `RequiredOptsFor<P>` resolves to require `complyTest` in opts — so\n * both halves of the invariant are enforced without runtime-only feedback.\n *\n * @example\n * ```ts\n * import {\n * createAdcpServerFromPlatform,\n * definePlatformWithCompliance,\n * } from '@adcp/sdk/server';\n *\n * const server = createAdcpServerFromPlatform(\n * definePlatformWithCompliance<Config, Meta>({\n * capabilities: {\n * specialisms: ['sales-guaranteed'],\n * compliance_testing: {}, // required by this helper ✓\n * },\n * accounts: { resolve: async (ref) => ... },\n * sales: { ... },\n * }),\n * {\n * name: 'my-seller',\n * version: '1.0.0',\n * complyTest: { seed: { product: ... } }, // required by RequiredOptsFor<P> ✓\n * }\n * );\n * ```\n */\nexport function definePlatformWithCompliance<TConfig = unknown, TCtxMeta = Record<string, unknown>>(\n platform: DecisioningPlatform<TConfig, TCtxMeta> & {\n capabilities: { compliance_testing: ComplianceTestingCapabilities };\n }\n): DecisioningPlatform<TConfig, TCtxMeta> & {\n capabilities: { compliance_testing: ComplianceTestingCapabilities };\n} {\n return platform;\n}\n"],"mappings":"AAqFO,SAAS,eACd,UACwC;AACxC,SAAO;AACT;AA6BO,SAAS,oBACd,UACyB;AAuBzB,SAAO;AACT;AAyBO,SAAS,wBACd,UAC6B;AAC7B,SAAO;AACT;AA2BO,SAAS,6BACd,UACkC;AAClC,SAAO;AACT;AAkBO,SAAS,uBACd,UAC4B;AAC5B,SAAO;AACT;AAaO,SAAS,sBACd,UAC2B;AAC3B,SAAO;AACT;AAmBO,SAAS,oCACd,UACyC;AACzC,SAAO;AACT;AAYO,SAAS,8BACd,UACmC;AACnC,SAAO;AACT;AAKO,SAAS,+BACd,UACoC;AACpC,SAAO;AACT;AAKO,SAAS,iCACd,UACsC;AACtC,SAAO;AACT;AAKO,SAAS,+BACd,UACoC;AACpC,SAAO;AACT;AAKO,SAAS,4BACd,UACiC;AACjC,SAAO;AACT;AAKO,SAAS,8BACd,UACmC;AACnC,SAAO;AACT;AAKO,SAAS,0BACd,UAC+B;AAC/B,SAAO;AACT;AAoCO,SAAS,6BACd,UAKA;AACA,SAAO;AACT;","names":[]}
|
|
@@ -1,7 +1 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
//# sourceMappingURL=platform.mjs.map
|
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
import { AdcpError, isTaskHandoff } from "../async-outcome.mjs";
|
|
8
2
|
import {
|
|
9
3
|
detectFinalizeAction,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../../src/lib/server/decisioning/proposal/dispatch.ts"],"sourcesContent":["/**\n * Proposal-dispatch — the v1.5 framework intercept seams.\n *\n * Pure functions that the runtime calls from the wire-handler shims\n * (`getProducts`, `createMediaBuy`, `updateMediaBuy`,\n * `getMediaBuyDelivery`). Each helper short-circuits when no manager /\n * store is wired for the request, so the v1 path is preserved\n * byte-for-byte.\n *\n * Five integration points (parity with `adcp-client-python.src/adcp/decisioning/proposal_dispatch.py`):\n *\n * - {@link maybeInterceptFinalize} — `getProducts` shim. Detects\n * `refine[i].action: 'finalize'`, calls the manager's\n * `finalizeProposal`, commits the proposal, returns the wire\n * response. Returns `null` when no finalize entry / no\n * finalize-capable manager.\n * - {@link maybePersistDraftAfterGetProducts} — `getProducts` shim\n * (post-call). Walks the response's `proposals[]`, validates\n * `overlap ⊆ wire`, persists each as a draft.\n * - {@link maybeReserveProposalForCreateMediaBuy} — `createMediaBuy`\n * shim. When `proposal_id` is set, validates expiry + capability\n * overlap, reserves the proposal (`COMMITTED → CONSUMING`), returns\n * the recipes map for `ctx.recipes` hydration.\n * - {@link finalizeProposalConsumption} — `createMediaBuy` shim\n * (post-success). Promotes `CONSUMING → CONSUMED` and records the\n * `mediaBuyId` back-reference.\n * - {@link releaseProposalReservation} — `createMediaBuy` shim\n * (failure rollback). Restores `CONSUMING → COMMITTED`.\n * - {@link maybeHydrateRecipesForMediaBuyId} —\n * `updateMediaBuy` / `getMediaBuyDelivery` shims. Reverse-index\n * hydration via `getByMediaBuyId`. Re-runs capability-overlap\n * validation per Resolutions §5.\n *\n * @public\n * @packageDocumentation\n */\n\nimport { AdcpError, isTaskHandoff, type TaskHandoff } from '../async-outcome';\nimport type { GetProductsRequest, Product, Proposal } from '../../../types/tools.generated';\nimport {\n detectFinalizeAction,\n enforceProposalExpiry,\n logConsumed,\n logDraftPersisted,\n logFinalizeSucceeded,\n validateCapabilityOverlap,\n validateOverlapSubsetOfWire,\n} from './lifecycle';\nimport type { ProposalRecord, ProposalStore } from './store';\nimport type {\n FinalizeProposalRequest,\n FinalizeProposalSuccess,\n ProposalGetProductsPayload,\n ProposalManager,\n Recipe,\n} from './types';\n\n// ---------------------------------------------------------------------------\n// Capability detection\n// ---------------------------------------------------------------------------\n\n/**\n * Per Resolutions §7: framework detects finalize via method-presence +\n * `capabilities.finalize` flag. Adopters opt in by both implementing\n * AND declaring; flipping only one half is an adopter bug.\n */\nfunction hasFinalizeCapability<TRecipe extends Recipe, TCtxMeta>(\n manager: ProposalManager<TRecipe, TCtxMeta> | undefined\n): boolean {\n if (!manager) return false;\n if (!manager.capabilities.finalize) return false;\n return typeof manager.finalizeProposal === 'function';\n}\n\n// ---------------------------------------------------------------------------\n// getProducts — finalize interception\n// ---------------------------------------------------------------------------\n\n/**\n * Result of {@link maybeInterceptFinalize}.\n *\n * - `kind: 'intercepted'` — adopter's `finalizeProposal` was called.\n * Caller threads `result` and `project` through the framework's\n * standard `routeIfHandoff` so the projection callback fires\n * synchronously for sync `FinalizeProposalSuccess` returns AND\n * inside the background task for `TaskHandoff<FinalizeProposalSuccess>`\n * returns. The projection commits the proposal store, emits the\n * `proposal.finalized` log, and shapes the wire response.\n * - `kind: 'pass'` — no finalize entry / no finalize-capable manager;\n * caller continues with the standard `getProducts` dispatch.\n *\n * No special-case handling: finalize HITL inherits the framework's\n * task-lifecycle posture (cancellation, restart-via-durable-store,\n * deadline, webhook delivery) from `routeIfHandoff`, the same machinery\n * that drives `createMediaBuy` HITL and `syncCreatives` HITL.\n *\n * @public\n */\nexport type FinalizeInterceptResult<TRecipe extends Recipe = Recipe> =\n | {\n kind: 'intercepted';\n result: FinalizeProposalSuccess<TRecipe> | TaskHandoff<FinalizeProposalSuccess<TRecipe>>;\n project: (success: FinalizeProposalSuccess<TRecipe>) => Promise<ProposalGetProductsPayload>;\n }\n | { kind: 'pass' };\n\n/**\n * Intercept `buying_mode: 'refine'` requests carrying a\n * `refine[i].action: 'finalize'` entry. Hydrates the draft, calls the\n * manager's `finalizeProposal`, and returns the raw adopter result + a\n * projection callback. The runtime threads them through the framework's\n * standard `routeIfHandoff` so:\n *\n * - Sync `FinalizeProposalSuccess` returns: projection runs inline,\n * buyer sees the committed proposal in the response.\n * - HITL `TaskHandoff<FinalizeProposalSuccess>` returns: framework\n * returns the Submitted envelope to the buyer, runs the adopter's\n * handoff fn in background; projection runs when the handoff\n * resolves, commits the proposal, projects the terminal task\n * artifact.\n *\n * Same machinery as `createMediaBuy` HITL — finalize inherits whatever\n * cancellation, restart-via-durable-store, deadline, and webhook\n * delivery semantics the framework's task lifecycle provides for every\n * other unified-hybrid tool. No special-case wrapper.\n *\n * @public\n */\nexport async function maybeInterceptFinalize<TRecipe extends Recipe, TCtxMeta>(args: {\n request: GetProductsRequest;\n manager: ProposalManager<TRecipe, TCtxMeta> | undefined;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } } & Record<string, unknown>;\n}): Promise<FinalizeInterceptResult<TRecipe>> {\n const { request, manager, store, ctx } = args;\n const finalizeEntry = detectFinalizeAction(request);\n if (!finalizeEntry) return { kind: 'pass' };\n if (!hasFinalizeCapability(manager) || !store) return { kind: 'pass' };\n\n const fieldPath = `refine[${finalizeEntry.index}].proposal_id`;\n const accountId = ctx.account.id;\n const record = await store.get(finalizeEntry.proposalId, { expectedAccountId: accountId });\n if (!record) {\n throw new AdcpError('PROPOSAL_NOT_FOUND', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(finalizeEntry.proposalId)} not found. The buyer must call ` +\n `get_products with buying_mode='brief' or 'refine' to obtain a draft proposal_id ` +\n `before finalizing it.`,\n field: fieldPath,\n });\n }\n if (record.state !== 'draft') {\n throw new AdcpError('PROPOSAL_NOT_COMMITTED', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(finalizeEntry.proposalId)} is in state ` +\n `${JSON.stringify(record.state)}; only draft proposals can be finalized. ` +\n `Already-committed proposals should be accepted via create_media_buy(proposal_id=...) ` +\n `directly.`,\n field: fieldPath,\n });\n }\n\n const finalizeReq: FinalizeProposalRequest<TRecipe> = {\n proposalId: finalizeEntry.proposalId,\n recipes: record.recipes,\n proposalPayload: record.proposalPayload,\n parentRequest: request,\n ...(finalizeEntry.ask !== undefined && { ask: finalizeEntry.ask }),\n };\n\n // manager + finalizeProposal are non-undefined per hasFinalizeCapability.\n const result = await manager!.finalizeProposal!(finalizeReq, ctx as never);\n // Pre-determine the path label by checking whether the adopter\n // returned a TaskHandoff up-front. `routeIfHandoff` runs `project`\n // synchronously for the sync arm and inside the background task for\n // the handoff arm; either way, we want the log to reflect which arm\n // the adopter chose.\n const path: 'inline' | 'handoff' = isTaskHandoff(result) ? 'handoff' : 'inline';\n const finalizeProposalId = finalizeEntry.proposalId;\n\n const project = async (success: FinalizeProposalSuccess<TRecipe>): Promise<ProposalGetProductsPayload> => {\n if (!isFinalizeSuccess<TRecipe>(success)) {\n throw new AdcpError('INTERNAL_ERROR', {\n recovery: 'terminal',\n message:\n `finalizeProposal resolved to an unexpected shape; expected FinalizeProposalSuccess ` +\n `with 'proposal' and 'expiresAt' fields.`,\n });\n }\n await store.commit(finalizeProposalId, {\n expiresAt: success.expiresAt,\n proposalPayload: success.proposal,\n });\n logFinalizeSucceeded({\n proposalId: finalizeProposalId,\n accountId,\n expiresAt: success.expiresAt,\n path,\n });\n return projectFinalizeResponse({\n request,\n committedProposal: success.proposal,\n finalizeProposalId,\n });\n };\n\n return { kind: 'intercepted', result, project };\n}\n\nfunction isFinalizeSuccess<TRecipe extends Recipe>(v: unknown): v is FinalizeProposalSuccess<TRecipe> {\n if (!v || typeof v !== 'object') return false;\n const r = v as Record<string, unknown>;\n return r.proposal != null && r.expiresAt instanceof Date;\n}\n\nfunction projectFinalizeResponse(args: {\n request: GetProductsRequest;\n committedProposal: Record<string, unknown>;\n finalizeProposalId: string;\n}): ProposalGetProductsPayload {\n const refineEntries = (args.request as { refine?: ReadonlyArray<Record<string, unknown>> }).refine;\n const refinementApplied: Array<Record<string, unknown>> = [];\n if (refineEntries) {\n for (const entry of refineEntries) {\n const scope = entry.scope;\n if (scope === 'proposal') {\n refinementApplied.push({\n scope: 'proposal',\n proposal_id: typeof entry.proposal_id === 'string' ? entry.proposal_id : args.finalizeProposalId,\n status: 'applied',\n });\n } else if (scope === 'product') {\n refinementApplied.push({\n scope: 'product',\n product_id: typeof entry.product_id === 'string' ? entry.product_id : '',\n status: 'applied',\n });\n } else {\n refinementApplied.push({ scope: 'request', status: 'applied' });\n }\n }\n }\n // **Decision: `products: []` on the finalize response by design.** The\n // committed proposal carries `allocations[]` keyed by `product_id`;\n // the buyer either has the products from the prior `brief_with_proposals`\n // step (the natural flow) or fetches by id. Echoing the products here\n // would require the framework to either re-emit from the persisted\n // draft (extra wire bytes the buyer already has) or call back into the\n // adopter (extra round-trip to upstream). Buyers who explicitly want\n // products on the finalize response can fetch them via a follow-up\n // `get_products({ product_ids: [...] })` keyed off\n // `proposals[0].allocations[].product_id`.\n return {\n cache_scope: 'account',\n products: [],\n proposals: [args.committedProposal as unknown as Proposal],\n refinement_applied: refinementApplied,\n } as unknown as ProposalGetProductsPayload;\n}\n\n// ---------------------------------------------------------------------------\n// getProducts / refineProducts — post-call draft persistence\n// ---------------------------------------------------------------------------\n\n/**\n * Persist proposals returned by `getProducts` / `refineProducts` as\n * drafts in the wired {@link ProposalStore}. Validates `overlap ⊆ wire`\n * for any returned recipes before persisting.\n *\n * Quietly returns when no store is wired, no `proposals[]` in the\n * response, or no typed recipes attached to products.\n *\n * @public\n */\nexport async function maybePersistDraftAfterGetProducts<TRecipe extends Recipe>(args: {\n response: ProposalGetProductsPayload;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } };\n}): Promise<void> {\n const { response, store, ctx } = args;\n if (!store) return;\n const proposals = (response as { proposals?: ReadonlyArray<Proposal> }).proposals;\n if (!proposals || proposals.length === 0) return;\n const products = (response as { products?: ReadonlyArray<Product> }).products ?? [];\n\n for (const proposal of proposals) {\n const proposalId = (proposal as { proposal_id?: string }).proposal_id;\n if (!proposalId) continue;\n const proposalPayload = toPlainObject(proposal);\n const recipes = collectRecipesFromProducts<TRecipe>(products, proposalPayload);\n if (recipes.size > 0) {\n validateOverlapSubsetOfWire({ recipes, products });\n }\n await store.putDraft({\n proposalId,\n accountId: ctx.account.id,\n recipes,\n proposalPayload,\n });\n logDraftPersisted({\n proposalId,\n accountId: ctx.account.id,\n recipesCount: recipes.size,\n });\n }\n}\n\nfunction collectRecipesFromProducts<TRecipe extends Recipe>(\n products: readonly Product[],\n proposalPayload: Record<string, unknown>\n): Map<string, TRecipe> {\n // Filter to products referenced by the proposal's allocations[] (per\n // spec) or legacy products[] string array when present.\n let referenced: Set<string> | null = null;\n const allocations = proposalPayload.allocations;\n if (Array.isArray(allocations)) {\n referenced = new Set(\n allocations\n .map((a: unknown) => (a as { product_id?: string }).product_id)\n .filter((id): id is string => typeof id === 'string')\n );\n } else if (Array.isArray(proposalPayload.products)) {\n referenced = new Set((proposalPayload.products as unknown[]).filter((p): p is string => typeof p === 'string'));\n }\n\n const recipes = new Map<string, TRecipe>();\n for (const product of products) {\n const productId = product.product_id;\n if (!productId) continue;\n if (referenced && !referenced.has(productId)) continue;\n const implConfig = (product as { implementation_config?: unknown }).implementation_config;\n if (isRecipe(implConfig)) {\n recipes.set(productId, implConfig as TRecipe);\n }\n }\n return recipes;\n}\n\nfunction isRecipe(v: unknown): boolean {\n return v != null && typeof v === 'object' && typeof (v as { recipe_kind?: unknown }).recipe_kind === 'string';\n}\n\nfunction toPlainObject(v: unknown): Record<string, unknown> {\n if (v == null || typeof v !== 'object') return {};\n // Deep clone via JSON to drop class-instance prototypes — the stored\n // payload must round-trip through a durable backing.\n return JSON.parse(JSON.stringify(v)) as Record<string, unknown>;\n}\n\n// ---------------------------------------------------------------------------\n// createMediaBuy — recipe hydration on proposal_id\n// ---------------------------------------------------------------------------\n\n/**\n * Result of {@link maybeReserveProposalForCreateMediaBuy}.\n *\n * - `record` — the reserved {@link ProposalRecord}. Caller threads\n * `recipes` onto `ctx.recipes` and calls\n * {@link finalizeProposalConsumption} on adapter success or\n * {@link releaseProposalReservation} on failure.\n * - `null` — request has no `proposal_id`, no store wired, or the\n * framework didn't intercept (v1 path).\n *\n * @public\n */\nexport type ReservedProposal<TRecipe extends Recipe> = ProposalRecord<TRecipe>;\n\n/**\n * Reserve the proposal for consumption and hydrate `ctx.recipes`.\n *\n * Atomic CAS via {@link ProposalStore.tryReserveConsumption} — the\n * proposal transitions `COMMITTED → CONSUMING` before the adapter runs.\n * Two parallel `createMediaBuy(proposal_id=X)` calls cannot both\n * reserve; the loser raises `PROPOSAL_NOT_COMMITTED`.\n *\n * Validates per § D7 (expiry) BEFORE reserving — an expired proposal\n * surfaces `PROPOSAL_EXPIRED` without flipping the state.\n *\n * @public\n */\nexport async function maybeReserveProposalForCreateMediaBuy<TRecipe extends Recipe, TCtxMeta>(args: {\n request: { proposal_id?: string; packages?: ReadonlyArray<unknown> } & Record<string, unknown>;\n manager: ProposalManager<TRecipe, TCtxMeta> | undefined;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } };\n now?: Date;\n}): Promise<ReservedProposal<TRecipe> | null> {\n const { request, manager, store, ctx, now } = args;\n const proposalId = request.proposal_id;\n if (!proposalId || !store) return null;\n const graceSeconds = manager?.capabilities.expiresAtGraceSeconds ?? 0;\n\n // Expiry check BEFORE reserving — keep the buyer's slot uncommitted\n // when telling them they're expired.\n await enforceProposalExpiry(proposalId, {\n proposalStore: store,\n expectedAccountId: ctx.account.id,\n graceSeconds,\n ...(now && { now }),\n });\n\n const reserved = await store.tryReserveConsumption(proposalId, {\n expectedAccountId: ctx.account.id,\n });\n\n // Capability-overlap gate per D4. Buyer's packages may be empty when\n // proposal_id is set (the spec allows the seller to derive packages\n // from allocations); skip the gate in that case.\n const packages = request.packages;\n if (packages && Array.isArray(packages) && packages.length > 0) {\n validateCapabilityOverlap({\n packages: packages as never,\n recipes: reserved.recipes,\n });\n }\n\n return reserved;\n}\n\n/**\n * Promote `CONSUMING → CONSUMED` after the adapter's `createMediaBuy`\n * succeeded.\n *\n * @public\n */\nexport async function finalizeProposalConsumption<TRecipe extends Recipe>(args: {\n store: ProposalStore<TRecipe> | undefined;\n record: ReservedProposal<TRecipe>;\n mediaBuyId: string;\n}): Promise<void> {\n const { store, record, mediaBuyId } = args;\n if (!store) return;\n await store.finalizeConsumption(record.proposalId, {\n mediaBuyId,\n expectedAccountId: record.accountId,\n });\n logConsumed({\n proposalId: record.proposalId,\n accountId: record.accountId,\n mediaBuyId,\n });\n}\n\n/**\n * Roll back the reservation: `CONSUMING → COMMITTED`. Best-effort.\n *\n * @public\n */\nexport async function releaseProposalReservation<TRecipe extends Recipe>(args: {\n store: ProposalStore<TRecipe> | undefined;\n record: ReservedProposal<TRecipe>;\n logger?: { warn(message: string): void };\n}): Promise<void> {\n const { store, record, logger } = args;\n if (!store) return;\n try {\n await store.releaseConsumption(record.proposalId, {\n expectedAccountId: record.accountId,\n });\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n logger?.warn(\n `[adcp/decisioning] failed to release consumption reservation for proposal ` +\n `${record.proposalId}: ${message}. The record may stay in CONSUMING until eviction.`\n );\n }\n}\n\n// ---------------------------------------------------------------------------\n// updateMediaBuy / getMediaBuyDelivery — reverse-index recipe hydration\n// ---------------------------------------------------------------------------\n\n/**\n * Hydrate `ctx.recipes` for post-acceptance buy operations via the\n * `getByMediaBuyId` reverse-index. Returns the record (so the caller\n * can re-validate overlap if a packages-shaped patch is provided);\n * returns `null` when no proposal backs this buy.\n *\n * Per Resolutions §5: re-validates capability overlap on every call\n * with packages.\n *\n * @public\n */\nexport async function maybeHydrateRecipesForMediaBuyId<TRecipe extends Recipe>(args: {\n mediaBuyId: string | undefined;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } };\n packages?: ReadonlyArray<unknown>;\n}): Promise<ProposalRecord<TRecipe> | null> {\n const { mediaBuyId, store, ctx, packages } = args;\n if (!mediaBuyId || !store) return null;\n const record = await store.getByMediaBuyId(mediaBuyId, {\n expectedAccountId: ctx.account.id,\n });\n if (!record) return null;\n if (packages && Array.isArray(packages) && packages.length > 0) {\n validateCapabilityOverlap({\n packages: packages as never,\n recipes: record.recipes,\n });\n }\n return record;\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../../../../src/lib/server/decisioning/proposal/dispatch.ts"],"sourcesContent":["/**\n * Proposal-dispatch — the v1.5 framework intercept seams.\n *\n * Pure functions that the runtime calls from the wire-handler shims\n * (`getProducts`, `createMediaBuy`, `updateMediaBuy`,\n * `getMediaBuyDelivery`). Each helper short-circuits when no manager /\n * store is wired for the request, so the v1 path is preserved\n * byte-for-byte.\n *\n * Five integration points (parity with `adcp-client-python.src/adcp/decisioning/proposal_dispatch.py`):\n *\n * - {@link maybeInterceptFinalize} — `getProducts` shim. Detects\n * `refine[i].action: 'finalize'`, calls the manager's\n * `finalizeProposal`, commits the proposal, returns the wire\n * response. Returns `null` when no finalize entry / no\n * finalize-capable manager.\n * - {@link maybePersistDraftAfterGetProducts} — `getProducts` shim\n * (post-call). Walks the response's `proposals[]`, validates\n * `overlap ⊆ wire`, persists each as a draft.\n * - {@link maybeReserveProposalForCreateMediaBuy} — `createMediaBuy`\n * shim. When `proposal_id` is set, validates expiry + capability\n * overlap, reserves the proposal (`COMMITTED → CONSUMING`), returns\n * the recipes map for `ctx.recipes` hydration.\n * - {@link finalizeProposalConsumption} — `createMediaBuy` shim\n * (post-success). Promotes `CONSUMING → CONSUMED` and records the\n * `mediaBuyId` back-reference.\n * - {@link releaseProposalReservation} — `createMediaBuy` shim\n * (failure rollback). Restores `CONSUMING → COMMITTED`.\n * - {@link maybeHydrateRecipesForMediaBuyId} —\n * `updateMediaBuy` / `getMediaBuyDelivery` shims. Reverse-index\n * hydration via `getByMediaBuyId`. Re-runs capability-overlap\n * validation per Resolutions §5.\n *\n * @public\n * @packageDocumentation\n */\n\nimport { AdcpError, isTaskHandoff, type TaskHandoff } from '../async-outcome';\nimport type { GetProductsRequest, Product, Proposal } from '../../../types/tools.generated';\nimport {\n detectFinalizeAction,\n enforceProposalExpiry,\n logConsumed,\n logDraftPersisted,\n logFinalizeSucceeded,\n validateCapabilityOverlap,\n validateOverlapSubsetOfWire,\n} from './lifecycle';\nimport type { ProposalRecord, ProposalStore } from './store';\nimport type {\n FinalizeProposalRequest,\n FinalizeProposalSuccess,\n ProposalGetProductsPayload,\n ProposalManager,\n Recipe,\n} from './types';\n\n// ---------------------------------------------------------------------------\n// Capability detection\n// ---------------------------------------------------------------------------\n\n/**\n * Per Resolutions §7: framework detects finalize via method-presence +\n * `capabilities.finalize` flag. Adopters opt in by both implementing\n * AND declaring; flipping only one half is an adopter bug.\n */\nfunction hasFinalizeCapability<TRecipe extends Recipe, TCtxMeta>(\n manager: ProposalManager<TRecipe, TCtxMeta> | undefined\n): boolean {\n if (!manager) return false;\n if (!manager.capabilities.finalize) return false;\n return typeof manager.finalizeProposal === 'function';\n}\n\n// ---------------------------------------------------------------------------\n// getProducts — finalize interception\n// ---------------------------------------------------------------------------\n\n/**\n * Result of {@link maybeInterceptFinalize}.\n *\n * - `kind: 'intercepted'` — adopter's `finalizeProposal` was called.\n * Caller threads `result` and `project` through the framework's\n * standard `routeIfHandoff` so the projection callback fires\n * synchronously for sync `FinalizeProposalSuccess` returns AND\n * inside the background task for `TaskHandoff<FinalizeProposalSuccess>`\n * returns. The projection commits the proposal store, emits the\n * `proposal.finalized` log, and shapes the wire response.\n * - `kind: 'pass'` — no finalize entry / no finalize-capable manager;\n * caller continues with the standard `getProducts` dispatch.\n *\n * No special-case handling: finalize HITL inherits the framework's\n * task-lifecycle posture (cancellation, restart-via-durable-store,\n * deadline, webhook delivery) from `routeIfHandoff`, the same machinery\n * that drives `createMediaBuy` HITL and `syncCreatives` HITL.\n *\n * @public\n */\nexport type FinalizeInterceptResult<TRecipe extends Recipe = Recipe> =\n | {\n kind: 'intercepted';\n result: FinalizeProposalSuccess<TRecipe> | TaskHandoff<FinalizeProposalSuccess<TRecipe>>;\n project: (success: FinalizeProposalSuccess<TRecipe>) => Promise<ProposalGetProductsPayload>;\n }\n | { kind: 'pass' };\n\n/**\n * Intercept `buying_mode: 'refine'` requests carrying a\n * `refine[i].action: 'finalize'` entry. Hydrates the draft, calls the\n * manager's `finalizeProposal`, and returns the raw adopter result + a\n * projection callback. The runtime threads them through the framework's\n * standard `routeIfHandoff` so:\n *\n * - Sync `FinalizeProposalSuccess` returns: projection runs inline,\n * buyer sees the committed proposal in the response.\n * - HITL `TaskHandoff<FinalizeProposalSuccess>` returns: framework\n * returns the Submitted envelope to the buyer, runs the adopter's\n * handoff fn in background; projection runs when the handoff\n * resolves, commits the proposal, projects the terminal task\n * artifact.\n *\n * Same machinery as `createMediaBuy` HITL — finalize inherits whatever\n * cancellation, restart-via-durable-store, deadline, and webhook\n * delivery semantics the framework's task lifecycle provides for every\n * other unified-hybrid tool. No special-case wrapper.\n *\n * @public\n */\nexport async function maybeInterceptFinalize<TRecipe extends Recipe, TCtxMeta>(args: {\n request: GetProductsRequest;\n manager: ProposalManager<TRecipe, TCtxMeta> | undefined;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } } & Record<string, unknown>;\n}): Promise<FinalizeInterceptResult<TRecipe>> {\n const { request, manager, store, ctx } = args;\n const finalizeEntry = detectFinalizeAction(request);\n if (!finalizeEntry) return { kind: 'pass' };\n if (!hasFinalizeCapability(manager) || !store) return { kind: 'pass' };\n\n const fieldPath = `refine[${finalizeEntry.index}].proposal_id`;\n const accountId = ctx.account.id;\n const record = await store.get(finalizeEntry.proposalId, { expectedAccountId: accountId });\n if (!record) {\n throw new AdcpError('PROPOSAL_NOT_FOUND', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(finalizeEntry.proposalId)} not found. The buyer must call ` +\n `get_products with buying_mode='brief' or 'refine' to obtain a draft proposal_id ` +\n `before finalizing it.`,\n field: fieldPath,\n });\n }\n if (record.state !== 'draft') {\n throw new AdcpError('PROPOSAL_NOT_COMMITTED', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(finalizeEntry.proposalId)} is in state ` +\n `${JSON.stringify(record.state)}; only draft proposals can be finalized. ` +\n `Already-committed proposals should be accepted via create_media_buy(proposal_id=...) ` +\n `directly.`,\n field: fieldPath,\n });\n }\n\n const finalizeReq: FinalizeProposalRequest<TRecipe> = {\n proposalId: finalizeEntry.proposalId,\n recipes: record.recipes,\n proposalPayload: record.proposalPayload,\n parentRequest: request,\n ...(finalizeEntry.ask !== undefined && { ask: finalizeEntry.ask }),\n };\n\n // manager + finalizeProposal are non-undefined per hasFinalizeCapability.\n const result = await manager!.finalizeProposal!(finalizeReq, ctx as never);\n // Pre-determine the path label by checking whether the adopter\n // returned a TaskHandoff up-front. `routeIfHandoff` runs `project`\n // synchronously for the sync arm and inside the background task for\n // the handoff arm; either way, we want the log to reflect which arm\n // the adopter chose.\n const path: 'inline' | 'handoff' = isTaskHandoff(result) ? 'handoff' : 'inline';\n const finalizeProposalId = finalizeEntry.proposalId;\n\n const project = async (success: FinalizeProposalSuccess<TRecipe>): Promise<ProposalGetProductsPayload> => {\n if (!isFinalizeSuccess<TRecipe>(success)) {\n throw new AdcpError('INTERNAL_ERROR', {\n recovery: 'terminal',\n message:\n `finalizeProposal resolved to an unexpected shape; expected FinalizeProposalSuccess ` +\n `with 'proposal' and 'expiresAt' fields.`,\n });\n }\n await store.commit(finalizeProposalId, {\n expiresAt: success.expiresAt,\n proposalPayload: success.proposal,\n });\n logFinalizeSucceeded({\n proposalId: finalizeProposalId,\n accountId,\n expiresAt: success.expiresAt,\n path,\n });\n return projectFinalizeResponse({\n request,\n committedProposal: success.proposal,\n finalizeProposalId,\n });\n };\n\n return { kind: 'intercepted', result, project };\n}\n\nfunction isFinalizeSuccess<TRecipe extends Recipe>(v: unknown): v is FinalizeProposalSuccess<TRecipe> {\n if (!v || typeof v !== 'object') return false;\n const r = v as Record<string, unknown>;\n return r.proposal != null && r.expiresAt instanceof Date;\n}\n\nfunction projectFinalizeResponse(args: {\n request: GetProductsRequest;\n committedProposal: Record<string, unknown>;\n finalizeProposalId: string;\n}): ProposalGetProductsPayload {\n const refineEntries = (args.request as { refine?: ReadonlyArray<Record<string, unknown>> }).refine;\n const refinementApplied: Array<Record<string, unknown>> = [];\n if (refineEntries) {\n for (const entry of refineEntries) {\n const scope = entry.scope;\n if (scope === 'proposal') {\n refinementApplied.push({\n scope: 'proposal',\n proposal_id: typeof entry.proposal_id === 'string' ? entry.proposal_id : args.finalizeProposalId,\n status: 'applied',\n });\n } else if (scope === 'product') {\n refinementApplied.push({\n scope: 'product',\n product_id: typeof entry.product_id === 'string' ? entry.product_id : '',\n status: 'applied',\n });\n } else {\n refinementApplied.push({ scope: 'request', status: 'applied' });\n }\n }\n }\n // **Decision: `products: []` on the finalize response by design.** The\n // committed proposal carries `allocations[]` keyed by `product_id`;\n // the buyer either has the products from the prior `brief_with_proposals`\n // step (the natural flow) or fetches by id. Echoing the products here\n // would require the framework to either re-emit from the persisted\n // draft (extra wire bytes the buyer already has) or call back into the\n // adopter (extra round-trip to upstream). Buyers who explicitly want\n // products on the finalize response can fetch them via a follow-up\n // `get_products({ product_ids: [...] })` keyed off\n // `proposals[0].allocations[].product_id`.\n return {\n cache_scope: 'account',\n products: [],\n proposals: [args.committedProposal as unknown as Proposal],\n refinement_applied: refinementApplied,\n } as unknown as ProposalGetProductsPayload;\n}\n\n// ---------------------------------------------------------------------------\n// getProducts / refineProducts — post-call draft persistence\n// ---------------------------------------------------------------------------\n\n/**\n * Persist proposals returned by `getProducts` / `refineProducts` as\n * drafts in the wired {@link ProposalStore}. Validates `overlap ⊆ wire`\n * for any returned recipes before persisting.\n *\n * Quietly returns when no store is wired, no `proposals[]` in the\n * response, or no typed recipes attached to products.\n *\n * @public\n */\nexport async function maybePersistDraftAfterGetProducts<TRecipe extends Recipe>(args: {\n response: ProposalGetProductsPayload;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } };\n}): Promise<void> {\n const { response, store, ctx } = args;\n if (!store) return;\n const proposals = (response as { proposals?: ReadonlyArray<Proposal> }).proposals;\n if (!proposals || proposals.length === 0) return;\n const products = (response as { products?: ReadonlyArray<Product> }).products ?? [];\n\n for (const proposal of proposals) {\n const proposalId = (proposal as { proposal_id?: string }).proposal_id;\n if (!proposalId) continue;\n const proposalPayload = toPlainObject(proposal);\n const recipes = collectRecipesFromProducts<TRecipe>(products, proposalPayload);\n if (recipes.size > 0) {\n validateOverlapSubsetOfWire({ recipes, products });\n }\n await store.putDraft({\n proposalId,\n accountId: ctx.account.id,\n recipes,\n proposalPayload,\n });\n logDraftPersisted({\n proposalId,\n accountId: ctx.account.id,\n recipesCount: recipes.size,\n });\n }\n}\n\nfunction collectRecipesFromProducts<TRecipe extends Recipe>(\n products: readonly Product[],\n proposalPayload: Record<string, unknown>\n): Map<string, TRecipe> {\n // Filter to products referenced by the proposal's allocations[] (per\n // spec) or legacy products[] string array when present.\n let referenced: Set<string> | null = null;\n const allocations = proposalPayload.allocations;\n if (Array.isArray(allocations)) {\n referenced = new Set(\n allocations\n .map((a: unknown) => (a as { product_id?: string }).product_id)\n .filter((id): id is string => typeof id === 'string')\n );\n } else if (Array.isArray(proposalPayload.products)) {\n referenced = new Set((proposalPayload.products as unknown[]).filter((p): p is string => typeof p === 'string'));\n }\n\n const recipes = new Map<string, TRecipe>();\n for (const product of products) {\n const productId = product.product_id;\n if (!productId) continue;\n if (referenced && !referenced.has(productId)) continue;\n const implConfig = (product as { implementation_config?: unknown }).implementation_config;\n if (isRecipe(implConfig)) {\n recipes.set(productId, implConfig as TRecipe);\n }\n }\n return recipes;\n}\n\nfunction isRecipe(v: unknown): boolean {\n return v != null && typeof v === 'object' && typeof (v as { recipe_kind?: unknown }).recipe_kind === 'string';\n}\n\nfunction toPlainObject(v: unknown): Record<string, unknown> {\n if (v == null || typeof v !== 'object') return {};\n // Deep clone via JSON to drop class-instance prototypes — the stored\n // payload must round-trip through a durable backing.\n return JSON.parse(JSON.stringify(v)) as Record<string, unknown>;\n}\n\n// ---------------------------------------------------------------------------\n// createMediaBuy — recipe hydration on proposal_id\n// ---------------------------------------------------------------------------\n\n/**\n * Result of {@link maybeReserveProposalForCreateMediaBuy}.\n *\n * - `record` — the reserved {@link ProposalRecord}. Caller threads\n * `recipes` onto `ctx.recipes` and calls\n * {@link finalizeProposalConsumption} on adapter success or\n * {@link releaseProposalReservation} on failure.\n * - `null` — request has no `proposal_id`, no store wired, or the\n * framework didn't intercept (v1 path).\n *\n * @public\n */\nexport type ReservedProposal<TRecipe extends Recipe> = ProposalRecord<TRecipe>;\n\n/**\n * Reserve the proposal for consumption and hydrate `ctx.recipes`.\n *\n * Atomic CAS via {@link ProposalStore.tryReserveConsumption} — the\n * proposal transitions `COMMITTED → CONSUMING` before the adapter runs.\n * Two parallel `createMediaBuy(proposal_id=X)` calls cannot both\n * reserve; the loser raises `PROPOSAL_NOT_COMMITTED`.\n *\n * Validates per § D7 (expiry) BEFORE reserving — an expired proposal\n * surfaces `PROPOSAL_EXPIRED` without flipping the state.\n *\n * @public\n */\nexport async function maybeReserveProposalForCreateMediaBuy<TRecipe extends Recipe, TCtxMeta>(args: {\n request: { proposal_id?: string; packages?: ReadonlyArray<unknown> } & Record<string, unknown>;\n manager: ProposalManager<TRecipe, TCtxMeta> | undefined;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } };\n now?: Date;\n}): Promise<ReservedProposal<TRecipe> | null> {\n const { request, manager, store, ctx, now } = args;\n const proposalId = request.proposal_id;\n if (!proposalId || !store) return null;\n const graceSeconds = manager?.capabilities.expiresAtGraceSeconds ?? 0;\n\n // Expiry check BEFORE reserving — keep the buyer's slot uncommitted\n // when telling them they're expired.\n await enforceProposalExpiry(proposalId, {\n proposalStore: store,\n expectedAccountId: ctx.account.id,\n graceSeconds,\n ...(now && { now }),\n });\n\n const reserved = await store.tryReserveConsumption(proposalId, {\n expectedAccountId: ctx.account.id,\n });\n\n // Capability-overlap gate per D4. Buyer's packages may be empty when\n // proposal_id is set (the spec allows the seller to derive packages\n // from allocations); skip the gate in that case.\n const packages = request.packages;\n if (packages && Array.isArray(packages) && packages.length > 0) {\n validateCapabilityOverlap({\n packages: packages as never,\n recipes: reserved.recipes,\n });\n }\n\n return reserved;\n}\n\n/**\n * Promote `CONSUMING → CONSUMED` after the adapter's `createMediaBuy`\n * succeeded.\n *\n * @public\n */\nexport async function finalizeProposalConsumption<TRecipe extends Recipe>(args: {\n store: ProposalStore<TRecipe> | undefined;\n record: ReservedProposal<TRecipe>;\n mediaBuyId: string;\n}): Promise<void> {\n const { store, record, mediaBuyId } = args;\n if (!store) return;\n await store.finalizeConsumption(record.proposalId, {\n mediaBuyId,\n expectedAccountId: record.accountId,\n });\n logConsumed({\n proposalId: record.proposalId,\n accountId: record.accountId,\n mediaBuyId,\n });\n}\n\n/**\n * Roll back the reservation: `CONSUMING → COMMITTED`. Best-effort.\n *\n * @public\n */\nexport async function releaseProposalReservation<TRecipe extends Recipe>(args: {\n store: ProposalStore<TRecipe> | undefined;\n record: ReservedProposal<TRecipe>;\n logger?: { warn(message: string): void };\n}): Promise<void> {\n const { store, record, logger } = args;\n if (!store) return;\n try {\n await store.releaseConsumption(record.proposalId, {\n expectedAccountId: record.accountId,\n });\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n logger?.warn(\n `[adcp/decisioning] failed to release consumption reservation for proposal ` +\n `${record.proposalId}: ${message}. The record may stay in CONSUMING until eviction.`\n );\n }\n}\n\n// ---------------------------------------------------------------------------\n// updateMediaBuy / getMediaBuyDelivery — reverse-index recipe hydration\n// ---------------------------------------------------------------------------\n\n/**\n * Hydrate `ctx.recipes` for post-acceptance buy operations via the\n * `getByMediaBuyId` reverse-index. Returns the record (so the caller\n * can re-validate overlap if a packages-shaped patch is provided);\n * returns `null` when no proposal backs this buy.\n *\n * Per Resolutions §5: re-validates capability overlap on every call\n * with packages.\n *\n * @public\n */\nexport async function maybeHydrateRecipesForMediaBuyId<TRecipe extends Recipe>(args: {\n mediaBuyId: string | undefined;\n store: ProposalStore<TRecipe> | undefined;\n ctx: { account: { id: string } };\n packages?: ReadonlyArray<unknown>;\n}): Promise<ProposalRecord<TRecipe> | null> {\n const { mediaBuyId, store, ctx, packages } = args;\n if (!mediaBuyId || !store) return null;\n const record = await store.getByMediaBuyId(mediaBuyId, {\n expectedAccountId: ctx.account.id,\n });\n if (!record) return null;\n if (packages && Array.isArray(packages) && packages.length > 0) {\n validateCapabilityOverlap({\n packages: packages as never,\n recipes: record.recipes,\n });\n }\n return record;\n}\n"],"mappings":"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","names":[]}
|
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
import { validateProposalCapabilities } from "./types.mjs";
|
|
8
2
|
import { InMemoryProposalStore } from "./store.mjs";
|
|
9
3
|
import { MockProposalManager } from "./mock-manager.mjs";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../../src/lib/server/decisioning/proposal/index.ts"],"sourcesContent":["/**\n * ProposalManager — primitives for the two-platform composition.\n *\n * Splits proposal assembly (`get_products`, refine, finalize) from media-buy\n * execution (`create_media_buy`, lifecycle), mirroring `adcp-client-python`'s\n * v1.5 ProposalManager. Either side can be mock-backed independently.\n *\n * @public\n * @packageDocumentation\n */\n\nexport type {\n ProposalManager,\n ProposalCapabilities,\n ProposalSalesSpecialism,\n Recipe,\n CapabilityOverlap,\n FinalizeProposalRequest,\n FinalizeProposalSuccess,\n} from './types';\n\nexport { validateProposalCapabilities } from './types';\n\nexport type { ProposalState, ProposalRecord, ProposalStore, InMemoryProposalStoreOptions } from './store';\n\nexport { InMemoryProposalStore } from './store';\n\nexport { MockProposalManager } from './mock-manager';\nexport type { MockProposalManagerOptions } from './mock-manager';\n\nexport {\n enforceProposalExpiry,\n validateCapabilityOverlap,\n validateOverlapSubsetOfWire,\n detectFinalizeAction,\n setProposalLifecycleLogger,\n logDraftPersisted,\n logFinalizeSucceeded,\n logExpired,\n logConsumed,\n} from './lifecycle';\nexport type { FinalizeActionRef, ProposalLifecycleLogger } from './lifecycle';\n\nexport {\n maybeInterceptFinalize,\n maybePersistDraftAfterGetProducts,\n maybeReserveProposalForCreateMediaBuy,\n finalizeProposalConsumption,\n releaseProposalReservation,\n maybeHydrateRecipesForMediaBuyId,\n} from './dispatch';\nexport type { FinalizeInterceptResult, ReservedProposal } from './dispatch';\n"],"mappings":"
|
|
1
|
+
{"version":3,"sources":["../../../../../src/lib/server/decisioning/proposal/index.ts"],"sourcesContent":["/**\n * ProposalManager — primitives for the two-platform composition.\n *\n * Splits proposal assembly (`get_products`, refine, finalize) from media-buy\n * execution (`create_media_buy`, lifecycle), mirroring `adcp-client-python`'s\n * v1.5 ProposalManager. Either side can be mock-backed independently.\n *\n * @public\n * @packageDocumentation\n */\n\nexport type {\n ProposalManager,\n ProposalCapabilities,\n ProposalSalesSpecialism,\n Recipe,\n CapabilityOverlap,\n FinalizeProposalRequest,\n FinalizeProposalSuccess,\n} from './types';\n\nexport { validateProposalCapabilities } from './types';\n\nexport type { ProposalState, ProposalRecord, ProposalStore, InMemoryProposalStoreOptions } from './store';\n\nexport { InMemoryProposalStore } from './store';\n\nexport { MockProposalManager } from './mock-manager';\nexport type { MockProposalManagerOptions } from './mock-manager';\n\nexport {\n enforceProposalExpiry,\n validateCapabilityOverlap,\n validateOverlapSubsetOfWire,\n detectFinalizeAction,\n setProposalLifecycleLogger,\n logDraftPersisted,\n logFinalizeSucceeded,\n logExpired,\n logConsumed,\n} from './lifecycle';\nexport type { FinalizeActionRef, ProposalLifecycleLogger } from './lifecycle';\n\nexport {\n maybeInterceptFinalize,\n maybePersistDraftAfterGetProducts,\n maybeReserveProposalForCreateMediaBuy,\n finalizeProposalConsumption,\n releaseProposalReservation,\n maybeHydrateRecipesForMediaBuyId,\n} from './dispatch';\nexport type { FinalizeInterceptResult, ReservedProposal } from './dispatch';\n"],"mappings":"AAqBA,SAAS,oCAAoC;AAI7C,SAAS,6BAA6B;AAEtC,SAAS,2BAA2B;AAGpC;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAGP;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;","names":[]}
|
|
@@ -1,9 +1,3 @@
|
|
|
1
|
-
import { fileURLToPath as __adcpFileURLToPath } from 'node:url';
|
|
2
|
-
import { dirname as __adcpDirname } from 'node:path';
|
|
3
|
-
import { createRequire as __adcpCreateRequire } from 'node:module';
|
|
4
|
-
const __filename = __adcpFileURLToPath(import.meta.url);
|
|
5
|
-
const __dirname = __adcpDirname(__filename);
|
|
6
|
-
const require = __adcpCreateRequire(import.meta.url);
|
|
7
1
|
import { AdcpError } from "../async-outcome.mjs";
|
|
8
2
|
async function enforceProposalExpiry(proposalId, args) {
|
|
9
3
|
const { proposalStore, expectedAccountId, graceSeconds = 0, now } = args;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../../src/lib/server/decisioning/proposal/lifecycle.ts"],"sourcesContent":["/**\n * Proposal-lifecycle framework helpers — the v1.5 intercept seam.\n *\n * Sits parallel to existing dispatch helpers in `runtime/from-platform.ts`.\n * Framework intercepts at a seam, does its work, dispatches.\n *\n * Public surface (the dispatch path imports these):\n *\n * - {@link enforceProposalExpiry} — D7. Look up the committed proposal,\n * validate `state === 'committed'` and `now <= expires_at + grace`,\n * return the record.\n * - {@link validateCapabilityOverlap} — D4. Walk a buyer's\n * `create_media_buy` / `update_media_buy` request packages against\n * each recipe's `capability_overlap` and reject mismatches with\n * `INVALID_REQUEST`.\n * - {@link validateOverlapSubsetOfWire} — D4 round-4. Validate at\n * `putDraft` time that each recipe's `capability_overlap` axis is a\n * subset of the corresponding wire-declared product capabilities.\n * Mismatches throw `INTERNAL_ERROR` (adopter bug, not buyer bug).\n * - {@link detectFinalizeAction} — pull out the first finalize-action\n * refine entry from a `GetProductsRequest`.\n * - structured-log helpers per § Observability.\n *\n * Ports `adcp-client-python.src/adcp/decisioning/proposal_lifecycle.py`.\n *\n * @public\n * @packageDocumentation\n */\n\nimport { AdcpError } from '../async-outcome';\nimport type { GetProductsRequest, Product } from '../../../types/tools.generated';\nimport type { ProposalRecord, ProposalStore } from './store';\nimport type { Recipe } from './types';\n\n// ---------------------------------------------------------------------------\n// D7 — expires_at enforcement\n// ---------------------------------------------------------------------------\n\n/**\n * Validate a proposal is committed and within its hold window.\n *\n * Three failure modes mapped to spec error codes:\n *\n * - Record not found OR cross-tenant → `PROPOSAL_NOT_FOUND` (correctable).\n * Cross-tenant probes return the same error as missing IDs (no\n * principal-enumeration via id probing).\n * - State !== `'committed'` → `PROPOSAL_NOT_COMMITTED` (correctable).\n * The buyer needs to call `getProducts({ buying_mode: 'refine',\n * refine: [{ action: 'finalize' }] })` first.\n * - Committed but `now > expires_at + grace` → `PROPOSAL_EXPIRED`\n * (correctable per AdCP 3.0.6 — the buyer re-discovers via\n * `get_products` to obtain a fresh proposal).\n *\n * @public\n */\nexport async function enforceProposalExpiry<TRecipe extends Recipe>(\n proposalId: string,\n args: {\n proposalStore: ProposalStore<TRecipe>;\n expectedAccountId: string;\n graceSeconds?: number;\n now?: Date;\n }\n): Promise<ProposalRecord<TRecipe>> {\n const { proposalStore, expectedAccountId, graceSeconds = 0, now } = args;\n const record = await proposalStore.get(proposalId, { expectedAccountId });\n if (!record) {\n throw new AdcpError('PROPOSAL_NOT_FOUND', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(proposalId)} not found. The buyer must call get_products ` +\n `with buying_mode='refine' and refine=[{action:'finalize',...}] to obtain a ` +\n `committed proposal_id before referencing it on create_media_buy.`,\n field: 'proposal_id',\n });\n }\n if (record.state !== 'committed') {\n throw new AdcpError('PROPOSAL_NOT_COMMITTED', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(proposalId)} is in state ${JSON.stringify(record.state)}; ` +\n `only committed proposals can be accepted via create_media_buy. Call get_products ` +\n `with buying_mode='refine' and action='finalize' first.`,\n field: 'proposal_id',\n });\n }\n if (record.expiresAt) {\n const current = now ?? new Date();\n const deadline = record.expiresAt.getTime() + graceSeconds * 1000;\n if (current.getTime() > deadline) {\n logExpired({\n proposalId,\n accountId: record.accountId,\n now: current,\n expiresAt: record.expiresAt,\n graceSeconds,\n });\n throw new AdcpError('PROPOSAL_EXPIRED', {\n // Per AdCP 3.0.6 schemas/cache/3.0.6/enums/error-code.json,\n // PROPOSAL_EXPIRED is `correctable` — the buyer re-discovers\n // via `get_products` to obtain a fresh proposal (the hold\n // window has lapsed but the buyer can re-request).\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(proposalId)} expired at ${record.expiresAt.toISOString()}; ` +\n `create_media_buy must be called within the inventory hold window. Call get_products ` +\n `with buying_mode='refine' and action='finalize' to request a fresh hold.`,\n field: 'proposal_id',\n });\n }\n }\n return record;\n}\n\n// ---------------------------------------------------------------------------\n// D4 — capability-overlap validation\n// ---------------------------------------------------------------------------\n\ninterface PackageLike {\n product_id?: string;\n pricing_option_id?: string;\n pricing_model?: string;\n delivery_type?: string;\n signal_type?: string;\n targeting_overlay?: Record<string, unknown>;\n /**\n * Adopter-resolved pricing model — the validation reads this when\n * present. Set by the framework when it has resolved\n * `pricing_option_id` against the product's pricing options.\n */\n _resolved_pricing_model?: string;\n _resolved_delivery_type?: string;\n [k: string]: unknown;\n}\n\n/**\n * Pre-adapter validation seam: walk buyer's packages against each recipe's\n * `capability_overlap` and reject mismatches.\n *\n * Called from the framework's `create_media_buy` and `update_media_buy`\n * dispatch paths after recipes are hydrated from the {@link ProposalStore}.\n * Per D4, the framework owns this gate so every adopter doesn't write the\n * same intersection logic.\n *\n * Validation axes (per {@link CapabilityOverlap}):\n *\n * - `pricingModels` — checked against `package._resolved_pricing_model`\n * or `package.pricing_model`.\n * - `targetingDimensions` — checked against `package.targeting_overlay` keys.\n * - `deliveryTypes` — checked against `package._resolved_delivery_type`\n * or `package.delivery_type`.\n * - `signalTypes` — checked against `package.signal_type`.\n *\n * Per the design's undefined-vs-empty-set semantics: `undefined` skips the\n * gate; an explicit `Set` (including the empty set) is enforced.\n *\n * @public\n */\nexport function validateCapabilityOverlap<TRecipe extends Recipe>(args: {\n packages: readonly PackageLike[];\n recipes: ReadonlyMap<string, TRecipe>;\n fieldPathPrefix?: string;\n}): void {\n const { packages, recipes, fieldPathPrefix = 'packages' } = args;\n for (let i = 0; i < packages.length; i++) {\n const pkg = packages[i]!;\n const productId = pkg.product_id;\n if (!productId) continue;\n const recipe = recipes.get(productId);\n if (!recipe || !recipe.capability_overlap) continue;\n const overlap = recipe.capability_overlap;\n\n if (overlap.pricingModels) {\n const requested = pkg._resolved_pricing_model ?? pkg.pricing_model;\n if (requested !== undefined && !overlap.pricingModels.has(String(requested))) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested pricing_model=${JSON.stringify(requested)} on package ` +\n `${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.pricingModels=${JSON.stringify([...overlap.pricingModels].sort())}. ` +\n `The seller did not enable that pricing model for this product.`,\n field: `${fieldPathPrefix}[${i}].pricing_option_id`,\n });\n }\n }\n\n if (overlap.targetingDimensions) {\n const overlay = pkg.targeting_overlay;\n const keys = overlay && typeof overlay === 'object' ? Object.keys(overlay) : [];\n const disallowed = keys.filter(k => !overlap.targetingDimensions!.has(k));\n if (disallowed.length > 0) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested targeting dimensions ${JSON.stringify(disallowed.sort())} on ` +\n `package ${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.targetingDimensions=` +\n `${JSON.stringify([...overlap.targetingDimensions].sort())}. The seller did not ` +\n `enable those targeting dimensions for this product.`,\n field: `${fieldPathPrefix}[${i}].targeting_overlay`,\n });\n }\n }\n\n if (overlap.deliveryTypes) {\n const delivery = pkg._resolved_delivery_type ?? pkg.delivery_type;\n if (delivery !== undefined && !overlap.deliveryTypes.has(String(delivery))) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested delivery_type=${JSON.stringify(delivery)} on package ` +\n `${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.deliveryTypes=${JSON.stringify([...overlap.deliveryTypes].sort())}.`,\n field: `${fieldPathPrefix}[${i}].delivery_type`,\n });\n }\n }\n\n if (overlap.signalTypes) {\n const signalType = pkg.signal_type;\n if (signalType !== undefined && !overlap.signalTypes.has(String(signalType))) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested signal_type=${JSON.stringify(signalType)} on package ` +\n `${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.signalTypes=${JSON.stringify([...overlap.signalTypes].sort())}.`,\n field: `${fieldPathPrefix}[${i}].signal_type`,\n });\n }\n }\n }\n}\n\n/**\n * Validate `recipe.capability_overlap` is a subset of the matching product's\n * wire-declared capabilities.\n *\n * Called at `putDraft` time. Mismatches throw `INTERNAL_ERROR` — this is\n * an adopter bug (the manager declared an overlap claiming capabilities the\n * wire shape doesn't advertise), not a buyer bug.\n *\n * @public\n */\nexport function validateOverlapSubsetOfWire<TRecipe extends Recipe>(args: {\n recipes: ReadonlyMap<string, TRecipe>;\n products: readonly Product[];\n}): void {\n const productsById = new Map<string, Product>();\n for (const p of args.products) {\n if (p.product_id) productsById.set(p.product_id, p);\n }\n for (const [productId, recipe] of args.recipes) {\n if (!recipe.capability_overlap) continue;\n const product = productsById.get(productId);\n if (!product) continue; // missing-product is caught elsewhere\n const overlap = recipe.capability_overlap;\n\n if (overlap.pricingModels) {\n const wirePricing = wirePricingModels(product);\n const extras = [...overlap.pricingModels].filter(p => !wirePricing.has(p));\n if (extras.length > 0) {\n throw new AdcpError('INTERNAL_ERROR', {\n recovery: 'terminal',\n message:\n `Recipe for product ${JSON.stringify(productId)} declares ` +\n `capability_overlap.pricingModels=${JSON.stringify([...overlap.pricingModels].sort())} ` +\n `including ${JSON.stringify(extras.sort())}, but the wire product only advertises ` +\n `${JSON.stringify([...wirePricing].sort())}. The recipe's overlap must be a subset ` +\n `of the wire-declared capabilities; adopter declaration is inconsistent with the ` +\n `product shape.`,\n });\n }\n }\n\n if (overlap.deliveryTypes) {\n const wireDelivery = wireDeliveryTypes(product);\n const extras = [...overlap.deliveryTypes].filter(p => !wireDelivery.has(p));\n // Only enforce when the wire declares something — products lacking a\n // delivery_type field shouldn't trip the gate.\n if (extras.length > 0 && wireDelivery.size > 0) {\n throw new AdcpError('INTERNAL_ERROR', {\n recovery: 'terminal',\n message:\n `Recipe for product ${JSON.stringify(productId)} declares ` +\n `capability_overlap.deliveryTypes=${JSON.stringify([...overlap.deliveryTypes].sort())} ` +\n `including ${JSON.stringify(extras.sort())}, but the wire product only advertises ` +\n `${JSON.stringify([...wireDelivery].sort())}.`,\n });\n }\n }\n }\n}\n\nfunction wirePricingModels(product: Product): Set<string> {\n const out = new Set<string>();\n const pricing = (product as { pricing_options?: ReadonlyArray<{ pricing_model?: string }> }).pricing_options;\n if (!pricing) return out;\n for (const opt of pricing) {\n if (opt.pricing_model) out.add(String(opt.pricing_model));\n }\n return out;\n}\n\nfunction wireDeliveryTypes(product: Product): Set<string> {\n const dt = (product as { delivery_type?: string }).delivery_type;\n return dt ? new Set([String(dt)]) : new Set();\n}\n\n// ---------------------------------------------------------------------------\n// Finalize action detection\n// ---------------------------------------------------------------------------\n\n/**\n * Result of {@link detectFinalizeAction}: the index, proposal_id, and\n * optional ask of the first finalize-action refine entry.\n *\n * @public\n */\nexport interface FinalizeActionRef {\n index: number;\n proposalId: string;\n ask?: string;\n}\n\n/**\n * Return the first finalize-action refine entry from a\n * `GetProductsRequest`, or `null` if no finalize entry exists.\n *\n * The index points at the entry's position in `refine[]` so the framework\n * can produce indexed wire field paths (`refine[3].proposal_id`) on\n * rejection — buyers parsing the error get a precise pointer.\n *\n * Per the spec, `buying_mode: 'refine'` carries a `refine[]` array of\n * entries. Each entry has a `scope` (`request` / `product` / `proposal`)\n * and an optional `action` (`include` / `omit` / `finalize`). v1.5 only\n * intercepts `proposal`-scoped entries with `action: 'finalize'`.\n *\n * The framework processes ONE finalize entry per request; if the buyer\n * sends multiple finalize entries, only the first is processed (rest fall\n * through to the standard refine path).\n *\n * @public\n */\nexport function detectFinalizeAction(req: GetProductsRequest): FinalizeActionRef | null {\n const refine = (req as { refine?: ReadonlyArray<Record<string, unknown>> }).refine;\n if (!refine || refine.length === 0) return null;\n for (let index = 0; index < refine.length; index++) {\n const entry = refine[index]!;\n if (entry.scope === 'proposal' && entry.action === 'finalize') {\n const proposalId = entry.proposal_id;\n if (typeof proposalId === 'string' && proposalId.length > 0) {\n const ask = typeof entry.ask === 'string' ? entry.ask : undefined;\n return ask !== undefined ? { index, proposalId, ask } : { index, proposalId };\n }\n }\n }\n return null;\n}\n\n// ---------------------------------------------------------------------------\n// Structured logging — § Observability\n// ---------------------------------------------------------------------------\n\n/**\n * Logger-shaped sink for structured proposal-lifecycle events. Defaults to\n * `console.info`-style emission; the dispatch path can pass a typed logger\n * to route through the rest of the framework's logging.\n *\n * @public\n */\nexport interface ProposalLifecycleLogger {\n info(message: string, fields?: Record<string, unknown>): void;\n}\n\nlet logger: ProposalLifecycleLogger = {\n info: (message, fields) => {\n if (fields) {\n console.log(JSON.stringify({ message, ...fields }));\n } else {\n console.log(message);\n }\n },\n};\n\n/**\n * Replace the module-level logger that proposal-lifecycle structured\n * events (`proposal.draft_persisted`, `proposal.finalized`, `proposal.expired`,\n * `proposal.consumed`) emit through. Adopters wire this to their existing\n * logger (pino, bunyan, etc.) so lifecycle events route through the same\n * pipeline as the rest of their server logs. Tests use it to capture\n * structured emissions for assertion.\n *\n * @public\n */\nexport function setProposalLifecycleLogger(next: ProposalLifecycleLogger): void {\n logger = next;\n}\n\n/** `proposal.draft_persisted` event. */\nexport function logDraftPersisted(args: { proposalId: string; accountId: string; recipesCount: number }): void {\n logger.info('proposal.draft_persisted', {\n event: 'proposal.draft_persisted',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n recipes_count: args.recipesCount,\n });\n}\n\n/**\n * `proposal.finalized` event. `path` is `'inline'` or `'handoff'`.\n */\nexport function logFinalizeSucceeded(args: {\n proposalId: string;\n accountId: string;\n expiresAt: Date;\n path: 'inline' | 'handoff';\n}): void {\n logger.info('proposal.finalized', {\n event: 'proposal.finalized',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n expires_at: args.expiresAt.toISOString(),\n path: args.path,\n });\n}\n\n/** `proposal.expired` event. */\nexport function logExpired(args: {\n proposalId: string;\n accountId: string;\n now: Date;\n expiresAt: Date;\n graceSeconds: number;\n}): void {\n logger.info('proposal.expired', {\n event: 'proposal.expired',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n now: args.now.toISOString(),\n expires_at: args.expiresAt.toISOString(),\n grace_seconds: args.graceSeconds,\n });\n}\n\n/** `proposal.consumed` event. */\nexport function logConsumed(args: { proposalId: string; accountId: string; mediaBuyId: string }): void {\n logger.info('proposal.consumed', {\n event: 'proposal.consumed',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n media_buy_id: args.mediaBuyId,\n });\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../../../../src/lib/server/decisioning/proposal/lifecycle.ts"],"sourcesContent":["/**\n * Proposal-lifecycle framework helpers — the v1.5 intercept seam.\n *\n * Sits parallel to existing dispatch helpers in `runtime/from-platform.ts`.\n * Framework intercepts at a seam, does its work, dispatches.\n *\n * Public surface (the dispatch path imports these):\n *\n * - {@link enforceProposalExpiry} — D7. Look up the committed proposal,\n * validate `state === 'committed'` and `now <= expires_at + grace`,\n * return the record.\n * - {@link validateCapabilityOverlap} — D4. Walk a buyer's\n * `create_media_buy` / `update_media_buy` request packages against\n * each recipe's `capability_overlap` and reject mismatches with\n * `INVALID_REQUEST`.\n * - {@link validateOverlapSubsetOfWire} — D4 round-4. Validate at\n * `putDraft` time that each recipe's `capability_overlap` axis is a\n * subset of the corresponding wire-declared product capabilities.\n * Mismatches throw `INTERNAL_ERROR` (adopter bug, not buyer bug).\n * - {@link detectFinalizeAction} — pull out the first finalize-action\n * refine entry from a `GetProductsRequest`.\n * - structured-log helpers per § Observability.\n *\n * Ports `adcp-client-python.src/adcp/decisioning/proposal_lifecycle.py`.\n *\n * @public\n * @packageDocumentation\n */\n\nimport { AdcpError } from '../async-outcome';\nimport type { GetProductsRequest, Product } from '../../../types/tools.generated';\nimport type { ProposalRecord, ProposalStore } from './store';\nimport type { Recipe } from './types';\n\n// ---------------------------------------------------------------------------\n// D7 — expires_at enforcement\n// ---------------------------------------------------------------------------\n\n/**\n * Validate a proposal is committed and within its hold window.\n *\n * Three failure modes mapped to spec error codes:\n *\n * - Record not found OR cross-tenant → `PROPOSAL_NOT_FOUND` (correctable).\n * Cross-tenant probes return the same error as missing IDs (no\n * principal-enumeration via id probing).\n * - State !== `'committed'` → `PROPOSAL_NOT_COMMITTED` (correctable).\n * The buyer needs to call `getProducts({ buying_mode: 'refine',\n * refine: [{ action: 'finalize' }] })` first.\n * - Committed but `now > expires_at + grace` → `PROPOSAL_EXPIRED`\n * (correctable per AdCP 3.0.6 — the buyer re-discovers via\n * `get_products` to obtain a fresh proposal).\n *\n * @public\n */\nexport async function enforceProposalExpiry<TRecipe extends Recipe>(\n proposalId: string,\n args: {\n proposalStore: ProposalStore<TRecipe>;\n expectedAccountId: string;\n graceSeconds?: number;\n now?: Date;\n }\n): Promise<ProposalRecord<TRecipe>> {\n const { proposalStore, expectedAccountId, graceSeconds = 0, now } = args;\n const record = await proposalStore.get(proposalId, { expectedAccountId });\n if (!record) {\n throw new AdcpError('PROPOSAL_NOT_FOUND', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(proposalId)} not found. The buyer must call get_products ` +\n `with buying_mode='refine' and refine=[{action:'finalize',...}] to obtain a ` +\n `committed proposal_id before referencing it on create_media_buy.`,\n field: 'proposal_id',\n });\n }\n if (record.state !== 'committed') {\n throw new AdcpError('PROPOSAL_NOT_COMMITTED', {\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(proposalId)} is in state ${JSON.stringify(record.state)}; ` +\n `only committed proposals can be accepted via create_media_buy. Call get_products ` +\n `with buying_mode='refine' and action='finalize' first.`,\n field: 'proposal_id',\n });\n }\n if (record.expiresAt) {\n const current = now ?? new Date();\n const deadline = record.expiresAt.getTime() + graceSeconds * 1000;\n if (current.getTime() > deadline) {\n logExpired({\n proposalId,\n accountId: record.accountId,\n now: current,\n expiresAt: record.expiresAt,\n graceSeconds,\n });\n throw new AdcpError('PROPOSAL_EXPIRED', {\n // Per AdCP 3.0.6 schemas/cache/3.0.6/enums/error-code.json,\n // PROPOSAL_EXPIRED is `correctable` — the buyer re-discovers\n // via `get_products` to obtain a fresh proposal (the hold\n // window has lapsed but the buyer can re-request).\n recovery: 'correctable',\n message:\n `Proposal ${JSON.stringify(proposalId)} expired at ${record.expiresAt.toISOString()}; ` +\n `create_media_buy must be called within the inventory hold window. Call get_products ` +\n `with buying_mode='refine' and action='finalize' to request a fresh hold.`,\n field: 'proposal_id',\n });\n }\n }\n return record;\n}\n\n// ---------------------------------------------------------------------------\n// D4 — capability-overlap validation\n// ---------------------------------------------------------------------------\n\ninterface PackageLike {\n product_id?: string;\n pricing_option_id?: string;\n pricing_model?: string;\n delivery_type?: string;\n signal_type?: string;\n targeting_overlay?: Record<string, unknown>;\n /**\n * Adopter-resolved pricing model — the validation reads this when\n * present. Set by the framework when it has resolved\n * `pricing_option_id` against the product's pricing options.\n */\n _resolved_pricing_model?: string;\n _resolved_delivery_type?: string;\n [k: string]: unknown;\n}\n\n/**\n * Pre-adapter validation seam: walk buyer's packages against each recipe's\n * `capability_overlap` and reject mismatches.\n *\n * Called from the framework's `create_media_buy` and `update_media_buy`\n * dispatch paths after recipes are hydrated from the {@link ProposalStore}.\n * Per D4, the framework owns this gate so every adopter doesn't write the\n * same intersection logic.\n *\n * Validation axes (per {@link CapabilityOverlap}):\n *\n * - `pricingModels` — checked against `package._resolved_pricing_model`\n * or `package.pricing_model`.\n * - `targetingDimensions` — checked against `package.targeting_overlay` keys.\n * - `deliveryTypes` — checked against `package._resolved_delivery_type`\n * or `package.delivery_type`.\n * - `signalTypes` — checked against `package.signal_type`.\n *\n * Per the design's undefined-vs-empty-set semantics: `undefined` skips the\n * gate; an explicit `Set` (including the empty set) is enforced.\n *\n * @public\n */\nexport function validateCapabilityOverlap<TRecipe extends Recipe>(args: {\n packages: readonly PackageLike[];\n recipes: ReadonlyMap<string, TRecipe>;\n fieldPathPrefix?: string;\n}): void {\n const { packages, recipes, fieldPathPrefix = 'packages' } = args;\n for (let i = 0; i < packages.length; i++) {\n const pkg = packages[i]!;\n const productId = pkg.product_id;\n if (!productId) continue;\n const recipe = recipes.get(productId);\n if (!recipe || !recipe.capability_overlap) continue;\n const overlap = recipe.capability_overlap;\n\n if (overlap.pricingModels) {\n const requested = pkg._resolved_pricing_model ?? pkg.pricing_model;\n if (requested !== undefined && !overlap.pricingModels.has(String(requested))) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested pricing_model=${JSON.stringify(requested)} on package ` +\n `${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.pricingModels=${JSON.stringify([...overlap.pricingModels].sort())}. ` +\n `The seller did not enable that pricing model for this product.`,\n field: `${fieldPathPrefix}[${i}].pricing_option_id`,\n });\n }\n }\n\n if (overlap.targetingDimensions) {\n const overlay = pkg.targeting_overlay;\n const keys = overlay && typeof overlay === 'object' ? Object.keys(overlay) : [];\n const disallowed = keys.filter(k => !overlap.targetingDimensions!.has(k));\n if (disallowed.length > 0) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested targeting dimensions ${JSON.stringify(disallowed.sort())} on ` +\n `package ${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.targetingDimensions=` +\n `${JSON.stringify([...overlap.targetingDimensions].sort())}. The seller did not ` +\n `enable those targeting dimensions for this product.`,\n field: `${fieldPathPrefix}[${i}].targeting_overlay`,\n });\n }\n }\n\n if (overlap.deliveryTypes) {\n const delivery = pkg._resolved_delivery_type ?? pkg.delivery_type;\n if (delivery !== undefined && !overlap.deliveryTypes.has(String(delivery))) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested delivery_type=${JSON.stringify(delivery)} on package ` +\n `${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.deliveryTypes=${JSON.stringify([...overlap.deliveryTypes].sort())}.`,\n field: `${fieldPathPrefix}[${i}].delivery_type`,\n });\n }\n }\n\n if (overlap.signalTypes) {\n const signalType = pkg.signal_type;\n if (signalType !== undefined && !overlap.signalTypes.has(String(signalType))) {\n throw new AdcpError('INVALID_REQUEST', {\n recovery: 'terminal',\n message:\n `Buyer requested signal_type=${JSON.stringify(signalType)} on package ` +\n `${JSON.stringify(productId)}, but this product's recipe declares ` +\n `capability_overlap.signalTypes=${JSON.stringify([...overlap.signalTypes].sort())}.`,\n field: `${fieldPathPrefix}[${i}].signal_type`,\n });\n }\n }\n }\n}\n\n/**\n * Validate `recipe.capability_overlap` is a subset of the matching product's\n * wire-declared capabilities.\n *\n * Called at `putDraft` time. Mismatches throw `INTERNAL_ERROR` — this is\n * an adopter bug (the manager declared an overlap claiming capabilities the\n * wire shape doesn't advertise), not a buyer bug.\n *\n * @public\n */\nexport function validateOverlapSubsetOfWire<TRecipe extends Recipe>(args: {\n recipes: ReadonlyMap<string, TRecipe>;\n products: readonly Product[];\n}): void {\n const productsById = new Map<string, Product>();\n for (const p of args.products) {\n if (p.product_id) productsById.set(p.product_id, p);\n }\n for (const [productId, recipe] of args.recipes) {\n if (!recipe.capability_overlap) continue;\n const product = productsById.get(productId);\n if (!product) continue; // missing-product is caught elsewhere\n const overlap = recipe.capability_overlap;\n\n if (overlap.pricingModels) {\n const wirePricing = wirePricingModels(product);\n const extras = [...overlap.pricingModels].filter(p => !wirePricing.has(p));\n if (extras.length > 0) {\n throw new AdcpError('INTERNAL_ERROR', {\n recovery: 'terminal',\n message:\n `Recipe for product ${JSON.stringify(productId)} declares ` +\n `capability_overlap.pricingModels=${JSON.stringify([...overlap.pricingModels].sort())} ` +\n `including ${JSON.stringify(extras.sort())}, but the wire product only advertises ` +\n `${JSON.stringify([...wirePricing].sort())}. The recipe's overlap must be a subset ` +\n `of the wire-declared capabilities; adopter declaration is inconsistent with the ` +\n `product shape.`,\n });\n }\n }\n\n if (overlap.deliveryTypes) {\n const wireDelivery = wireDeliveryTypes(product);\n const extras = [...overlap.deliveryTypes].filter(p => !wireDelivery.has(p));\n // Only enforce when the wire declares something — products lacking a\n // delivery_type field shouldn't trip the gate.\n if (extras.length > 0 && wireDelivery.size > 0) {\n throw new AdcpError('INTERNAL_ERROR', {\n recovery: 'terminal',\n message:\n `Recipe for product ${JSON.stringify(productId)} declares ` +\n `capability_overlap.deliveryTypes=${JSON.stringify([...overlap.deliveryTypes].sort())} ` +\n `including ${JSON.stringify(extras.sort())}, but the wire product only advertises ` +\n `${JSON.stringify([...wireDelivery].sort())}.`,\n });\n }\n }\n }\n}\n\nfunction wirePricingModels(product: Product): Set<string> {\n const out = new Set<string>();\n const pricing = (product as { pricing_options?: ReadonlyArray<{ pricing_model?: string }> }).pricing_options;\n if (!pricing) return out;\n for (const opt of pricing) {\n if (opt.pricing_model) out.add(String(opt.pricing_model));\n }\n return out;\n}\n\nfunction wireDeliveryTypes(product: Product): Set<string> {\n const dt = (product as { delivery_type?: string }).delivery_type;\n return dt ? new Set([String(dt)]) : new Set();\n}\n\n// ---------------------------------------------------------------------------\n// Finalize action detection\n// ---------------------------------------------------------------------------\n\n/**\n * Result of {@link detectFinalizeAction}: the index, proposal_id, and\n * optional ask of the first finalize-action refine entry.\n *\n * @public\n */\nexport interface FinalizeActionRef {\n index: number;\n proposalId: string;\n ask?: string;\n}\n\n/**\n * Return the first finalize-action refine entry from a\n * `GetProductsRequest`, or `null` if no finalize entry exists.\n *\n * The index points at the entry's position in `refine[]` so the framework\n * can produce indexed wire field paths (`refine[3].proposal_id`) on\n * rejection — buyers parsing the error get a precise pointer.\n *\n * Per the spec, `buying_mode: 'refine'` carries a `refine[]` array of\n * entries. Each entry has a `scope` (`request` / `product` / `proposal`)\n * and an optional `action` (`include` / `omit` / `finalize`). v1.5 only\n * intercepts `proposal`-scoped entries with `action: 'finalize'`.\n *\n * The framework processes ONE finalize entry per request; if the buyer\n * sends multiple finalize entries, only the first is processed (rest fall\n * through to the standard refine path).\n *\n * @public\n */\nexport function detectFinalizeAction(req: GetProductsRequest): FinalizeActionRef | null {\n const refine = (req as { refine?: ReadonlyArray<Record<string, unknown>> }).refine;\n if (!refine || refine.length === 0) return null;\n for (let index = 0; index < refine.length; index++) {\n const entry = refine[index]!;\n if (entry.scope === 'proposal' && entry.action === 'finalize') {\n const proposalId = entry.proposal_id;\n if (typeof proposalId === 'string' && proposalId.length > 0) {\n const ask = typeof entry.ask === 'string' ? entry.ask : undefined;\n return ask !== undefined ? { index, proposalId, ask } : { index, proposalId };\n }\n }\n }\n return null;\n}\n\n// ---------------------------------------------------------------------------\n// Structured logging — § Observability\n// ---------------------------------------------------------------------------\n\n/**\n * Logger-shaped sink for structured proposal-lifecycle events. Defaults to\n * `console.info`-style emission; the dispatch path can pass a typed logger\n * to route through the rest of the framework's logging.\n *\n * @public\n */\nexport interface ProposalLifecycleLogger {\n info(message: string, fields?: Record<string, unknown>): void;\n}\n\nlet logger: ProposalLifecycleLogger = {\n info: (message, fields) => {\n if (fields) {\n console.log(JSON.stringify({ message, ...fields }));\n } else {\n console.log(message);\n }\n },\n};\n\n/**\n * Replace the module-level logger that proposal-lifecycle structured\n * events (`proposal.draft_persisted`, `proposal.finalized`, `proposal.expired`,\n * `proposal.consumed`) emit through. Adopters wire this to their existing\n * logger (pino, bunyan, etc.) so lifecycle events route through the same\n * pipeline as the rest of their server logs. Tests use it to capture\n * structured emissions for assertion.\n *\n * @public\n */\nexport function setProposalLifecycleLogger(next: ProposalLifecycleLogger): void {\n logger = next;\n}\n\n/** `proposal.draft_persisted` event. */\nexport function logDraftPersisted(args: { proposalId: string; accountId: string; recipesCount: number }): void {\n logger.info('proposal.draft_persisted', {\n event: 'proposal.draft_persisted',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n recipes_count: args.recipesCount,\n });\n}\n\n/**\n * `proposal.finalized` event. `path` is `'inline'` or `'handoff'`.\n */\nexport function logFinalizeSucceeded(args: {\n proposalId: string;\n accountId: string;\n expiresAt: Date;\n path: 'inline' | 'handoff';\n}): void {\n logger.info('proposal.finalized', {\n event: 'proposal.finalized',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n expires_at: args.expiresAt.toISOString(),\n path: args.path,\n });\n}\n\n/** `proposal.expired` event. */\nexport function logExpired(args: {\n proposalId: string;\n accountId: string;\n now: Date;\n expiresAt: Date;\n graceSeconds: number;\n}): void {\n logger.info('proposal.expired', {\n event: 'proposal.expired',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n now: args.now.toISOString(),\n expires_at: args.expiresAt.toISOString(),\n grace_seconds: args.graceSeconds,\n });\n}\n\n/** `proposal.consumed` event. */\nexport function logConsumed(args: { proposalId: string; accountId: string; mediaBuyId: string }): void {\n logger.info('proposal.consumed', {\n event: 'proposal.consumed',\n proposal_id: args.proposalId,\n account_id: args.accountId,\n media_buy_id: args.mediaBuyId,\n });\n}\n"],"mappings":"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","names":[]}
|