@adcp/client 4.21.0 → 4.22.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (160) hide show
  1. package/AGENTS.md +278 -0
  2. package/README.md +96 -61
  3. package/bin/adcp.js +342 -4
  4. package/dist/lib/agents/index.generated.d.ts +9 -1
  5. package/dist/lib/agents/index.generated.d.ts.map +1 -1
  6. package/dist/lib/agents/index.generated.js +12 -0
  7. package/dist/lib/agents/index.generated.js.map +1 -1
  8. package/dist/lib/core/AgentClient.d.ts.map +1 -1
  9. package/dist/lib/core/SingleAgentClient.d.ts +2 -1
  10. package/dist/lib/core/SingleAgentClient.d.ts.map +1 -1
  11. package/dist/lib/core/SingleAgentClient.js +10 -1
  12. package/dist/lib/core/SingleAgentClient.js.map +1 -1
  13. package/dist/lib/discovery/property-crawler.d.ts +4 -0
  14. package/dist/lib/discovery/property-crawler.d.ts.map +1 -1
  15. package/dist/lib/discovery/property-crawler.js +10 -2
  16. package/dist/lib/discovery/property-crawler.js.map +1 -1
  17. package/dist/lib/index.d.ts +4 -4
  18. package/dist/lib/index.d.ts.map +1 -1
  19. package/dist/lib/index.js +6 -4
  20. package/dist/lib/index.js.map +1 -1
  21. package/dist/lib/protocols/index.d.ts.map +1 -1
  22. package/dist/lib/protocols/index.js +8 -6
  23. package/dist/lib/protocols/index.js.map +1 -1
  24. package/dist/lib/protocols/mcp.d.ts.map +1 -1
  25. package/dist/lib/protocols/mcp.js +24 -11
  26. package/dist/lib/protocols/mcp.js.map +1 -1
  27. package/dist/lib/server/index.d.ts +2 -0
  28. package/dist/lib/server/index.d.ts.map +1 -1
  29. package/dist/lib/server/index.js +3 -1
  30. package/dist/lib/server/index.js.map +1 -1
  31. package/dist/lib/server/serve.d.ts +73 -0
  32. package/dist/lib/server/serve.d.ts.map +1 -0
  33. package/dist/lib/server/serve.js +94 -0
  34. package/dist/lib/server/serve.js.map +1 -0
  35. package/dist/lib/testing/client.d.ts.map +1 -1
  36. package/dist/lib/testing/client.js +1 -0
  37. package/dist/lib/testing/client.js.map +1 -1
  38. package/dist/lib/testing/compliance/comply.d.ts.map +1 -1
  39. package/dist/lib/testing/compliance/comply.js +48 -63
  40. package/dist/lib/testing/compliance/comply.js.map +1 -1
  41. package/dist/lib/testing/compliance/storyboard-tracks.d.ts +24 -0
  42. package/dist/lib/testing/compliance/storyboard-tracks.d.ts.map +1 -0
  43. package/dist/lib/testing/compliance/storyboard-tracks.js +157 -0
  44. package/dist/lib/testing/compliance/storyboard-tracks.js.map +1 -0
  45. package/dist/lib/testing/compliance/types.d.ts +1 -1
  46. package/dist/lib/testing/compliance/types.d.ts.map +1 -1
  47. package/dist/lib/testing/index.d.ts +1 -0
  48. package/dist/lib/testing/index.d.ts.map +1 -1
  49. package/dist/lib/testing/index.js +23 -1
  50. package/dist/lib/testing/index.js.map +1 -1
  51. package/dist/lib/testing/orchestrator.d.ts +8 -0
  52. package/dist/lib/testing/orchestrator.d.ts.map +1 -1
  53. package/dist/lib/testing/orchestrator.js +8 -0
  54. package/dist/lib/testing/orchestrator.js.map +1 -1
  55. package/dist/lib/testing/storyboard/context.d.ts +34 -0
  56. package/dist/lib/testing/storyboard/context.d.ts.map +1 -0
  57. package/dist/lib/testing/storyboard/context.js +257 -0
  58. package/dist/lib/testing/storyboard/context.js.map +1 -0
  59. package/dist/lib/testing/storyboard/index.d.ts +15 -0
  60. package/dist/lib/testing/storyboard/index.d.ts.map +1 -0
  61. package/dist/lib/testing/storyboard/index.js +48 -0
  62. package/dist/lib/testing/storyboard/index.js.map +1 -0
  63. package/dist/lib/testing/storyboard/loader.d.ts +53 -0
  64. package/dist/lib/testing/storyboard/loader.d.ts.map +1 -0
  65. package/dist/lib/testing/storyboard/loader.js +114 -0
  66. package/dist/lib/testing/storyboard/loader.js.map +1 -0
  67. package/dist/lib/testing/storyboard/path.d.ts +29 -0
  68. package/dist/lib/testing/storyboard/path.d.ts.map +1 -0
  69. package/dist/lib/testing/storyboard/path.js +121 -0
  70. package/dist/lib/testing/storyboard/path.js.map +1 -0
  71. package/dist/lib/testing/storyboard/request-builder.d.ts +28 -0
  72. package/dist/lib/testing/storyboard/request-builder.d.ts.map +1 -0
  73. package/dist/lib/testing/storyboard/request-builder.js +410 -0
  74. package/dist/lib/testing/storyboard/request-builder.js.map +1 -0
  75. package/dist/lib/testing/storyboard/runner.d.ts +24 -0
  76. package/dist/lib/testing/storyboard/runner.d.ts.map +1 -0
  77. package/dist/lib/testing/storyboard/runner.js +280 -0
  78. package/dist/lib/testing/storyboard/runner.js.map +1 -0
  79. package/dist/lib/testing/storyboard/task-map.d.ts +21 -0
  80. package/dist/lib/testing/storyboard/task-map.d.ts.map +1 -0
  81. package/dist/lib/testing/storyboard/task-map.js +84 -0
  82. package/dist/lib/testing/storyboard/task-map.js.map +1 -0
  83. package/dist/lib/testing/storyboard/types.d.ts +156 -0
  84. package/dist/lib/testing/storyboard/types.d.ts.map +1 -0
  85. package/dist/lib/testing/storyboard/types.js +10 -0
  86. package/dist/lib/testing/storyboard/types.js.map +1 -0
  87. package/dist/lib/testing/storyboard/validations.d.ts +17 -0
  88. package/dist/lib/testing/storyboard/validations.d.ts.map +1 -0
  89. package/dist/lib/testing/storyboard/validations.js +166 -0
  90. package/dist/lib/testing/storyboard/validations.js.map +1 -0
  91. package/dist/lib/testing/types.d.ts +2 -0
  92. package/dist/lib/testing/types.d.ts.map +1 -1
  93. package/dist/lib/types/core.generated.d.ts +2 -2
  94. package/dist/lib/types/core.generated.d.ts.map +1 -1
  95. package/dist/lib/types/core.generated.js +1 -1
  96. package/dist/lib/types/schemas.generated.d.ts +193 -34
  97. package/dist/lib/types/schemas.generated.d.ts.map +1 -1
  98. package/dist/lib/types/schemas.generated.js +87 -5
  99. package/dist/lib/types/schemas.generated.js.map +1 -1
  100. package/dist/lib/types/tools.generated.d.ts +280 -3
  101. package/dist/lib/types/tools.generated.d.ts.map +1 -1
  102. package/dist/lib/utils/response-schemas.d.ts.map +1 -1
  103. package/dist/lib/utils/response-schemas.js +34 -3
  104. package/dist/lib/utils/response-schemas.js.map +1 -1
  105. package/dist/lib/utils/validate-user-agent.d.ts +8 -0
  106. package/dist/lib/utils/validate-user-agent.d.ts.map +1 -0
  107. package/dist/lib/utils/validate-user-agent.js +15 -0
  108. package/dist/lib/utils/validate-user-agent.js.map +1 -0
  109. package/dist/lib/version.d.ts +6 -0
  110. package/dist/lib/version.d.ts.map +1 -1
  111. package/dist/lib/version.js +7 -1
  112. package/dist/lib/version.js.map +1 -1
  113. package/docs/README.md +42 -0
  114. package/docs/guides/BUILD-AN-AGENT.md +294 -0
  115. package/docs/llms.txt +634 -0
  116. package/examples/README.md +106 -0
  117. package/examples/adcp.config.json +30 -0
  118. package/examples/basic-a2a.ts +76 -0
  119. package/examples/basic-mcp.ts +50 -0
  120. package/examples/batch-preview-test.ts +266 -0
  121. package/examples/conversation-client.ts +291 -0
  122. package/examples/debug-preview-response.ts +73 -0
  123. package/examples/debug-preview-with-logging.ts +50 -0
  124. package/examples/easy-config-demo.ts +242 -0
  125. package/examples/env-config.ts +51 -0
  126. package/examples/error-compliant-server.ts +237 -0
  127. package/examples/generative-creative-demo.ts +205 -0
  128. package/examples/inspect-card-formats.ts +161 -0
  129. package/examples/logger-usage.ts +165 -0
  130. package/examples/oauth-cli-example.ts +154 -0
  131. package/examples/pr78-async-patterns-demo.ts +247 -0
  132. package/examples/signals-agent.ts +163 -0
  133. package/examples/simple-getting-started.ts +225 -0
  134. package/examples/simple-protocol-demo.ts +75 -0
  135. package/examples/test-helpers-demo.ts +239 -0
  136. package/examples/zod-validation-example.ts +126 -0
  137. package/package.json +12 -2
  138. package/skills/adcp/SKILL.md +13 -2
  139. package/storyboards/audience_sync.yaml +199 -0
  140. package/storyboards/behavioral_analysis.yaml +244 -0
  141. package/storyboards/brand_rights.yaml +131 -0
  142. package/storyboards/creative_ad_server.yaml +171 -0
  143. package/storyboards/creative_sales_agent.yaml +169 -0
  144. package/storyboards/creative_template.yaml +306 -0
  145. package/storyboards/deterministic_testing.yaml +925 -0
  146. package/storyboards/error_compliance.yaml +231 -0
  147. package/storyboards/governance_content_standards.yaml +213 -0
  148. package/storyboards/governance_property_lists.yaml +372 -0
  149. package/storyboards/media_buy_catalog_creative.yaml +457 -0
  150. package/storyboards/media_buy_governance_escalation.yaml +467 -0
  151. package/storyboards/media_buy_guaranteed_approval.yaml +396 -0
  152. package/storyboards/media_buy_non_guaranteed.yaml +288 -0
  153. package/storyboards/media_buy_proposal_mode.yaml +369 -0
  154. package/storyboards/media_buy_seller.yaml +560 -0
  155. package/storyboards/media_buy_state_machine.yaml +254 -0
  156. package/storyboards/schema.yaml +65 -0
  157. package/storyboards/schema_validation.yaml +166 -0
  158. package/storyboards/si_session.yaml +384 -0
  159. package/storyboards/signal_marketplace.yaml +283 -0
  160. package/storyboards/signal_owned.yaml +211 -0
@@ -0,0 +1,106 @@
1
+ # AdCP Client Examples
2
+
3
+ This directory contains practical examples of how to use the `@adcp/client` library.
4
+
5
+ ## Examples
6
+
7
+ ### Basic Usage
8
+
9
+ - **`basic-mcp.ts`** - Simple MCP protocol client usage
10
+ - **`basic-a2a.ts`** - Simple A2A protocol client usage with multi-agent testing
11
+ - **`env-config.ts`** - Loading agent configuration from environment variables
12
+ - **`conversation-client.ts`** - Conversation-aware client with input handlers
13
+
14
+ ### Running Examples
15
+
16
+ ```bash
17
+ # Install dependencies
18
+ npm install
19
+
20
+ # Set up environment variables
21
+ export A2A_AUTH_TOKEN=your-token
22
+ export MCP_AUTH_TOKEN=your-token
23
+
24
+ # Run TypeScript examples directly
25
+ npx tsx examples/basic-mcp.ts
26
+ npx tsx examples/basic-a2a.ts
27
+ npx tsx examples/env-config.ts
28
+ npx tsx examples/conversation-client.ts
29
+ ```
30
+
31
+ ## Environment Configuration
32
+
33
+ The library supports loading agent configurations from environment variables. Set `ADCP_AGENTS_CONFIG` (or `SALES_AGENTS_CONFIG`):
34
+
35
+ ```bash
36
+ ADCP_AGENTS_CONFIG='[{"id":"test-agent","name":"Test Agent","agent_uri":"https://test-agent.example.com","protocol":"mcp","auth_token":"your-token"}]'
37
+ ```
38
+
39
+ ## Library Usage Patterns
40
+
41
+ ### 1. Multi-Agent Client
42
+
43
+ ```typescript
44
+ import { ADCPMultiAgentClient, type AgentConfig } from '@adcp/client';
45
+
46
+ const agents: AgentConfig[] = [/* your agents */];
47
+ const client = new ADCPMultiAgentClient(agents);
48
+
49
+ // Single agent operation
50
+ const agent = client.agent('agent-id');
51
+ const result = await agent.getProducts({ brief: '...' });
52
+
53
+ // Multi-agent parallel operation
54
+ const results = await client.agents(['id1', 'id2']).getProducts({ brief: '...' });
55
+ ```
56
+
57
+ ### 2. Environment-based Configuration
58
+
59
+ ```typescript
60
+ import { ADCPMultiAgentClient } from '@adcp/client';
61
+
62
+ // Auto-discover from env vars and config files
63
+ const client = ADCPMultiAgentClient.fromConfig();
64
+
65
+ // Or from environment only
66
+ const client = ADCPMultiAgentClient.fromEnv();
67
+ ```
68
+
69
+ ## Available Tools
70
+
71
+ AdCP tools available on `AgentClient`:
72
+
73
+ - `getProducts()` - Discover advertising products
74
+ - `listCreativeFormats()` - Get supported creative formats
75
+ - `createMediaBuy()` - Create a media buy
76
+ - `updateMediaBuy()` - Update a media buy
77
+ - `syncCreatives()` - Sync creative assets
78
+ - `listCreatives()` - List creative assets
79
+ - `getMediaBuyDelivery()` - Get delivery performance
80
+ - `getSignals()` - Get audience signals
81
+ - `activateSignal()` - Activate audience signals
82
+ - `providePerformanceFeedback()` - Send performance feedback
83
+ - `getAdcpCapabilities()` - Get agent capabilities (v3)
84
+
85
+ ## Error Handling
86
+
87
+ ```typescript
88
+ const result = await agent.getProducts({ brief: 'test' });
89
+
90
+ if (result.success && result.status === 'completed') {
91
+ console.log('Data:', result.data);
92
+ } else {
93
+ console.log('Error:', result.error);
94
+ }
95
+ ```
96
+
97
+ ## Testing Framework
98
+
99
+ This package also includes a complete testing framework. To run the testing UI:
100
+
101
+ ```bash
102
+ npm run dev
103
+ # Open http://localhost:8080
104
+ ```
105
+
106
+ See the main README for full testing framework documentation.
@@ -0,0 +1,30 @@
1
+ {
2
+ "agents": [
3
+ {
4
+ "id": "premium-network",
5
+ "name": "Premium Ad Network",
6
+ "agent_uri": "https://premium-ads.example.com/mcp/",
7
+ "protocol": "mcp",
8
+ "auth_token": "your-premium-token-here"
9
+ },
10
+ {
11
+ "id": "budget-network",
12
+ "name": "Budget Ad Network",
13
+ "agent_uri": "https://budget-ads.example.com/a2a/",
14
+ "protocol": "a2a"
15
+ },
16
+ {
17
+ "id": "social-network",
18
+ "name": "Social Media Ad Network",
19
+ "agent_uri": "https://social-ads.example.com/mcp/",
20
+ "protocol": "mcp",
21
+ "auth_token": "your-social-token-here"
22
+ }
23
+ ],
24
+ "defaults": {
25
+ "protocol": "mcp",
26
+ "timeout": 30000,
27
+ "maxClarifications": 3,
28
+ "debug": false
29
+ }
30
+ }
@@ -0,0 +1,76 @@
1
+ // Basic A2A Client Example
2
+ import { AdCPClient, type AgentConfig } from '@adcp/client';
3
+
4
+ // Using AdCPClient with A2A protocol (recommended)
5
+ async function configuredA2AExample() {
6
+ const agent: AgentConfig = {
7
+ id: 'test-a2a-agent',
8
+ name: 'Test A2A Agent',
9
+ agent_uri: 'https://test-agent.adcontextprotocol.org',
10
+ protocol: 'a2a',
11
+ auth_token: process.env.A2A_AUTH_TOKEN,
12
+ };
13
+
14
+ const client = new AdCPClient([agent]);
15
+
16
+ try {
17
+ const agentClient = client.agent('test-a2a-agent');
18
+ const result = await agentClient.getProducts({
19
+ brief: 'Sustainable fashion brands',
20
+ promoted_offering: 'Eco-friendly clothing',
21
+ });
22
+
23
+ console.log('Test Result:', result);
24
+ } catch (error) {
25
+ console.error('Error:', error);
26
+ }
27
+ }
28
+
29
+ // Multi-agent testing
30
+ async function multiAgentExample() {
31
+ const agents: AgentConfig[] = [
32
+ {
33
+ id: 'mcp-agent',
34
+ name: 'MCP Test Agent',
35
+ agent_uri: 'https://test-agent.adcontextprotocol.org/mcp/',
36
+ protocol: 'mcp',
37
+ auth_token: process.env.MCP_AUTH_TOKEN,
38
+ },
39
+ {
40
+ id: 'a2a-agent',
41
+ name: 'A2A Test Agent',
42
+ agent_uri: 'https://test-agent.adcontextprotocol.org',
43
+ protocol: 'a2a',
44
+ auth_token: process.env.A2A_AUTH_TOKEN,
45
+ },
46
+ ];
47
+
48
+ const client = new AdCPClient(agents);
49
+
50
+ try {
51
+ const agentCollection = client.agents(['mcp-agent', 'a2a-agent']);
52
+ const results = await agentCollection.getProducts({
53
+ brief: 'Tech gadgets for remote work',
54
+ promoted_offering: 'Ergonomic workspace solutions',
55
+ });
56
+
57
+ console.log('Results from both agents:', results);
58
+ results.forEach(result => {
59
+ if (result.status === 'completed') {
60
+ console.log(`${result.metadata.agent.name}: Success`);
61
+ console.log(' Data:', result.data);
62
+ } else {
63
+ console.log(`${result.metadata.agent.name}: Failed`);
64
+ console.log(' Error:', result.error);
65
+ }
66
+ });
67
+ } catch (error) {
68
+ console.error('Error:', error);
69
+ }
70
+ }
71
+
72
+ // Run examples
73
+ if (require.main === module) {
74
+ configuredA2AExample();
75
+ multiAgentExample();
76
+ }
@@ -0,0 +1,50 @@
1
+ // Basic MCP Client Example
2
+ import { createMCPClient, type AgentConfig } from '@adcp/client';
3
+
4
+ async function basicMCPExample() {
5
+ // Simple MCP client usage
6
+ const client = createMCPClient('https://test-agent.adcontextprotocol.org/mcp/', 'your-auth-token');
7
+
8
+ try {
9
+ const result = await client.callTool('get_products', {
10
+ brief: 'Looking for premium coffee brands',
11
+ promoted_offering: 'Artisan coffee blends',
12
+ });
13
+
14
+ console.log('Products:', result);
15
+ } catch (error) {
16
+ console.error('Error calling MCP agent:', error);
17
+ }
18
+ }
19
+
20
+ // Using AgentConfig with AdCPClient
21
+ import { AdCPClient } from '@adcp/client';
22
+
23
+ async function configuredMCPExample() {
24
+ const agent: AgentConfig = {
25
+ id: 'test-mcp-agent',
26
+ name: 'Test MCP Agent',
27
+ agent_uri: 'https://test-agent.adcontextprotocol.org/mcp/',
28
+ protocol: 'mcp',
29
+ auth_token: process.env.MCP_AUTH_TOKEN,
30
+ };
31
+
32
+ const client = new AdCPClient([agent]);
33
+
34
+ try {
35
+ const agentClient = client.agent('test-mcp-agent');
36
+ const result = await agentClient.getProducts({
37
+ brief: 'Sustainable fashion brands',
38
+ });
39
+
40
+ console.log('Test Result:', result);
41
+ } catch (error) {
42
+ console.error('Error:', error);
43
+ }
44
+ }
45
+
46
+ // Run examples
47
+ if (require.main === module) {
48
+ basicMCPExample();
49
+ configuredMCPExample();
50
+ }
@@ -0,0 +1,266 @@
1
+ #!/usr/bin/env tsx
2
+
3
+ /**
4
+ * Test batch preview functionality with creative agent
5
+ *
6
+ * This example demonstrates:
7
+ * 1. Creating mock products/formats with product_card/format_card manifests
8
+ * 2. Using batchPreviewProducts/batchPreviewFormats to render cards
9
+ * 3. Caching behavior
10
+ */
11
+
12
+ import { AdCPClient } from '../src/lib/core/AdCPClient';
13
+ import { batchPreviewProducts, batchPreviewFormats, clearPreviewCache } from '../src/lib/utils/preview-utils';
14
+ import type { Product, Format } from '../src/lib/types/tools.generated';
15
+
16
+ // Configuration
17
+ const CREATIVE_AGENT_URL = process.env.CREATIVE_AGENT_URL || 'https://creative.adcontextprotocol.org/mcp';
18
+ const CREATIVE_AGENT_PROTOCOL = (process.env.CREATIVE_AGENT_PROTOCOL || 'mcp') as 'mcp' | 'a2a';
19
+
20
+ async function main() {
21
+ console.log('🧪 Testing Batch Preview Functionality\n');
22
+
23
+ // Create AdCPClient for creative agent
24
+ const creativeAgent = new AdCPClient({
25
+ id: 'creative_agent',
26
+ name: 'Creative Agent',
27
+ agent_uri: CREATIVE_AGENT_URL,
28
+ protocol: CREATIVE_AGENT_PROTOCOL,
29
+ });
30
+
31
+ console.log(`šŸ“” Connected to creative agent: ${CREATIVE_AGENT_URL}`);
32
+ console.log(`šŸ”Œ Using protocol: ${CREATIVE_AGENT_PROTOCOL}\n`);
33
+
34
+ // Test 1: Batch preview products with product_card
35
+ console.log('═══════════════════════════════════════════════════════════');
36
+ console.log('Test 1: Batch Preview Products');
37
+ console.log('═══════════════════════════════════════════════════════════\n');
38
+
39
+ const testProducts: Product[] = [
40
+ {
41
+ product_id: 'test_product_1',
42
+ name: 'Premium Display Package',
43
+ description: 'High-visibility display advertising',
44
+ product_card: {
45
+ format_id: {
46
+ agent_url: CREATIVE_AGENT_URL.replace('/mcp', ''),
47
+ id: 'product_card_standard',
48
+ },
49
+ manifest: {
50
+ product_image: {
51
+ url: 'https://images.unsplash.com/photo-1460925895917-afdab827c52f?w=400&h=300',
52
+ },
53
+ product_name: {
54
+ content: 'Premium Display Package',
55
+ },
56
+ product_description: {
57
+ content:
58
+ 'High-visibility display advertising with guaranteed impressions and premium placements across our network.',
59
+ },
60
+ pricing_model: {
61
+ content: 'CPM',
62
+ },
63
+ pricing_amount: {
64
+ content: '$5,000/month',
65
+ },
66
+ pricing_currency: {
67
+ content: 'USD',
68
+ },
69
+ delivery_type: {
70
+ content: 'Guaranteed',
71
+ },
72
+ primary_asset_type: {
73
+ content: 'Display',
74
+ },
75
+ } as any,
76
+ },
77
+ },
78
+ {
79
+ product_id: 'test_product_2',
80
+ name: 'Video Advertising',
81
+ description: 'Engaging video ad placements',
82
+ product_card: {
83
+ format_id: {
84
+ agent_url: CREATIVE_AGENT_URL.replace('/mcp', ''),
85
+ id: 'product_card_standard',
86
+ },
87
+ manifest: {
88
+ product_image: {
89
+ url: 'https://images.unsplash.com/photo-1536240478700-b869070f9279?w=400&h=300',
90
+ },
91
+ product_name: {
92
+ content: 'Video Advertising',
93
+ },
94
+ product_description: {
95
+ content: 'Pre-roll and mid-roll video inventory with 15s and 30s spots in HD quality.',
96
+ },
97
+ pricing_model: {
98
+ content: 'CPCV',
99
+ },
100
+ pricing_amount: {
101
+ content: '$10,000/month',
102
+ },
103
+ pricing_currency: {
104
+ content: 'USD',
105
+ },
106
+ delivery_type: {
107
+ content: 'Standard',
108
+ },
109
+ primary_asset_type: {
110
+ content: 'Video',
111
+ },
112
+ } as any,
113
+ },
114
+ },
115
+ {
116
+ product_id: 'test_product_3',
117
+ name: 'Sponsored Content',
118
+ description: 'Native advertising opportunities',
119
+ // No product_card - should return without preview
120
+ },
121
+ ];
122
+
123
+ try {
124
+ console.log(`šŸ“¦ Testing with ${testProducts.length} products...`);
125
+ const startTime = Date.now();
126
+
127
+ const productPreviews = await batchPreviewProducts(testProducts, creativeAgent);
128
+
129
+ const elapsed = Date.now() - startTime;
130
+ console.log(`āœ… Batch preview completed in ${elapsed}ms\n`);
131
+
132
+ console.log('Results:');
133
+ productPreviews.forEach((preview, index) => {
134
+ const product = preview.item as Product;
135
+ console.log(`\n Product ${index + 1}: ${product.name}`);
136
+ if (preview.previewUrl) {
137
+ console.log(` āœ… Preview URL: ${preview.previewUrl}`);
138
+ console.log(` šŸ“ Preview ID: ${preview.previewId}`);
139
+ } else if (preview.error) {
140
+ console.log(` āŒ Error: ${preview.error}`);
141
+ } else {
142
+ console.log(` āš ļø No product_card provided`);
143
+ }
144
+ });
145
+
146
+ // Test caching
147
+ console.log('\n─────────────────────────────────────────────────────────');
148
+ console.log('Testing cache...\n');
149
+
150
+ const cacheStartTime = Date.now();
151
+ const cachedPreviews = await batchPreviewProducts(testProducts, creativeAgent);
152
+ const cacheElapsed = Date.now() - cacheStartTime;
153
+
154
+ console.log(`āœ… Cached preview completed in ${cacheElapsed}ms`);
155
+ console.log(`⚔ Speed improvement: ${Math.round((elapsed / cacheElapsed) * 100) / 100}x faster\n`);
156
+ } catch (error) {
157
+ console.error('āŒ Product preview test failed:', error);
158
+ }
159
+
160
+ // Test 2: Batch preview formats with format_card
161
+ console.log('\n═══════════════════════════════════════════════════════════');
162
+ console.log('Test 2: Batch Preview Formats');
163
+ console.log('═══════════════════════════════════════════════════════════\n');
164
+
165
+ const format1 = {
166
+ format_id: {
167
+ agent_url: 'https://example.com',
168
+ id: 'display_300x250',
169
+ },
170
+ name: 'Medium Rectangle',
171
+ description: '300x250 display banner',
172
+ type: 'display' as const,
173
+ };
174
+
175
+ const format2 = {
176
+ format_id: {
177
+ agent_url: 'https://example.com',
178
+ id: 'video_1920x1080',
179
+ },
180
+ name: 'HD Video',
181
+ description: '1920x1080 video format',
182
+ type: 'video' as const,
183
+ };
184
+
185
+ const testFormats: Format[] = [
186
+ {
187
+ ...format1,
188
+ format_card: {
189
+ format_id: {
190
+ agent_url: CREATIVE_AGENT_URL.replace('/mcp', ''),
191
+ id: 'format_card_standard',
192
+ },
193
+ manifest: {
194
+ format: {
195
+ content: JSON.stringify(format1),
196
+ },
197
+ } as any,
198
+ },
199
+ },
200
+ {
201
+ ...format2,
202
+ format_card: {
203
+ format_id: {
204
+ agent_url: CREATIVE_AGENT_URL.replace('/mcp', ''),
205
+ id: 'format_card_standard',
206
+ },
207
+ manifest: {
208
+ format: {
209
+ content: JSON.stringify(format2),
210
+ },
211
+ } as any,
212
+ },
213
+ },
214
+ ];
215
+
216
+ try {
217
+ console.log(`šŸ“¦ Testing with ${testFormats.length} formats...`);
218
+ const startTime = Date.now();
219
+
220
+ const formatPreviews = await batchPreviewFormats(testFormats, creativeAgent);
221
+
222
+ const elapsed = Date.now() - startTime;
223
+ console.log(`āœ… Batch preview completed in ${elapsed}ms\n`);
224
+
225
+ console.log('Results:');
226
+ formatPreviews.forEach((preview, index) => {
227
+ const format = preview.item as Format;
228
+ console.log(`\n Format ${index + 1}: ${format.name}`);
229
+ if (preview.previewUrl) {
230
+ console.log(` āœ… Preview URL: ${preview.previewUrl}`);
231
+ console.log(` šŸ“ Preview ID: ${preview.previewId}`);
232
+ } else if (preview.error) {
233
+ console.log(` āŒ Error: ${preview.error}`);
234
+ } else {
235
+ console.log(` āš ļø No format_card provided`);
236
+ }
237
+ });
238
+ } catch (error) {
239
+ console.error('āŒ Format preview test failed:', error);
240
+ }
241
+
242
+ // Test 3: Cache clearing
243
+ console.log('\n═══════════════════════════════════════════════════════════');
244
+ console.log('Test 3: Cache Management');
245
+ console.log('═══════════════════════════════════════════════════════════\n');
246
+
247
+ console.log('šŸ—‘ļø Clearing preview cache...');
248
+ clearPreviewCache();
249
+ console.log('āœ… Cache cleared\n');
250
+
251
+ console.log('šŸ“¦ Re-fetching products (should be slower now)...');
252
+ const noCacheStartTime = Date.now();
253
+ await batchPreviewProducts(testProducts.slice(0, 2), creativeAgent);
254
+ const noCacheElapsed = Date.now() - noCacheStartTime;
255
+ console.log(`āœ… Completed in ${noCacheElapsed}ms (cache was cleared)\n`);
256
+
257
+ console.log('═══════════════════════════════════════════════════════════');
258
+ console.log('āœ… All tests completed!');
259
+ console.log('═══════════════════════════════════════════════════════════\n');
260
+ }
261
+
262
+ // Run tests
263
+ main().catch(error => {
264
+ console.error('Fatal error:', error);
265
+ process.exit(1);
266
+ });