agentstack-sdk 0.4.2-rc1

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 (57) hide show
  1. package/dist/client/a2a/extensions/common/form.d.ts +244 -0
  2. package/dist/client/a2a/extensions/fulfillment-resolvers/build-llm-extension-fulfillment-resolver.d.ts +8 -0
  3. package/dist/client/a2a/extensions/handle-agent-card.d.ts +146 -0
  4. package/dist/client/a2a/extensions/handle-input-required.d.ts +11 -0
  5. package/dist/client/a2a/extensions/handle-task-status-update.d.ts +26 -0
  6. package/dist/client/a2a/extensions/services/embedding.d.ts +25 -0
  7. package/dist/client/a2a/extensions/services/form.d.ts +103 -0
  8. package/dist/client/a2a/extensions/services/llm.d.ts +25 -0
  9. package/dist/client/a2a/extensions/services/mcp.d.ts +46 -0
  10. package/dist/client/a2a/extensions/services/oauth-provider.d.ts +30 -0
  11. package/dist/client/a2a/extensions/services/platform.d.ts +11 -0
  12. package/dist/client/a2a/extensions/services/secrets.d.ts +28 -0
  13. package/dist/client/a2a/extensions/types.d.ts +16 -0
  14. package/dist/client/a2a/extensions/ui/agent-detail.d.ts +49 -0
  15. package/dist/client/a2a/extensions/ui/citation.d.ts +27 -0
  16. package/dist/client/a2a/extensions/ui/form-request.d.ts +11 -0
  17. package/dist/client/a2a/extensions/ui/oauth.d.ts +13 -0
  18. package/dist/client/a2a/extensions/ui/settings.d.ts +110 -0
  19. package/dist/client/a2a/extensions/ui/trajectory.d.ts +15 -0
  20. package/dist/client/a2a/extensions/utils/build-message-builder.d.ts +9 -0
  21. package/dist/client/a2a/extensions/utils.d.ts +11 -0
  22. package/dist/client/api/build-api-client.d.ts +27 -0
  23. package/dist/client/api/types.d.ts +59 -0
  24. package/dist/index.cjs +2 -0
  25. package/dist/index.cjs.map +1 -0
  26. package/dist/index.d.ts +27 -0
  27. package/dist/index.js +2 -0
  28. package/dist/index.js.map +1 -0
  29. package/dist/index.umd.js +2 -0
  30. package/dist/index.umd.js.map +1 -0
  31. package/dist/types.d.ts +10 -0
  32. package/package.json +56 -0
  33. package/src/client/a2a/extensions/common/form.ts +144 -0
  34. package/src/client/a2a/extensions/fulfillment-resolvers/build-llm-extension-fulfillment-resolver.ts +43 -0
  35. package/src/client/a2a/extensions/handle-agent-card.ts +116 -0
  36. package/src/client/a2a/extensions/handle-input-required.ts +29 -0
  37. package/src/client/a2a/extensions/handle-task-status-update.ts +74 -0
  38. package/src/client/a2a/extensions/services/embedding.ts +43 -0
  39. package/src/client/a2a/extensions/services/form.ts +31 -0
  40. package/src/client/a2a/extensions/services/llm.ts +39 -0
  41. package/src/client/a2a/extensions/services/mcp.ts +59 -0
  42. package/src/client/a2a/extensions/services/oauth-provider.ts +52 -0
  43. package/src/client/a2a/extensions/services/platform.ts +22 -0
  44. package/src/client/a2a/extensions/services/secrets.ts +46 -0
  45. package/src/client/a2a/extensions/types.ts +20 -0
  46. package/src/client/a2a/extensions/ui/agent-detail.ts +46 -0
  47. package/src/client/a2a/extensions/ui/citation.ts +30 -0
  48. package/src/client/a2a/extensions/ui/form-request.ts +18 -0
  49. package/src/client/a2a/extensions/ui/oauth.ts +21 -0
  50. package/src/client/a2a/extensions/ui/settings.ts +84 -0
  51. package/src/client/a2a/extensions/ui/trajectory.ts +23 -0
  52. package/src/client/a2a/extensions/utils/build-message-builder.ts +28 -0
  53. package/src/client/a2a/extensions/utils.ts +66 -0
  54. package/src/client/api/build-api-client.ts +74 -0
  55. package/src/client/api/types.ts +72 -0
  56. package/src/index.ts +32 -0
  57. package/src/types.ts +9 -0
@@ -0,0 +1,116 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import type { AgentCapabilities } from '@a2a-js/sdk';
7
+
8
+ import type { ContextToken } from '../../api/types';
9
+ import type { EmbeddingDemands, EmbeddingFulfillments } from './services/embedding';
10
+ import { embeddingExtension } from './services/embedding';
11
+ import type { FormDemands, FormFulfillments } from './services/form';
12
+ import { formExtension } from './services/form';
13
+ import type { LLMDemands, LLMFulfillments } from './services/llm';
14
+ import { llmExtension } from './services/llm';
15
+ import type { MCPDemands, MCPFulfillments } from './services/mcp';
16
+ import { mcpExtension } from './services/mcp';
17
+ import type { OAuthDemands, OAuthFulfillments } from './services/oauth-provider';
18
+ import { oauthProviderExtension } from './services/oauth-provider';
19
+ import { platformApiExtension } from './services/platform';
20
+ import type { SecretDemands, SecretFulfillments } from './services/secrets';
21
+ import { secretsExtension } from './services/secrets';
22
+ import { oauthRequestExtension } from './ui/oauth';
23
+ import type { SettingsDemands, SettingsFulfillments } from './ui/settings';
24
+ import { settingsExtension } from './ui/settings';
25
+ import { extractServiceExtensionDemands, fulfillServiceExtensionDemand } from './utils';
26
+
27
+ export interface Fulfillments {
28
+ llm: (demand: LLMDemands) => Promise<LLMFulfillments>;
29
+ embedding: (demand: EmbeddingDemands) => Promise<EmbeddingFulfillments>;
30
+ mcp: (demand: MCPDemands) => Promise<MCPFulfillments>;
31
+ oauth: (demand: OAuthDemands) => Promise<OAuthFulfillments>;
32
+ settings: (demand: SettingsDemands) => Promise<SettingsFulfillments>;
33
+ secrets: (demand: SecretDemands) => Promise<SecretFulfillments>;
34
+ form: (demand: FormDemands) => Promise<FormFulfillments>;
35
+ oauthRedirectUri: () => string | null;
36
+ getContextToken: () => ContextToken;
37
+ }
38
+
39
+ const mcpExtensionExtractor = extractServiceExtensionDemands(mcpExtension);
40
+ const llmExtensionExtractor = extractServiceExtensionDemands(llmExtension);
41
+ const embeddingExtensionExtractor = extractServiceExtensionDemands(embeddingExtension);
42
+ const oauthExtensionExtractor = extractServiceExtensionDemands(oauthProviderExtension);
43
+ const settingsExtensionExtractor = extractServiceExtensionDemands(settingsExtension);
44
+ const secretExtensionExtractor = extractServiceExtensionDemands(secretsExtension);
45
+ const formExtensionExtractor = extractServiceExtensionDemands(formExtension);
46
+
47
+ const fulfillMcpDemand = fulfillServiceExtensionDemand(mcpExtension);
48
+ const fulfillLlmDemand = fulfillServiceExtensionDemand(llmExtension);
49
+ const fulfillEmbeddingDemand = fulfillServiceExtensionDemand(embeddingExtension);
50
+ const fulfillOAuthDemand = fulfillServiceExtensionDemand(oauthProviderExtension);
51
+ const fulfillSettingsDemand = fulfillServiceExtensionDemand(settingsExtension);
52
+ const fulfillSecretDemand = fulfillServiceExtensionDemand(secretsExtension);
53
+ const fulfillFormDemand = fulfillServiceExtensionDemand(formExtension);
54
+
55
+ export const handleAgentCard = (agentCard: { capabilities: AgentCapabilities }) => {
56
+ const extensions = agentCard.capabilities.extensions ?? [];
57
+
58
+ const llmDemands = llmExtensionExtractor(extensions);
59
+ const embeddingDemands = embeddingExtensionExtractor(extensions);
60
+ const mcpDemands = mcpExtensionExtractor(extensions);
61
+ const oauthDemands = oauthExtensionExtractor(extensions);
62
+ const settingsDemands = settingsExtensionExtractor(extensions);
63
+ const secretDemands = secretExtensionExtractor(extensions);
64
+ const formDemands = formExtensionExtractor(extensions);
65
+
66
+ const resolveMetadata = async (fulfillments: Fulfillments) => {
67
+ let fulfilledMetadata: Record<string, unknown> = {};
68
+
69
+ fulfilledMetadata = platformApiExtension(fulfilledMetadata, fulfillments.getContextToken());
70
+
71
+ if (llmDemands) {
72
+ fulfilledMetadata = fulfillLlmDemand(fulfilledMetadata, await fulfillments.llm(llmDemands));
73
+ }
74
+
75
+ if (embeddingDemands) {
76
+ fulfilledMetadata = fulfillEmbeddingDemand(fulfilledMetadata, await fulfillments.embedding(embeddingDemands));
77
+ }
78
+
79
+ if (mcpDemands) {
80
+ fulfilledMetadata = fulfillMcpDemand(fulfilledMetadata, await fulfillments.mcp(mcpDemands));
81
+ }
82
+
83
+ if (oauthDemands) {
84
+ fulfilledMetadata = fulfillOAuthDemand(fulfilledMetadata, await fulfillments.oauth(oauthDemands));
85
+ }
86
+
87
+ if (settingsDemands) {
88
+ fulfilledMetadata = fulfillSettingsDemand(fulfilledMetadata, await fulfillments.settings(settingsDemands));
89
+ }
90
+
91
+ if (secretDemands) {
92
+ fulfilledMetadata = fulfillSecretDemand(fulfilledMetadata, await fulfillments.secrets(secretDemands));
93
+ }
94
+
95
+ if (formDemands) {
96
+ fulfilledMetadata = fulfillFormDemand(fulfilledMetadata, await fulfillments.form(formDemands));
97
+ }
98
+
99
+ const oauthRedirectUri = fulfillments.oauthRedirectUri();
100
+ if (oauthRedirectUri) {
101
+ fulfilledMetadata = {
102
+ ...fulfilledMetadata,
103
+ [oauthRequestExtension.getUri()]: {
104
+ redirect_uri: oauthRedirectUri,
105
+ },
106
+ };
107
+ }
108
+
109
+ return fulfilledMetadata;
110
+ };
111
+
112
+ return {
113
+ resolveMetadata,
114
+ demands: { llmDemands, embeddingDemands, mcpDemands, oauthDemands, settingsDemands, secretDemands, formDemands },
115
+ };
116
+ };
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import type { FormResponseValue } from './common/form';
7
+ import { FormRequestExtension } from './ui/form-request';
8
+
9
+ export type InputRequiredResponses = Partial<{
10
+ form: Record<string, FormResponseValue>;
11
+ }>;
12
+
13
+ export const handleInputRequired = () => {
14
+ const resolveMetadata = async (responses: InputRequiredResponses) => {
15
+ const metadata: Record<string, unknown> = {};
16
+
17
+ if (responses.form) {
18
+ metadata[FormRequestExtension.getUri()] = {
19
+ values: responses.form,
20
+ };
21
+ }
22
+
23
+ return metadata;
24
+ };
25
+
26
+ return {
27
+ resolveMetadata,
28
+ };
29
+ };
@@ -0,0 +1,74 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import type { TaskStatusUpdateEvent } from '@a2a-js/sdk';
7
+
8
+ import type { FormRender } from './common/form';
9
+ import type { SecretDemands } from './services/secrets';
10
+ import { secretsMessageExtension } from './services/secrets';
11
+ import { FormRequestExtension } from './ui/form-request';
12
+ import { oauthRequestExtension } from './ui/oauth';
13
+ import { extractUiExtensionData } from './utils';
14
+
15
+ const secretsMessageExtensionExtractor = extractUiExtensionData(secretsMessageExtension);
16
+ const oauthRequestExtensionExtractor = extractUiExtensionData(oauthRequestExtension);
17
+ const FormRequestExtensionExtractor = extractUiExtensionData(FormRequestExtension);
18
+
19
+ export enum TaskStatusUpdateType {
20
+ SecretRequired = 'secret-required',
21
+ FormRequired = 'form-required',
22
+ OAuthRequired = 'oauth-required',
23
+ }
24
+
25
+ export interface SecretRequiredResult {
26
+ type: TaskStatusUpdateType.SecretRequired;
27
+ demands: SecretDemands;
28
+ }
29
+
30
+ export interface FormRequiredResult {
31
+ type: TaskStatusUpdateType.FormRequired;
32
+ form: FormRender;
33
+ }
34
+
35
+ export interface OAuthRequiredResult {
36
+ type: TaskStatusUpdateType.OAuthRequired;
37
+ url: string;
38
+ }
39
+
40
+ export type TaskStatusUpdateResult = SecretRequiredResult | FormRequiredResult | OAuthRequiredResult;
41
+
42
+ export const handleTaskStatusUpdate = (event: TaskStatusUpdateEvent): TaskStatusUpdateResult[] => {
43
+ const results: TaskStatusUpdateResult[] = [];
44
+
45
+ if (event.status.state === 'auth-required') {
46
+ const secretRequired = secretsMessageExtensionExtractor(event.status.message?.metadata);
47
+ const oauthRequired = oauthRequestExtensionExtractor(event.status.message?.metadata);
48
+
49
+ if (oauthRequired) {
50
+ results.push({
51
+ type: TaskStatusUpdateType.OAuthRequired,
52
+ url: oauthRequired.authorization_endpoint_url,
53
+ });
54
+ }
55
+
56
+ if (secretRequired) {
57
+ results.push({
58
+ type: TaskStatusUpdateType.SecretRequired,
59
+ demands: secretRequired,
60
+ });
61
+ }
62
+ } else if (event.status.state === 'input-required') {
63
+ const formRequired = FormRequestExtensionExtractor(event.status.message?.metadata);
64
+
65
+ if (formRequired) {
66
+ results.push({
67
+ type: TaskStatusUpdateType.FormRequired,
68
+ form: formRequired,
69
+ });
70
+ }
71
+ }
72
+
73
+ return results;
74
+ };
@@ -0,0 +1,43 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import type { A2AServiceExtension } from '../types';
9
+
10
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/services/embedding/v1';
11
+
12
+ const embeddingDemandSchema = z.object({
13
+ description: z.string().nullish(),
14
+ suggested: z.array(z.string()).nullish(),
15
+ });
16
+
17
+ const embeddingDemandsSchema = z.object({
18
+ embedding_demands: z.record(z.string(), embeddingDemandSchema),
19
+ });
20
+ export type EmbeddingDemands = z.infer<typeof embeddingDemandsSchema>;
21
+
22
+ const embeddingFulfillmentsSchema = z.object({
23
+ embedding_fulfillments: z.record(
24
+ z.string(),
25
+ z.object({
26
+ identifier: z.string().nullish(),
27
+ api_base: z.string(),
28
+ api_key: z.string(),
29
+ api_model: z.string(),
30
+ }),
31
+ ),
32
+ });
33
+ export type EmbeddingFulfillments = z.infer<typeof embeddingFulfillmentsSchema>;
34
+
35
+ export const embeddingExtension: A2AServiceExtension<
36
+ typeof URI,
37
+ z.infer<typeof embeddingDemandsSchema>,
38
+ EmbeddingFulfillments
39
+ > = {
40
+ getUri: () => URI,
41
+ getDemandsSchema: () => embeddingDemandsSchema,
42
+ getFulfillmentSchema: () => embeddingFulfillmentsSchema,
43
+ };
@@ -0,0 +1,31 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import { formRenderSchema, formResponseSchema } from '../common/form';
9
+ import type { A2AServiceExtension } from '../types';
10
+
11
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/services/form/v1';
12
+
13
+ const formDemandSchema = z.object({
14
+ form_demands: z
15
+ .object({
16
+ initial_form: formRenderSchema,
17
+ })
18
+ .partial(),
19
+ });
20
+ export type FormDemands = z.infer<typeof formDemandSchema>;
21
+
22
+ const formFulfillmentSchema = z.object({
23
+ form_fulfillments: z.record(z.string(), formResponseSchema),
24
+ });
25
+ export type FormFulfillments = z.infer<typeof formFulfillmentSchema>;
26
+
27
+ export const formExtension: A2AServiceExtension<typeof URI, FormDemands, FormFulfillments> = {
28
+ getDemandsSchema: () => formDemandSchema,
29
+ getFulfillmentSchema: () => formFulfillmentSchema,
30
+ getUri: () => URI,
31
+ };
@@ -0,0 +1,39 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import type { A2AServiceExtension } from '../types';
9
+
10
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/services/llm/v1';
11
+
12
+ const llmDemandSchema = z.object({
13
+ description: z.string().nullish(),
14
+ suggested: z.array(z.string()).nullish(),
15
+ });
16
+
17
+ const llmDemandsSchema = z.object({
18
+ llm_demands: z.record(z.string(), llmDemandSchema),
19
+ });
20
+ export type LLMDemands = z.infer<typeof llmDemandsSchema>;
21
+
22
+ const llmFulfillmentSchema = z.object({
23
+ llm_fulfillments: z.record(
24
+ z.string(),
25
+ z.object({
26
+ identifier: z.string().nullish(),
27
+ api_base: z.string(),
28
+ api_key: z.string(),
29
+ api_model: z.string(),
30
+ }),
31
+ ),
32
+ });
33
+ export type LLMFulfillments = z.infer<typeof llmFulfillmentSchema>;
34
+
35
+ export const llmExtension: A2AServiceExtension<typeof URI, z.infer<typeof llmDemandsSchema>, LLMFulfillments> = {
36
+ getUri: () => URI,
37
+ getDemandsSchema: () => llmDemandsSchema,
38
+ getFulfillmentSchema: () => llmFulfillmentSchema,
39
+ };
@@ -0,0 +1,59 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import type { A2AServiceExtension } from '../types';
9
+
10
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/services/mcp/v1';
11
+
12
+ const mcpTransportTypesEnum = z.enum(['streamable_http', 'stdio']);
13
+ type MCPTransportType = z.infer<typeof mcpTransportTypesEnum>;
14
+
15
+ const mcpDemandSchema = z.object({
16
+ description: z.string().nullish(),
17
+ suggested: z.array(z.string()).nullish(),
18
+ allowed_transports: z.array(mcpTransportTypesEnum).nullish(),
19
+ });
20
+
21
+ const mcpDemandsSchema = z.object({
22
+ mcp_demands: z.record(z.string(), mcpDemandSchema),
23
+ });
24
+ export type MCPDemands = z.infer<typeof mcpDemandsSchema>;
25
+
26
+ const mcpFulfillmentSchema = z.object({
27
+ mcp_fulfillments: z.record(
28
+ z.string(),
29
+ z.object({
30
+ transport: z.object({
31
+ type: mcpTransportTypesEnum,
32
+ url: z.string(),
33
+ headers: z.record(z.string(), z.string()).optional(),
34
+ }),
35
+ }),
36
+ ),
37
+ });
38
+ export type MCPFulfillments = z.infer<typeof mcpFulfillmentSchema>;
39
+
40
+ export const mcpExtension: A2AServiceExtension<
41
+ typeof URI,
42
+ z.infer<typeof mcpDemandsSchema>,
43
+ {
44
+ mcp_fulfillments: Record<
45
+ string,
46
+ {
47
+ transport: {
48
+ type: MCPTransportType;
49
+ url: string;
50
+ headers?: Record<string, string>;
51
+ };
52
+ }
53
+ >;
54
+ }
55
+ > = {
56
+ getUri: () => URI,
57
+ getDemandsSchema: () => mcpDemandsSchema,
58
+ getFulfillmentSchema: () => mcpFulfillmentSchema,
59
+ };
@@ -0,0 +1,52 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import type { A2AServiceExtension } from '../types';
9
+
10
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/auth/oauth/v1';
11
+
12
+ const oauthDemandSchema = z.object({
13
+ redirect_uri: z.boolean(),
14
+ });
15
+
16
+ const oauthDemandsSchema = z.object({
17
+ oauth_demands: z.record(z.string(), oauthDemandSchema),
18
+ });
19
+ export type OAuthDemands = z.infer<typeof oauthDemandsSchema>;
20
+
21
+ const oauthFulfillmentSchema = z.object({
22
+ oauth_fulfillments: z.record(
23
+ z.string(),
24
+ z.object({
25
+ redirect_uri: z.string(),
26
+ }),
27
+ ),
28
+ });
29
+ export type OAuthFulfillments = z.infer<typeof oauthFulfillmentSchema>;
30
+
31
+ export const oauthProviderExtension: A2AServiceExtension<
32
+ typeof URI,
33
+ z.infer<typeof oauthDemandsSchema>,
34
+ {
35
+ oauth_fulfillments: Record<
36
+ string,
37
+ {
38
+ redirect_uri: string;
39
+ }
40
+ >;
41
+ }
42
+ > = {
43
+ getUri: () => URI,
44
+ getDemandsSchema: () => oauthDemandsSchema,
45
+ getFulfillmentSchema: () => oauthFulfillmentSchema,
46
+ };
47
+
48
+ export const oauthMessageSchema = z.object({
49
+ data: z.object({
50
+ redirect_uri: z.string(),
51
+ }),
52
+ });
@@ -0,0 +1,22 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import type { ContextToken } from '../../../api/types';
7
+
8
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/services/platform_api/v1';
9
+
10
+ const getMetadata = (contextToken: ContextToken) => {
11
+ return {
12
+ auth_token: contextToken.token,
13
+ expires_at: contextToken.expires_at,
14
+ };
15
+ };
16
+
17
+ export const platformApiExtension = (metadata: Record<string, unknown>, contextToken: ContextToken) => {
18
+ return {
19
+ ...metadata,
20
+ [URI]: getMetadata(contextToken),
21
+ };
22
+ };
@@ -0,0 +1,46 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import type { A2AServiceExtension, A2AUiExtension } from '../types';
9
+
10
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/auth/secrets/v1';
11
+
12
+ const secretDemandSchema = z.object({
13
+ name: z.string(),
14
+ description: z.string().nullish(),
15
+ });
16
+ export type SecretDemand = z.infer<typeof secretDemandSchema>;
17
+
18
+ const secretDemandsSchema = z.object({
19
+ secret_demands: z.record(z.string(), secretDemandSchema),
20
+ });
21
+ export type SecretDemands = z.infer<typeof secretDemandsSchema>;
22
+
23
+ const secretFulfillmentSchema = z.object({
24
+ secret_fulfillments: z.record(
25
+ z.string(),
26
+ z.object({
27
+ secret: z.string(),
28
+ }),
29
+ ),
30
+ });
31
+ export type SecretFulfillments = z.infer<typeof secretFulfillmentSchema>;
32
+
33
+ export const secretsExtension: A2AServiceExtension<
34
+ typeof URI,
35
+ z.infer<typeof secretDemandsSchema>,
36
+ SecretFulfillments
37
+ > = {
38
+ getUri: () => URI,
39
+ getDemandsSchema: () => secretDemandsSchema,
40
+ getFulfillmentSchema: () => secretFulfillmentSchema,
41
+ };
42
+
43
+ export const secretsMessageExtension: A2AUiExtension<typeof URI, SecretDemands> = {
44
+ getMessageMetadataSchema: () => z.object({ [URI]: secretDemandsSchema }).partial(),
45
+ getUri: () => URI,
46
+ };
@@ -0,0 +1,20 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import type { z } from 'zod';
7
+
8
+ export interface A2AExtension<U extends string> {
9
+ getUri: () => U;
10
+ }
11
+
12
+ export interface A2AUiExtension<U extends string, D> extends A2AExtension<U> {
13
+ getMessageMetadataSchema: () => z.ZodSchema<Partial<Record<U, D>>>;
14
+ }
15
+
16
+ export interface A2AServiceExtension<U extends string, D, F> extends A2AExtension<U> {
17
+ getUri: () => U;
18
+ getDemandsSchema: () => z.ZodSchema<D>;
19
+ getFulfillmentSchema: () => z.ZodSchema<F>;
20
+ }
@@ -0,0 +1,46 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import { interactionModeSchema } from '../../../../types';
9
+ import type { A2AUiExtension } from '../types';
10
+
11
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/ui/agent-detail/v1';
12
+
13
+ const contributorSchema = z.object({
14
+ name: z.string(),
15
+ email: z.string().nullish(),
16
+ url: z.string().nullish(),
17
+ });
18
+
19
+ const toolSchema = z.object({
20
+ name: z.string(),
21
+ description: z.string(),
22
+ });
23
+
24
+ const schema = z.object({
25
+ interaction_mode: z.union([interactionModeSchema, z.string()]).nullish(),
26
+ user_greeting: z.string().nullish(),
27
+ input_placeholder: z.string().nullish(),
28
+ tools: z.array(toolSchema).nullish(),
29
+ framework: z.string().nullish(),
30
+ license: z.string().nullish(),
31
+ programming_language: z.string().nullish(),
32
+ homepage_url: z.string().nullish(),
33
+ source_code_url: z.string().nullish(),
34
+ container_image_url: z.string().nullish(),
35
+ author: contributorSchema.nullish(),
36
+ contributors: z.array(contributorSchema).nullish(),
37
+ });
38
+
39
+ export type AgentDetailTool = z.infer<typeof toolSchema>;
40
+ export type AgentDetailContributor = z.infer<typeof contributorSchema>;
41
+ export type AgentDetail = z.infer<typeof schema>;
42
+
43
+ export const agentDetailExtension: A2AUiExtension<typeof URI, AgentDetail> = {
44
+ getMessageMetadataSchema: () => z.object({ [URI]: schema }).partial(),
45
+ getUri: () => URI,
46
+ };
@@ -0,0 +1,30 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import type { A2AUiExtension } from '../types';
9
+
10
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/ui/citation/v1';
11
+
12
+ const citationSchema = z.object({
13
+ url: z.string().nullish(),
14
+ start_index: z.number().nullish(),
15
+ end_index: z.number().nullish(),
16
+ title: z.string().nullish(),
17
+ description: z.string().nullish(),
18
+ });
19
+
20
+ const schema = z.object({
21
+ citations: z.array(citationSchema),
22
+ });
23
+
24
+ export type CitationMetadata = z.infer<typeof schema>;
25
+ export type Citation = z.infer<typeof citationSchema>;
26
+
27
+ export const citationExtension: A2AUiExtension<typeof URI, CitationMetadata> = {
28
+ getMessageMetadataSchema: () => z.object({ [URI]: schema }).partial(),
29
+ getUri: () => URI,
30
+ };
@@ -0,0 +1,18 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import { formRenderSchema } from '../common/form';
9
+ import type { A2AUiExtension } from '../types';
10
+
11
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/ui/form_request/v1';
12
+
13
+ export type FormRequest = z.infer<typeof formRenderSchema>;
14
+
15
+ export const FormRequestExtension: A2AUiExtension<typeof URI, FormRequest> = {
16
+ getMessageMetadataSchema: () => z.object({ [URI]: formRenderSchema }).partial(),
17
+ getUri: () => URI,
18
+ };
@@ -0,0 +1,21 @@
1
+ /**
2
+ * Copyright 2025 © BeeAI a Series of LF Projects, LLC
3
+ * SPDX-License-Identifier: Apache-2.0
4
+ */
5
+
6
+ import z from 'zod';
7
+
8
+ import type { A2AUiExtension } from '../types';
9
+
10
+ const URI = 'https://a2a-extensions.agentstack.beeai.dev/auth/oauth/v1';
11
+
12
+ const schema = z.object({
13
+ authorization_endpoint_url: z.string(),
14
+ });
15
+
16
+ export type OAuthRequest = z.infer<typeof schema>;
17
+
18
+ export const oauthRequestExtension: A2AUiExtension<typeof URI, OAuthRequest> = {
19
+ getMessageMetadataSchema: () => z.object({ [URI]: schema }).partial(),
20
+ getUri: () => URI,
21
+ };