Skip to content

Commit 9c35418

Browse files
authored
Add version fields (google#581)
1 parent d0c2a71 commit 9c35418

14 files changed

Lines changed: 92 additions & 27 deletions

specification/v0_9/docs/a2ui_extension_specification.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -89,12 +89,14 @@ Example DataPart:
8989
{
9090
"data": [
9191
{
92+
"version": "v0.9",
9293
"createSurface": {
9394
"surfaceId": "example_surface",
9495
"catalogId": "https://a2ui.org/specification/v0_9/standard_catalog.json"
9596
}
9697
},
9798
{
99+
"version": "v0.9",
98100
"updateComponents": {
99101
"surfaceId": "example_surface",
100102
"components": [
@@ -125,6 +127,7 @@ Example `action` DataPart:
125127
{
126128
"data": [
127129
{
130+
"version": "v0.9",
128131
"action": {
129132
"name": "submit_form",
130133
"surfaceId": "contact_form_1",

specification/v0_9/docs/a2ui_protocol.md

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -189,6 +189,7 @@ This message signals the client to create a new surface and begin rendering it.
189189

190190
```json
191191
{
192+
"version": "v0.9",
192193
"createSurface": {
193194
"surfaceId": "user_profile_card",
194195
"catalogId": "https://a2ui.org/specification/v0_9/standard_catalog.json",
@@ -213,6 +214,7 @@ This message provides a list of UI components to be added to or updated within a
213214

214215
```json
215216
{
217+
"version": "v0.9",
216218
"updateComponents": {
217219
"surfaceId": "user_profile_card",
218220
"components": [
@@ -250,6 +252,7 @@ This message is used to send or update the data that populates the UI components
250252

251253
```json
252254
{
255+
"version": "v0.9",
253256
"updateDataModel": {
254257
"surfaceId": "user_profile_card",
255258
"path": "/user/name",
@@ -270,6 +273,7 @@ This message instructs the client to remove a surface and all its associated com
270273

271274
```json
272275
{
276+
"version": "v0.9",
273277
"deleteSurface": {
274278
"surfaceId": "user_profile_card"
275279
}
@@ -281,10 +285,10 @@ This message instructs the client to remove a surface and all its associated com
281285
The following example demonstrates a complete interaction to render a Contact Form, expressed as a JSONL stream.
282286

283287
```jsonl
284-
{"createSurface":{"surfaceId":"contact_form_1","catalogId":"https://a2ui.org/specification/v0_9/standard_catalog.json"}}
285-
{"updateComponents":{"surfaceId":"contact_form_1","components":[{"id":"root","component":"Card","child":"form_container"},{"id":"form_container","component":"Column","children":["header_row","name_row","email_group","phone_group","pref_group","divider_1","newsletter_checkbox","submit_button"],"justify":"start","align":"stretch"},{"id":"header_row","component":"Row","children":["header_icon","header_text"],"align":"center"},{"id":"header_icon","component":"Icon","name":"mail"},{"id":"header_text","component":"Text","text":"# Contact Us","variant":"h2"},{"id":"name_row","component":"Row","children":["first_name_group","last_name_group"],"justify":"spaceBetween"},{"id":"first_name_group","component":"Column","children":["first_name_label","first_name_field"],"weight":1},{"id":"first_name_label","component":"Text","text":"First Name","variant":"caption"},{"id":"first_name_field","component":"TextField","label":"First Name","value":{"path":"/contact/firstName"},"variant":"shortText"},{"id":"last_name_group","component":"Column","children":["last_name_label","last_name_field"],"weight":1},{"id":"last_name_label","component":"Text","text":"Last Name","variant":"caption"},{"id":"last_name_field","component":"TextField","label":"Last Name","value":{"path":"/contact/lastName"},"variant":"shortText"},{"id":"email_group","component":"Column","children":["email_label","email_field"]},{"id":"email_label","component":"Text","text":"Email Address","variant":"caption"},{"id":"email_field","component":"TextField","label":"Email","value":{"path":"/contact/email"},"variant":"shortText","checks":[{"call":"required","args":{"value":{"path":"/contact/email"}},"message":"Email is required."},{"call":"email","args":{"value":{"path":"/contact/email"}},"message":"Please enter a valid email address."}]},{"id":"phone_group","component":"Column","children":["phone_label","phone_field"]},{"id":"phone_label","component":"Text","text":"Phone Number","variant":"caption"},{"id":"phone_field","component":"TextField","label":"Phone","value":{"path":"/contact/phone"},"variant":"shortText","checks":[{"call":"regex","args":{"value":{"path":"/contact/phone"},"pattern":"^\\d{10}$"},"message":"Phone number must be 10 digits."}]},{"id":"pref_group","component":"Column","children":["pref_label","pref_picker"]},{"id":"pref_label","component":"Text","text":"Preferred Contact Method","variant":"caption"},{"id":"pref_picker","component":"ChoicePicker","variant":"mutuallyExclusive","options":[{"label":"Email","value":"email"},{"label":"Phone","value":"phone"},{"label":"SMS","value":"sms"}],"value":{"path":"/contact/preference"}},{"id":"divider_1","component":"Divider","axis":"horizontal"},{"id":"newsletter_checkbox","component":"CheckBox","label":"Subscribe to our newsletter","value":{"path":"/contact/subscribe"}},{"id":"submit_button_label","component":"Text","text":"Send Message"},{"id":"submit_button","component":"Button","child":"submit_button_label","variant":"primary","action":{"event":{"name":"submitContactForm","context":{"formId":"contact_form_1","clientTime":{"call":"now","args":{},"returnType":"string"},"isNewsletterSubscribed":{"path":"/contact/subscribe"}}}}}]}}
286-
{"updateDataModel":{"surfaceId":"contact_form_1","path":"/contact","value":{"firstName":"John","lastName":"Doe","email":"john.doe@example.com","phone":"1234567890","preference":["email"],"subscribe":true}}}
287-
{"deleteSurface":{"surfaceId":"contact_form_1"}}
288+
{"version": "v0.9", "createSurface":{"surfaceId":"contact_form_1","catalogId":"https://a2ui.org/specification/v0_9/standard_catalog.json"}}
289+
{"version": "v0.9", "updateComponents":{"surfaceId":"contact_form_1","components":[{"id":"root","component":"Card","child":"form_container"},{"id":"form_container","component":"Column","children":["header_row","name_row","email_group","phone_group","pref_group","divider_1","newsletter_checkbox","submit_button"],"justify":"start","align":"stretch"},{"id":"header_row","component":"Row","children":["header_icon","header_text"],"align":"center"},{"id":"header_icon","component":"Icon","name":"mail"},{"id":"header_text","component":"Text","text":"# Contact Us","variant":"h2"},{"id":"name_row","component":"Row","children":["first_name_group","last_name_group"],"justify":"spaceBetween"},{"id":"first_name_group","component":"Column","children":["first_name_label","first_name_field"],"weight":1},{"id":"first_name_label","component":"Text","text":"First Name","variant":"caption"},{"id":"first_name_field","component":"TextField","label":"First Name","value":{"path":"/contact/firstName"},"variant":"shortText"},{"id":"last_name_group","component":"Column","children":["last_name_label","last_name_field"],"weight":1},{"id":"last_name_label","component":"Text","text":"Last Name","variant":"caption"},{"id":"last_name_field","component":"TextField","label":"Last Name","value":{"path":"/contact/lastName"},"variant":"shortText"},{"id":"email_group","component":"Column","children":["email_label","email_field"]},{"id":"email_label","component":"Text","text":"Email Address","variant":"caption"},{"id":"email_field","component":"TextField","label":"Email","value":{"path":"/contact/email"},"variant":"shortText","checks":[{"call":"required","args":{"value":{"path":"/contact/email"}},"message":"Email is required."},{"call":"email","args":{"value":{"path":"/contact/email"}},"message":"Please enter a valid email address."}]},{"id":"phone_group","component":"Column","children":["phone_label","phone_field"]},{"id":"phone_label","component":"Text","text":"Phone Number","variant":"caption"},{"id":"phone_field","component":"TextField","label":"Phone","value":{"path":"/contact/phone"},"variant":"shortText","checks":[{"call":"regex","args":{"value":{"path":"/contact/phone"},"pattern":"^\\d{10}$"},"message":"Phone number must be 10 digits."}]},{"id":"pref_group","component":"Column","children":["pref_label","pref_picker"]},{"id":"pref_label","component":"Text","text":"Preferred Contact Method","variant":"caption"},{"id":"pref_picker","component":"ChoicePicker","variant":"mutuallyExclusive","options":[{"label":"Email","value":"email"},{"label":"Phone","value":"phone"},{"label":"SMS","value":"sms"}],"value":{"path":"/contact/preference"}},{"id":"divider_1","component":"Divider","axis":"horizontal"},{"id":"newsletter_checkbox","component":"CheckBox","label":"Subscribe to our newsletter","value":{"path":"/contact/subscribe"}},{"id":"submit_button_label","component":"Text","text":"Send Message"},{"id":"submit_button","component":"Button","child":"submit_button_label","variant":"primary","action":{"event":{"name":"submitContactForm","context":{"formId":"contact_form_1","clientTime":{"call":"now","args":{},"returnType":"string"},"isNewsletterSubscribed":{"path":"/contact/subscribe"}}}}}]}}
290+
{"version": "v0.9", "updateDataModel":{"surfaceId":"contact_form_1","path":"/contact","value":{"firstName":"John","lastName":"Doe","email":"john.doe@example.com","phone":"1234567890","preference":["email"],"subscribe":true}}}
291+
{"version": "v0.9", "deleteSurface":{"surfaceId":"contact_form_1"}}
288292
```
289293

290294
## Component model
@@ -531,6 +535,7 @@ _Update a specific field:_
531535

532536
```json
533537
{
538+
"version": "v0.9",
534539
"updateDataModel": {
535540
"surfaceId": "surface_123",
536541
"path": "/user/firstName",
@@ -543,6 +548,7 @@ _Remove a field:_
543548

544549
```json
545550
{
551+
"version": "v0.9",
546552
"updateDataModel": {
547553
"surfaceId": "surface_123",
548554
"path": "/user/tempData"
@@ -554,6 +560,7 @@ _Replace the entire data model:_
554560

555561
```json
556562
{
563+
"version": "v0.9",
557564
"updateDataModel": {
558565
"surfaceId": "surface_123",
559566
"value": {

specification/v0_9/docs/evolution_guide.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,7 @@ Version 0.9 represents a fundamental philosophical shift from "Structured Output
103103

104104
```json
105105
{
106+
"version": "v0.9",
106107
"createSurface": {
107108
"surfaceId": "user_profile_card",
108109
"catalogId": "https://a2ui.org/specification/v0_9/standard_catalog.json",
@@ -155,6 +156,7 @@ Specifying an unknown surfaceId will cause an error. It is recommended that clie
155156

156157
```json
157158
{
159+
"version": "v0.9",
158160
"updateComponents": {
159161
"surfaceId": "main",
160162
"components": [

specification/v0_9/eval/src/generation_flow.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ Standard Instructions:
5656
13. Do NOT use a 'style' property. Use standard properties like 'align', 'justify', 'variant', etc.
5757
14. Do NOT invent properties that are not in the schema. Check the 'properties' list for each component type.
5858
15. Use 'checks' property for validation rules if required.
59+
16. EVERY message object MUST include the property "version": "v0.9" at the top level.
5960
${catalogRules ? `\nInstructions specific to this catalog:\n${catalogRules}` : ""}
6061
6162
Schemas:

specification/v0_9/json/a2ui_client_capabilities.json

Lines changed: 17 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -5,18 +5,25 @@
55
"description": "A schema for the a2uiClientCapabilities object, which is sent from the client to the server as part of the A2A metadata to describe the client's UI rendering capabilities.",
66
"type": "object",
77
"properties": {
8-
"supportedCatalogIds": {
9-
"type": "array",
10-
"description": "The URI of each of the component and function catalogs that is supported by the client.",
11-
"items": { "type": "string" }
12-
},
13-
"inlineCatalogs": {
14-
"type": "array",
15-
"description": "An array of inline catalog definitions, which can contain both components and functions. This should only be provided if the agent declares 'acceptsInlineCatalogs: true' in its capabilities.",
16-
"items": { "$ref": "#/$defs/Catalog" }
8+
"v0.9": {
9+
"type": "object",
10+
"description": "The capabilities structure for version 0.9 of the A2UI protocol.",
11+
"properties": {
12+
"supportedCatalogIds": {
13+
"type": "array",
14+
"description": "The URI of each of the component and function catalogs that is supported by the client.",
15+
"items": { "type": "string" }
16+
},
17+
"inlineCatalogs": {
18+
"type": "array",
19+
"description": "An array of inline catalog definitions, which can contain both components and functions. This should only be provided if the agent declares 'acceptsInlineCatalogs: true' in its capabilities.",
20+
"items": { "$ref": "#/$defs/Catalog" }
21+
}
22+
},
23+
"required": ["supportedCatalogIds"]
1724
}
1825
},
19-
"required": ["supportedCatalogIds"],
26+
"required": ["v0.9"],
2027
"$defs": {
2128
"FunctionDefinition": {
2229
"type": "object",

specification/v0_9/json/a2ui_client_data_model.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,9 @@
55
"description": "Schema for attaching the client data model to A2A message metadata. This object should be placed in the `a2uiClientDataModel` field of the metadata.",
66
"type": "object",
77
"properties": {
8+
"version": {
9+
"const": "v0.9"
10+
},
811
"surfaces": {
912
"type": "object",
1013
"description": "A map of surface IDs to their current data models.",
@@ -14,6 +17,6 @@
1417
}
1518
}
1619
},
17-
"required": ["surfaces"],
20+
"required": ["version", "surfaces"],
1821
"additionalProperties": false
1922
}

specification/v0_9/json/client_to_server.json

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,12 @@
22
"title": "A2UI (Agent to UI) Client-to-Server Event Schema",
33
"description": "Describes a JSON payload for a client-to-server event message.",
44
"type": "object",
5-
"minProperties": 1,
6-
"maxProperties": 1,
5+
"minProperties": 2,
6+
"maxProperties": 2,
77
"properties": {
8+
"version": {
9+
"const": "v0.9"
10+
},
811
"action": {
912
"type": "object",
1013
"description": "Reports a user-initiated action from a component.",
@@ -92,10 +95,10 @@
9295
},
9396
"oneOf": [
9497
{
95-
"required": ["action"]
98+
"required": ["action", "version"]
9699
},
97100
{
98-
"required": ["error"]
101+
"required": ["error", "version"]
99102
}
100103
]
101104
}

specification/v0_9/json/server_to_client.json

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,9 @@
1414
"CreateSurfaceMessage": {
1515
"type": "object",
1616
"properties": {
17+
"version": {
18+
"const": "v0.9"
19+
},
1720
"createSurface": {
1821
"type": "object",
1922
"description": "Signals the client to create a new surface and begin rendering it. When this message is sent, the client will expect 'updateComponents' and/or 'updateDataModel' messages for the same surfaceId that define the component tree.",
@@ -40,12 +43,15 @@
4043
"additionalProperties": false
4144
}
4245
},
43-
"required": ["createSurface"],
46+
"required": ["createSurface", "version"],
4447
"additionalProperties": false
4548
},
4649
"UpdateComponentsMessage": {
4750
"type": "object",
4851
"properties": {
52+
"version": {
53+
"const": "v0.9"
54+
},
4955
"updateComponents": {
5056
"type": "object",
5157
"description": "Updates a surface with a new set of components. This message can be sent multiple times to update the component tree of an existing surface. One of the components in one of the components lists MUST have an 'id' of 'root' to serve as the root of the component tree. The createSurface message MUST have been previously sent with the 'catalogId' that is in this message.",
@@ -68,12 +74,15 @@
6874
"additionalProperties": false
6975
}
7076
},
71-
"required": ["updateComponents"],
77+
"required": ["updateComponents", "version"],
7278
"additionalProperties": false
7379
},
7480
"UpdateDataModelMessage": {
7581
"type": "object",
7682
"properties": {
83+
"version": {
84+
"const": "v0.9"
85+
},
7786
"updateDataModel": {
7887
"type": "object",
7988
"description": "Updates the data model for an existing surface. This message can be sent multiple times to update the data model. The createSurface message MUST have been previously sent with the 'catalogId' that is in this message.",
@@ -95,12 +104,15 @@
95104
"additionalProperties": false
96105
}
97106
},
98-
"required": ["updateDataModel"],
107+
"required": ["updateDataModel", "version"],
99108
"additionalProperties": false
100109
},
101110
"DeleteSurfaceMessage": {
102111
"type": "object",
103112
"properties": {
113+
"version": {
114+
"const": "v0.9"
115+
},
104116
"deleteSurface": {
105117
"type": "object",
106118
"description": "Signals the client to delete the surface identified by 'surfaceId'. The createSurface message MUST have been previously sent with the 'catalogId' that is in this message.",
@@ -114,7 +126,7 @@
114126
"additionalProperties": false
115127
}
116128
},
117-
"required": ["deleteSurface"],
129+
"required": ["deleteSurface", "version"],
118130
"additionalProperties": false
119131
}
120132
}

specification/v0_9/test/cases/button_checks.json

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
"description": "Button with nested valid checks",
66
"valid": true,
77
"data": {
8+
"version": "v0.9",
89
"updateComponents": {
910
"surfaceId": "test_surface",
1011
"components": [
@@ -49,6 +50,7 @@
4950
"description": "Button with deprecated enabled property (should fail)",
5051
"valid": false,
5152
"data": {
53+
"version": "v0.9",
5254
"updateComponents": {
5355
"surfaceId": "test_surface",
5456
"components": [
@@ -68,6 +70,7 @@
6870
"description": "Button with invalid check structure (invalid returnType)",
6971
"valid": false,
7072
"data": {
73+
"version": "v0.9",
7174
"updateComponents": {
7275
"surfaceId": "test_surface",
7376
"components": [
@@ -93,6 +96,7 @@
9396
"description": "Button with invalid nested structure (extra property)",
9497
"valid": false,
9598
"data": {
99+
"version": "v0.9",
96100
"updateComponents": {
97101
"surfaceId": "test_surface",
98102
"components": [
@@ -118,6 +122,7 @@
118122
"description": "Button with variant 'primary'",
119123
"valid": true,
120124
"data": {
125+
"version": "v0.9",
121126
"updateComponents": {
122127
"surfaceId": "test_surface",
123128
"components": [
@@ -137,6 +142,7 @@
137142
"description": "Button with variant 'borderless'",
138143
"valid": true,
139144
"data": {
145+
"version": "v0.9",
140146
"updateComponents": {
141147
"surfaceId": "test_surface",
142148
"components": [
@@ -156,6 +162,7 @@
156162
"description": "Button with deprecated 'primary' property (should fail)",
157163
"valid": false,
158164
"data": {
165+
"version": "v0.9",
159166
"updateComponents": {
160167
"surfaceId": "test_surface",
161168
"components": [

0 commit comments

Comments
 (0)