diff --git a/renderers/lit/src/0.8/ui/multiple-choice.ts b/renderers/lit/src/0.8/ui/multiple-choice.ts index 3358055a6..065d48f1d 100644 --- a/renderers/lit/src/0.8/ui/multiple-choice.ts +++ b/renderers/lit/src/0.8/ui/multiple-choice.ts @@ -240,7 +240,7 @@ export class MultipleChoice extends Root { } .chip.selected:hover { - background: var(--md-sys-color-secondary-container-high, #e8def8); + background: var(--md-sys-color-secondary-container-high); } .chip-icon { diff --git a/renderers/lit/src/0.8/ui/text-field.ts b/renderers/lit/src/0.8/ui/text-field.ts index b58d45d1a..08295e874 100644 --- a/renderers/lit/src/0.8/ui/text-field.ts +++ b/renderers/lit/src/0.8/ui/text-field.ts @@ -36,6 +36,9 @@ export class TextField extends Root { @property() accessor inputType: Types.ResolvedTextField["type"] | null = null; + @property() + accessor validationRegexp: string | null = null; + static styles = [ structuralStyles, css` @@ -52,6 +55,17 @@ export class TextField extends Root { display: block; width: 100%; } + + input:invalid { + border-color: var(--color-error); + color: var(--color-error); + outline-color: var(--color-error); + } + + input:invalid:focus { + border-color: var(--color-error); + outline-color: var(--color-error); + } label { display: block; @@ -107,6 +121,7 @@ export class TextField extends Root { id="data" .value=${value} .placeholder=${"Please enter a value"} + pattern=${this.validationRegexp || nothing} type=${this.inputType === "number" ? "number" : "text"} /> `; diff --git a/samples/agent/adk/component_gallery/__main__.py b/samples/agent/adk/component_gallery/__main__.py index 331c3deb2..347adbb6f 100644 --- a/samples/agent/adk/component_gallery/__main__.py +++ b/samples/agent/adk/component_gallery/__main__.py @@ -1,3 +1,4 @@ + """Main entry point for the Component Gallery agent.""" import logging import os @@ -14,6 +15,7 @@ from starlette.staticfiles import StaticFiles from dotenv import load_dotenv + from agent_executor import ComponentGalleryExecutor load_dotenv() diff --git a/samples/agent/adk/component_gallery/gallery_examples.py b/samples/agent/adk/component_gallery/gallery_examples.py index 59417c1d2..18630ea4f 100644 --- a/samples/agent/adk/component_gallery/gallery_examples.py +++ b/samples/agent/adk/component_gallery/gallery_examples.py @@ -56,6 +56,15 @@ def add_demo_surface(surface_id, component_def): } }) + # 1b. TextField (Regex) + add_demo_surface("demo-text-regex", { + "TextField": { + "label": { "literalString": "Enter exactly 5 digits" }, + "text": { "path": "galleryData/textFieldRegex" }, + "validationRegexp": "^\\d{5}$" + } + }) + # 2. CheckBox add_demo_surface("demo-checkbox", { "CheckBox": { diff --git a/samples/client/lit/component_gallery/client.ts b/samples/client/lit/component_gallery/client.ts index 9ee992654..0603dc992 100644 --- a/samples/client/lit/component_gallery/client.ts +++ b/samples/client/lit/component_gallery/client.ts @@ -15,7 +15,7 @@ */ import { v0_8 } from "@a2ui/lit"; - +import { registerContactComponents } from "./ui/custom-components/register-components.js"; type A2TextPayload = { kind: "text"; text: string; @@ -72,4 +72,4 @@ export class A2UIClient { throw new Error(error.error); } } - +registerContactComponents(); diff --git a/samples/client/lit/component_gallery/component-gallery.ts b/samples/client/lit/component_gallery/component-gallery.ts index 8a3cea64d..773643ff0 100644 --- a/samples/client/lit/component_gallery/component-gallery.ts +++ b/samples/client/lit/component_gallery/component-gallery.ts @@ -20,6 +20,7 @@ interface DemoItem { const DEMO_ITEMS: DemoItem[] = [ { id: "demo-text", title: "TextField", description: "Allows user to enter text. Supports binding to data model.", actionButton: true }, + { id: "demo-text-regex", title: "TextField (Regex)", description: "TextField with 5-digit regex validation.", actionButton: true }, { id: "demo-checkbox", title: "CheckBox", description: "A binary toggle.", actionButton: true }, { id: "demo-slider", title: "Slider", description: "Select a value from a range.", actionButton: true }, { id: "demo-date", title: "DateTimeInput", description: "Pick a date or time.", actionButton: true }, @@ -260,6 +261,7 @@ export class A2UIComponentGallery extends SignalWatcher(LitElement) { // Map item IDs to data paths based on knowledge of gallery_examples.py const pathMap: Record = { "demo-text": "galleryData/textField", + "demo-text-regex": "galleryData/textFieldRegex", "demo-checkbox": "galleryData/checkbox", "demo-slider": "galleryData/slider", "demo-date": "galleryData/date", diff --git a/samples/client/lit/component_gallery/theme/theme.ts b/samples/client/lit/component_gallery/theme/theme.ts index 82cce9bfd..034299719 100644 --- a/samples/client/lit/component_gallery/theme/theme.ts +++ b/samples/client/lit/component_gallery/theme/theme.ts @@ -217,6 +217,9 @@ export const theme: v0_8.Types.Theme = { display: "flex", flexDirection: "column", }, + MultipleChoice: { + "--md-sys-color-secondary-container-high": "#e8def8", + }, }, components: { AudioPlayer: {}, diff --git a/samples/client/lit/shell/theme/default-theme.ts b/samples/client/lit/shell/theme/default-theme.ts index 34996dffc..581338c4d 100644 --- a/samples/client/lit/shell/theme/default-theme.ts +++ b/samples/client/lit/shell/theme/default-theme.ts @@ -205,6 +205,7 @@ export const theme: v0_8.Types.Theme = { }, TextField: { "--p-0": "light-dark(var(--n-0), #1e293b)", + "--color-error": "#B3261E", }, }, components: { diff --git a/specification/v0_8/json/standard_catalog_definition.json b/specification/v0_8/json/standard_catalog_definition.json index 5a662cf1d..fa6fc228f 100644 --- a/specification/v0_8/json/standard_catalog_definition.json +++ b/specification/v0_8/json/standard_catalog_definition.json @@ -31,7 +31,9 @@ ] } }, - "required": ["text"] + "required": [ + "text" + ] }, "Image": { "type": "object", @@ -74,7 +76,9 @@ ] } }, - "required": ["url"] + "required": [ + "url" + ] }, "Icon": { "type": "object", @@ -144,7 +148,9 @@ } } }, - "required": ["name"] + "required": [ + "name" + ] }, "Video": { "type": "object", @@ -164,7 +170,9 @@ } } }, - "required": ["url"] + "required": [ + "url" + ] }, "AudioPlayer": { "type": "object", @@ -197,7 +205,9 @@ } } }, - "required": ["url"] + "required": [ + "url" + ] }, "Row": { "type": "object", @@ -226,7 +236,10 @@ "type": "string" } }, - "required": ["componentId", "dataBinding"] + "required": [ + "componentId", + "dataBinding" + ] } } }, @@ -245,10 +258,17 @@ "alignment": { "type": "string", "description": "Defines the alignment of children along the cross axis (vertically). This corresponds to the CSS 'align-items' property.", - "enum": ["start", "center", "end", "stretch"] + "enum": [ + "start", + "center", + "end", + "stretch" + ] } }, - "required": ["children"] + "required": [ + "children" + ] }, "Column": { "type": "object", @@ -277,7 +297,10 @@ "type": "string" } }, - "required": ["componentId", "dataBinding"] + "required": [ + "componentId", + "dataBinding" + ] } } }, @@ -296,10 +319,17 @@ "alignment": { "type": "string", "description": "Defines the alignment of children along the cross axis (horizontally). This corresponds to the CSS 'align-items' property.", - "enum": ["center", "end", "start", "stretch"] + "enum": [ + "center", + "end", + "start", + "stretch" + ] } }, - "required": ["children"] + "required": [ + "children" + ] }, "List": { "type": "object", @@ -328,22 +358,35 @@ "type": "string" } }, - "required": ["componentId", "dataBinding"] + "required": [ + "componentId", + "dataBinding" + ] } } }, "direction": { "type": "string", "description": "The direction in which the list items are laid out.", - "enum": ["vertical", "horizontal"] + "enum": [ + "vertical", + "horizontal" + ] }, "alignment": { "type": "string", "description": "Defines the alignment of children along the cross axis.", - "enum": ["start", "center", "end", "stretch"] + "enum": [ + "start", + "center", + "end", + "stretch" + ] } }, - "required": ["children"] + "required": [ + "children" + ] }, "Card": { "type": "object", @@ -354,7 +397,9 @@ "description": "The ID of the component to be rendered inside the card." } }, - "required": ["child"] + "required": [ + "child" + ] }, "Tabs": { "type": "object", @@ -384,11 +429,16 @@ "type": "string" } }, - "required": ["title", "child"] + "required": [ + "title", + "child" + ] } } }, - "required": ["tabItems"] + "required": [ + "tabItems" + ] }, "Divider": { "type": "object", @@ -397,7 +447,10 @@ "axis": { "type": "string", "description": "The orientation of the divider.", - "enum": ["horizontal", "vertical"] + "enum": [ + "horizontal", + "vertical" + ] } } }, @@ -414,7 +467,10 @@ "description": "The ID of the component to be displayed inside the modal." } }, - "required": ["entryPointChild", "contentChild"] + "required": [ + "entryPointChild", + "contentChild" + ] }, "Button": { "type": "object", @@ -465,14 +521,22 @@ } } }, - "required": ["key", "value"] + "required": [ + "key", + "value" + ] } } }, - "required": ["name"] + "required": [ + "name" + ] } }, - "required": ["child", "action"] + "required": [ + "child", + "action" + ] }, "CheckBox": { "type": "object", @@ -505,7 +569,10 @@ } } }, - "required": ["label", "value"] + "required": [ + "label", + "value" + ] }, "TextField": { "type": "object", @@ -553,7 +620,9 @@ "description": "A regular expression used for client-side validation of the input." } }, - "required": ["label"] + "required": [ + "label" + ] }, "DateTimeInput": { "type": "object", @@ -581,7 +650,9 @@ "description": "If true, allows the user to select a time." } }, - "required": ["value"] + "required": [ + "value" + ] }, "MultipleChoice": { "type": "object", @@ -632,7 +703,10 @@ "description": "The value to be associated with this option when selected." } }, - "required": ["label", "value"] + "required": [ + "label", + "value" + ] } }, "maxAllowedSelections": { @@ -650,7 +724,7 @@ "filterable": { "type": "boolean", "description": "If true, displays a search input to filter the options." - }, + } } }, "Slider": { @@ -679,7 +753,9 @@ "description": "The maximum value of the slider." } }, - "required": ["value"] + "required": [ + "value" + ] } }, "styles": { diff --git a/specification/v0_9/json/standard_catalog.json b/specification/v0_9/json/standard_catalog.json index 06a05b982..b3860b565 100644 --- a/specification/v0_9/json/standard_catalog.json +++ b/specification/v0_9/json/standard_catalog.json @@ -8,12 +8,18 @@ "Text": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Text" }, + "component": { + "const": "Text" + }, "text": { "$ref": "common_types.json#/$defs/DynamicString", "description": "The text content to display. While simple Markdown formatting is supported (i.e. without HTML, images, or links), utilizing dedicated UI components is generally preferred for a richer and more structured presentation." @@ -21,10 +27,21 @@ "variant": { "type": "string", "description": "A hint for the base text style.", - "enum": ["h1", "h2", "h3", "h4", "h5", "caption", "body"] + "enum": [ + "h1", + "h2", + "h3", + "h4", + "h5", + "caption", + "body" + ] } }, - "required": ["component", "text"] + "required": [ + "component", + "text" + ] } ], "unevaluatedProperties": false @@ -32,12 +49,18 @@ "Image": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Image" }, + "component": { + "const": "Image" + }, "url": { "$ref": "common_types.json#/$defs/DynamicString", "description": "The URL of the image to display." @@ -45,7 +68,13 @@ "fit": { "type": "string", "description": "Specifies how the image should be resized to fit its container. This corresponds to the CSS 'object-fit' property.", - "enum": ["contain", "cover", "fill", "none", "scale-down"] + "enum": [ + "contain", + "cover", + "fill", + "none", + "scale-down" + ] }, "variant": { "type": "string", @@ -60,7 +89,10 @@ ] } }, - "required": ["component", "url"] + "required": [ + "component", + "url" + ] } ], "unevaluatedProperties": false @@ -68,12 +100,18 @@ "Icon": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Icon" }, + "component": { + "const": "Icon" + }, "name": { "description": "The name of the icon to display.", "oneOf": [ @@ -144,15 +182,22 @@ { "type": "object", "properties": { - "path": { "type": "string" } + "path": { + "type": "string" + } }, - "required": ["path"], + "required": [ + "path" + ], "additionalProperties": false } ] } }, - "required": ["component", "name"] + "required": [ + "component", + "name" + ] } ], "unevaluatedProperties": false @@ -160,18 +205,27 @@ "Video": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Video" }, + "component": { + "const": "Video" + }, "url": { "$ref": "common_types.json#/$defs/DynamicString", "description": "The URL of the video to display." } }, - "required": ["component", "url"] + "required": [ + "component", + "url" + ] } ], "unevaluatedProperties": false @@ -179,12 +233,18 @@ "AudioPlayer": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "AudioPlayer" }, + "component": { + "const": "AudioPlayer" + }, "url": { "$ref": "common_types.json#/$defs/DynamicString", "description": "The URL of the audio to be played." @@ -194,7 +254,10 @@ "$ref": "common_types.json#/$defs/DynamicString" } }, - "required": ["component", "url"] + "required": [ + "component", + "url" + ] } ], "unevaluatedProperties": false @@ -202,13 +265,19 @@ "Row": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "description": "A layout component that arranges its children horizontally. To create a grid layout, nest Columns within this Row.", "properties": { - "component": { "const": "Row" }, + "component": { + "const": "Row" + }, "children": { "description": "Defines the children. Use an array of strings for a fixed set of children, or a template object to generate children from a data list. Children cannot be defined inline, they must be referred to by ID.", "$ref": "common_types.json#/$defs/ChildList" @@ -229,10 +298,18 @@ "align": { "type": "string", "description": "Defines the alignment of children along the cross axis (vertically). This is similar to the CSS 'align-items' property, but uses camelCase values (e.g., 'start').", - "enum": ["start", "center", "end", "stretch"] + "enum": [ + "start", + "center", + "end", + "stretch" + ] } }, - "required": ["component", "children"] + "required": [ + "component", + "children" + ] } ], "unevaluatedProperties": false @@ -240,13 +317,19 @@ "Column": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "description": "A layout component that arranges its children vertically. To create a grid layout, nest Rows within this Column.", "properties": { - "component": { "const": "Column" }, + "component": { + "const": "Column" + }, "children": { "description": "Defines the children. Use an array of strings for a fixed set of children, or a template object to generate children from a data list. Children cannot be defined inline, they must be referred to by ID.", "$ref": "common_types.json#/$defs/ChildList" @@ -267,10 +350,18 @@ "align": { "type": "string", "description": "Defines the alignment of children along the cross axis (horizontally). This is similar to the CSS 'align-items' property.", - "enum": ["center", "end", "start", "stretch"] + "enum": [ + "center", + "end", + "start", + "stretch" + ] } }, - "required": ["component", "children"] + "required": [ + "component", + "children" + ] } ], "unevaluatedProperties": false @@ -278,12 +369,18 @@ "List": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "List" }, + "component": { + "const": "List" + }, "children": { "description": "Defines the children. Use an array of strings for a fixed set of children, or a template object to generate children from a data list.", "$ref": "common_types.json#/$defs/ChildList" @@ -291,15 +388,26 @@ "direction": { "type": "string", "description": "The direction in which the list items are laid out.", - "enum": ["vertical", "horizontal"] + "enum": [ + "vertical", + "horizontal" + ] }, "align": { "type": "string", "description": "Defines the alignment of children along the cross axis.", - "enum": ["start", "center", "end", "stretch"] + "enum": [ + "start", + "center", + "end", + "stretch" + ] } }, - "required": ["component", "children"] + "required": [ + "component", + "children" + ] } ], "unevaluatedProperties": false @@ -307,18 +415,27 @@ "Card": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Card" }, + "component": { + "const": "Card" + }, "child": { "$ref": "common_types.json#/$defs/ComponentId", "description": "The ID of the single child component to be rendered inside the card. To display multiple elements, you MUST wrap them in a layout component (like Column or Row) and pass that container's ID here. Do NOT pass multiple IDs or a non-existent ID. Do NOT define the child component inline." } }, - "required": ["component", "child"] + "required": [ + "component", + "child" + ] } ], "unevaluatedProperties": false @@ -326,12 +443,18 @@ "Tabs": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Tabs" }, + "component": { + "const": "Tabs" + }, "tabs": { "type": "array", "description": "An array of objects, where each object defines a tab with a title and a child component.", @@ -347,12 +470,18 @@ "description": "The ID of the child component. Do NOT define the component inline." } }, - "required": ["title", "child"], + "required": [ + "title", + "child" + ], "additionalProperties": false } } }, - "required": ["component", "tabs"] + "required": [ + "component", + "tabs" + ] } ], "unevaluatedProperties": false @@ -360,12 +489,18 @@ "Modal": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Modal" }, + "component": { + "const": "Modal" + }, "trigger": { "$ref": "common_types.json#/$defs/ComponentId", "description": "The ID of the component that opens the modal when interacted with (e.g., a button). Do NOT define the component inline." @@ -375,7 +510,11 @@ "description": "The ID of the component to be displayed inside the modal. Do NOT define the component inline." } }, - "required": ["component", "trigger", "content"] + "required": [ + "component", + "trigger", + "content" + ] } ], "unevaluatedProperties": false @@ -383,20 +522,31 @@ "Divider": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, { "type": "object", "properties": { - "component": { "const": "Divider" }, + "component": { + "const": "Divider" + }, "axis": { "type": "string", "description": "The orientation of the divider.", - "enum": ["horizontal", "vertical"], + "enum": [ + "horizontal", + "vertical" + ], "default": "horizontal" } }, - "required": ["component"] + "required": [ + "component" + ] } ], "unevaluatedProperties": false @@ -404,13 +554,21 @@ "Button": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, - { "$ref": "common_types.json#/$defs/Checkable" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, + { + "$ref": "common_types.json#/$defs/Checkable" + }, { "type": "object", "properties": { - "component": { "const": "Button" }, + "component": { + "const": "Button" + }, "child": { "$ref": "common_types.json#/$defs/ComponentId", "description": "The ID of the child component. Use a 'Text' component for a labeled button. Only use an 'Icon' if the requirements explicitly ask for an icon-only button. Do NOT define the child component inline." @@ -418,13 +576,20 @@ "variant": { "type": "string", "description": "A hint for the button style. If omitted, a default button style is used. 'primary' indicates this is the main call-to-action button. 'borderless' means the button has no visual border or background, making its child content appear like a clickable link.", - "enum": ["primary", "borderless"] + "enum": [ + "primary", + "borderless" + ] }, "action": { "$ref": "common_types.json#/$defs/Action" } }, - "required": ["component", "child", "action"] + "required": [ + "component", + "child", + "action" + ] } ], "unevaluatedProperties": false @@ -432,13 +597,21 @@ "TextField": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, - { "$ref": "common_types.json#/$defs/Checkable" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, + { + "$ref": "common_types.json#/$defs/Checkable" + }, { "type": "object", "properties": { - "component": { "const": "TextField" }, + "component": { + "const": "TextField" + }, "label": { "$ref": "common_types.json#/$defs/DynamicString", "description": "The text label for the input field." @@ -450,10 +623,22 @@ "variant": { "type": "string", "description": "The type of input field to display.", - "enum": ["longText", "number", "shortText", "obscured"] + "enum": [ + "longText", + "number", + "shortText", + "obscured" + ] + }, + "validationRegexp": { + "type": "string", + "description": "A regular expression used for client-side validation of the input." } }, - "required": ["component", "label"] + "required": [ + "component", + "label" + ] } ], "unevaluatedProperties": false @@ -461,13 +646,21 @@ "CheckBox": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, - { "$ref": "common_types.json#/$defs/Checkable" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, + { + "$ref": "common_types.json#/$defs/Checkable" + }, { "type": "object", "properties": { - "component": { "const": "CheckBox" }, + "component": { + "const": "CheckBox" + }, "label": { "$ref": "common_types.json#/$defs/DynamicString", "description": "The text to display next to the checkbox." @@ -477,7 +670,11 @@ "description": "The current state of the checkbox (true for checked, false for unchecked)." } }, - "required": ["component", "label", "value"] + "required": [ + "component", + "label", + "value" + ] } ], "unevaluatedProperties": false @@ -485,14 +682,22 @@ "ChoicePicker": { "type": "object", "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, - { "$ref": "common_types.json#/$defs/Checkable" }, + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, + { + "$ref": "common_types.json#/$defs/Checkable" + }, { "type": "object", "description": "A component that allows selecting one or more options from a list.", "properties": { - "component": { "const": "ChoicePicker" }, + "component": { + "const": "ChoicePicker" + }, "label": { "$ref": "common_types.json#/$defs/DynamicString", "description": "The label for the group of options." @@ -500,7 +705,10 @@ "variant": { "type": "string", "description": "A hint for how the choice picker should be displayed and behave.", - "enum": ["multipleSelection", "mutuallyExclusive"] + "enum": [ + "multipleSelection", + "mutuallyExclusive" + ] }, "options": { "type": "array", @@ -517,7 +725,10 @@ "description": "The stable value associated with this option." } }, - "required": ["label", "value"], + "required": [ + "label", + "value" + ], "additionalProperties": false } }, @@ -533,618 +744,823 @@ "chips" ] }, - "filterable": { - "type": "boolean", - "description": "If true, displays a search input to filter the options." - } + "type": "string", + "description": "The display style of the component.", + "enum": [ + "checkbox", + "chips" + ] }, - "required": ["component", "options", "value"] - } - ], - "unevaluatedProperties": false - }, - "Slider": { - "type": "object", - "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, - { "$ref": "common_types.json#/$defs/Checkable" }, - { - "type": "object", - "properties": { - "component": { "const": "Slider" }, - "label": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "The label for the slider." - }, - "min": { - "type": "number", - "description": "The minimum value of the slider." - }, - "max": { - "type": "number", - "description": "The maximum value of the slider." - }, - "value": { - "$ref": "common_types.json#/$defs/DynamicNumber", - "description": "The current value of the slider." - } + "filterable": { + "type": "boolean", + "description": "If true, displays a search input to filter the options." + } + }, + "required": [ + "component", + "options", + "value" + ] + } + ], + "unevaluatedProperties": false + }, + "Slider": { + "type": "object", + "allOf": [ + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, + { + "$ref": "common_types.json#/$defs/Checkable" + }, + { + "type": "object", + "properties": { + "component": { + "const": "Slider" }, - "required": ["component", "value", "min", "max"] - } - ], - "unevaluatedProperties": false - }, - "DateTimeInput": { - "type": "object", - "allOf": [ - { "$ref": "common_types.json#/$defs/ComponentCommon" }, - { "$ref": "#/$defs/CatalogComponentCommon" }, - { "$ref": "common_types.json#/$defs/Checkable" }, - { - "type": "object", - "properties": { - "component": { "const": "DateTimeInput" }, - "value": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "The selected date and/or time value in ISO 8601 format. If not yet set, initialize with an empty string." - }, - "enableDate": { - "type": "boolean", - "description": "If true, allows the user to select a date." - }, - "enableTime": { - "type": "boolean", - "description": "If true, allows the user to select a time." - }, - "min": { - "allOf": [ - { - "$ref": "common_types.json#/$defs/DynamicString" + "label": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "The label for the slider." + }, + "min": { + "type": "number", + "description": "The minimum value of the slider." + }, + "max": { + "type": "number", + "description": "The maximum value of the slider." + }, + "value": { + "$ref": "common_types.json#/$defs/DynamicNumber", + "description": "The current value of the slider." + } + }, + "required": [ + "component", + "value", + "min", + "max" + ] + } + ], + "unevaluatedProperties": false + }, + "DateTimeInput": { + "type": "object", + "allOf": [ + { + "$ref": "common_types.json#/$defs/ComponentCommon" + }, + { + "$ref": "#/$defs/CatalogComponentCommon" + }, + { + "$ref": "common_types.json#/$defs/Checkable" + }, + { + "type": "object", + "properties": { + "component": { + "const": "DateTimeInput" + }, + "value": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "The selected date and/or time value in ISO 8601 format. If not yet set, initialize with an empty string." + }, + "enableDate": { + "type": "boolean", + "description": "If true, allows the user to select a date." + }, + "enableTime": { + "type": "boolean", + "description": "If true, allows the user to select a time." + }, + "min": { + "allOf": [ + { + "$ref": "common_types.json#/$defs/DynamicString" + }, + { + "if": { + "type": "string" }, - { - "if": { - "type": "string" - }, - "then": { - "oneOf": [ - { - "format": "date" - }, - { - "format": "time" - }, - { - "format": "date-time" - } - ] - } + "then": { + "oneOf": [ + { + "format": "date" + }, + { + "format": "time" + }, + { + "format": "date-time" + } + ] } - ], - "description": "The minimum allowed date/time in ISO 8601 format." - }, - "max": { - "allOf": [ - { - "$ref": "common_types.json#/$defs/DynamicString" + } + ], + "description": "The minimum allowed date/time in ISO 8601 format." + }, + "max": { + "allOf": [ + { + "$ref": "common_types.json#/$defs/DynamicString" + }, + { + "if": { + "type": "string" }, - { - "if": { - "type": "string" - }, - "then": { - "oneOf": [ - { - "format": "date" - }, - { - "format": "time" - }, - { - "format": "date-time" - } - ] - } + "then": { + "oneOf": [ + { + "format": "date" + }, + { + "format": "time" + }, + { + "format": "date-time" + } + ] } - ], - "description": "The maximum allowed date/time in ISO 8601 format." - }, - "label": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "The text label for the input field." - } + } + ], + "description": "The maximum allowed date/time in ISO 8601 format." }, - "required": ["component", "value"] - } - ], - "unevaluatedProperties": false - } - }, - "functions": { - "required": { - "type": "object", - "description": "Checks that the value is not null, undefined, or empty.", - "properties": { - "call": { - "const": "required" + "label": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "The text label for the input field." + } }, - "args": { - "type": "object", - "properties": { - "value": { - "description": "The value to check." - } - }, - "required": ["value"], - "additionalProperties": false + "required": [ + "component", + "value" + ] + } + ], + "unevaluatedProperties": false + } +}, +"functions": { + "required": { + "type": "object", + "description": "Checks that the value is not null, undefined, or empty.", + "properties": { + "call": { + "const": "required" + }, + "args": { + "type": "object", + "properties": { + "value": { + "description": "The value to check." + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "value" + ], + "additionalProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "boolean" + } }, - "regex": { - "type": "object", - "description": "Checks that the value matches a regular expression string.", - "properties": { - "call": { - "const": "regex" - }, - "args": { - "type": "object", - "properties": { - "value": { "$ref": "common_types.json#/$defs/DynamicString" }, - "pattern": { - "type": "string", - "description": "The regex pattern to match against." - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "regex": { + "type": "object", + "description": "Checks that the value matches a regular expression string.", + "properties": { + "call": { + "const": "regex" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicString" }, - "required": ["value", "pattern"], - "unevaluatedProperties": false + "pattern": { + "type": "string", + "description": "The regex pattern to match against." + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "value", + "pattern" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "boolean" + } }, - "length": { - "type": "object", - "description": "Checks string length constraints.", - "properties": { - "call": { - "const": "length" - }, - "args": { - "type": "object", - "properties": { - "value": { "$ref": "common_types.json#/$defs/DynamicString" }, - "min": { - "type": "integer", - "minimum": 0, - "description": "The minimum allowed length." - }, - "max": { - "type": "integer", - "minimum": 0, - "description": "The maximum allowed length." - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "length": { + "type": "object", + "description": "Checks string length constraints.", + "properties": { + "call": { + "const": "length" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicString" + }, + "min": { + "type": "integer", + "minimum": 0, + "description": "The minimum allowed length." }, - "required": ["value"], - "anyOf": [{ "required": ["min"] }, { "required": ["max"] }], - "unevaluatedProperties": false + "max": { + "type": "integer", + "minimum": 0, + "description": "The maximum allowed length." + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "value" + ], + "anyOf": [ + { + "required": [ + "min" + ] + }, + { + "required": [ + "max" + ] + } + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "boolean" + } }, - "numeric": { - "type": "object", - "description": "Checks numeric range constraints.", - "properties": { - "call": { - "const": "numeric" - }, - "args": { - "type": "object", - "properties": { - "value": { "$ref": "common_types.json#/$defs/DynamicNumber" }, - "min": { - "type": "number", - "description": "The minimum allowed value." - }, - "max": { - "type": "number", - "description": "The maximum allowed value." - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "numeric": { + "type": "object", + "description": "Checks numeric range constraints.", + "properties": { + "call": { + "const": "numeric" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicNumber" }, - "required": ["value"], - "anyOf": [{ "required": ["min"] }, { "required": ["max"] }], - "unevaluatedProperties": false + "min": { + "type": "number", + "description": "The minimum allowed value." + }, + "max": { + "type": "number", + "description": "The maximum allowed value." + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "value" + ], + "anyOf": [ + { + "required": [ + "min" + ] + }, + { + "required": [ + "max" + ] + } + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "boolean" + } }, - "email": { - "type": "object", - "description": "Checks that the value is a valid email address.", - "properties": { - "call": { - "const": "email" - }, - "args": { - "type": "object", - "properties": { - "value": { "$ref": "common_types.json#/$defs/DynamicString" } - }, - "required": ["value"], - "unevaluatedProperties": false + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "email": { + "type": "object", + "description": "Checks that the value is a valid email address.", + "properties": { + "call": { + "const": "email" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicString" + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "value" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "boolean" + } }, - "formatString": { - "type": "object", - "description": "Performs string interpolation of data model values and other functions in the catalog functions list and returns the resulting string. The value string can contain interpolated expressions in the `${expression}` format. Supported expression types include: JSON Pointer paths to the data model (e.g., `${/absolute/path}` or `${relative/path}`), and client-side function calls (e.g., `${now()}`). Function arguments must be named (e.g., `${formatDate(value:${/currentDate}, format:'MM-dd')}`). To include a literal `${` sequence, escape it as `\\${`.", - "properties": { - "call": { - "const": "formatString" - }, - "args": { - "type": "object", - "properties": { - "value": { "$ref": "common_types.json#/$defs/DynamicString" } - }, - "required": ["value"], - "unevaluatedProperties": false + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "formatString": { + "type": "object", + "description": "Performs string interpolation of data model values and other functions in the catalog functions list and returns the resulting string. The value string can contain interpolated expressions in the `${expression}` format. Supported expression types include: JSON Pointer paths to the data model (e.g., `${/absolute/path}` or `${relative/path}`), and client-side function calls (e.g., `${now()}`). Function arguments must be named (e.g., `${formatDate(value:${/currentDate}, format:'MM-dd')}`). To include a literal `${` sequence, escape it as `\\${`.", + "properties": { + "call": { + "const": "formatString" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicString" + } }, - "returnType": { - "const": "string" - } + "required": [ + "value" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "string" + } }, - "formatNumber": { - "type": "object", - "description": "Formats a number with the specified grouping and decimal precision.", - "properties": { - "call": { - "const": "formatNumber" - }, - "args": { - "type": "object", - "properties": { - "value": { - "$ref": "common_types.json#/$defs/DynamicNumber", - "description": "The number to format." - }, - "decimals": { - "$ref": "common_types.json#/$defs/DynamicNumber", - "description": "Optional. The number of decimal places to show. Defaults to 0 or 2 depending on locale." - }, - "grouping": { - "$ref": "common_types.json#/$defs/DynamicBoolean", - "description": "Optional. If true, uses locale-specific grouping separators (e.g. '1,000'). If false, returns raw digits (e.g. '1000'). Defaults to true." - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "formatNumber": { + "type": "object", + "description": "Formats a number with the specified grouping and decimal precision.", + "properties": { + "call": { + "const": "formatNumber" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicNumber", + "description": "The number to format." + }, + "decimals": { + "$ref": "common_types.json#/$defs/DynamicNumber", + "description": "Optional. The number of decimal places to show. Defaults to 0 or 2 depending on locale." }, - "required": ["value"], - "unevaluatedProperties": false + "grouping": { + "$ref": "common_types.json#/$defs/DynamicBoolean", + "description": "Optional. If true, uses locale-specific grouping separators (e.g. '1,000'). If false, returns raw digits (e.g. '1000'). Defaults to true." + } }, - "returnType": { - "const": "string" - } + "required": [ + "value" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "string" + } }, - "formatCurrency": { - "type": "object", - "description": "Formats a number as a currency string.", - "properties": { - "call": { - "const": "formatCurrency" - }, - "args": { - "type": "object", - "properties": { - "value": { - "$ref": "common_types.json#/$defs/DynamicNumber", - "description": "The monetary amount." - }, - "currency": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "The ISO 4217 currency code (e.g., 'USD', 'EUR')." - }, - "decimals": { - "$ref": "common_types.json#/$defs/DynamicNumber", - "description": "Optional. The number of decimal places to show. Defaults to 0 or 2 depending on locale." - }, - "grouping": { - "$ref": "common_types.json#/$defs/DynamicBoolean", - "description": "Optional. If true, uses locale-specific grouping separators (e.g. '1,000'). If false, returns raw digits (e.g. '1000'). Defaults to true." - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "formatCurrency": { + "type": "object", + "description": "Formats a number as a currency string.", + "properties": { + "call": { + "const": "formatCurrency" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicNumber", + "description": "The monetary amount." }, - "required": ["currency", "value"], - "unevaluatedProperties": false + "currency": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "The ISO 4217 currency code (e.g., 'USD', 'EUR')." + }, + "decimals": { + "$ref": "common_types.json#/$defs/DynamicNumber", + "description": "Optional. The number of decimal places to show. Defaults to 0 or 2 depending on locale." + }, + "grouping": { + "$ref": "common_types.json#/$defs/DynamicBoolean", + "description": "Optional. If true, uses locale-specific grouping separators (e.g. '1,000'). If false, returns raw digits (e.g. '1000'). Defaults to true." + } }, - "returnType": { - "const": "string" - } + "required": [ + "currency", + "value" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "string" + } }, - "formatDate": { - "type": "object", - "description": "Formats a timestamp into a string using a pattern.", - "properties": { - "call": { - "const": "formatDate" - }, - "args": { - "type": "object", - "properties": { - "value": { - "$ref": "common_types.json#/$defs/DynamicValue", - "description": "The date to format." - }, - "format": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "A Unicode TR35 date pattern string.\n\nToken Reference:\n- Year: 'yy' (26), 'yyyy' (2026)\n- Month: 'M' (1), 'MM' (01), 'MMM' (Jan), 'MMMM' (January)\n- Day: 'd' (1), 'dd' (01), 'E' (Tue), 'EEEE' (Tuesday)\n- Hour (12h): 'h' (1-12), 'hh' (01-12) - requires 'a' for AM/PM\n- Hour (24h): 'H' (0-23), 'HH' (00-23) - Military Time\n- Minute: 'mm' (00-59)\n- Second: 'ss' (00-59)\n- Period: 'a' (AM/PM)\n\nExamples:\n- 'MMM dd, yyyy' -> 'Jan 16, 2026'\n- 'HH:mm' -> '14:30' (Military)\n- 'h:mm a' -> '2:30 PM'\n- 'EEEE, d MMMM' -> 'Friday, 16 January'" - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "formatDate": { + "type": "object", + "description": "Formats a timestamp into a string using a pattern.", + "properties": { + "call": { + "const": "formatDate" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicValue", + "description": "The date to format." }, - "required": ["format", "value"], - "unevaluatedProperties": false + "format": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "A Unicode TR35 date pattern string.\n\nToken Reference:\n- Year: 'yy' (26), 'yyyy' (2026)\n- Month: 'M' (1), 'MM' (01), 'MMM' (Jan), 'MMMM' (January)\n- Day: 'd' (1), 'dd' (01), 'E' (Tue), 'EEEE' (Tuesday)\n- Hour (12h): 'h' (1-12), 'hh' (01-12) - requires 'a' for AM/PM\n- Hour (24h): 'H' (0-23), 'HH' (00-23) - Military Time\n- Minute: 'mm' (00-59)\n- Second: 'ss' (00-59)\n- Period: 'a' (AM/PM)\n\nExamples:\n- 'MMM dd, yyyy' -> 'Jan 16, 2026'\n- 'HH:mm' -> '14:30' (Military)\n- 'h:mm a' -> '2:30 PM'\n- 'EEEE, d MMMM' -> 'Friday, 16 January'" + } }, - "returnType": { - "const": "string" - } + "required": [ + "format", + "value" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "string" + } }, - "pluralize": { - "type": "object", - "description": "Returns a localized string based on the Common Locale Data Repository (CLDR) plural category of the count (zero, one, two, few, many, other). Requires an 'other' fallback. For English, just use 'one' and 'other'.", - "properties": { - "call": { - "const": "pluralize" - }, - "args": { - "type": "object", - "properties": { - "value": { - "$ref": "common_types.json#/$defs/DynamicNumber", - "description": "The numeric value used to determine the plural category." - }, - "zero": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "String for the 'zero' category (e.g., 0 items)." - }, - "one": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "String for the 'one' category (e.g., 1 item)." - }, - "two": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "String for the 'two' category (used in Arabic, Welsh, etc.)." - }, - "few": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "String for the 'few' category (e.g., small groups in Slavic languages)." - }, - "many": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "String for the 'many' category (e.g., large groups in various languages)." - }, - "other": { - "$ref": "common_types.json#/$defs/DynamicString", - "description": "The default/fallback string (used for general plural cases)." - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "pluralize": { + "type": "object", + "description": "Returns a localized string based on the Common Locale Data Repository (CLDR) plural category of the count (zero, one, two, few, many, other). Requires an 'other' fallback. For English, just use 'one' and 'other'.", + "properties": { + "call": { + "const": "pluralize" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicNumber", + "description": "The numeric value used to determine the plural category." + }, + "zero": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "String for the 'zero' category (e.g., 0 items)." + }, + "one": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "String for the 'one' category (e.g., 1 item)." + }, + "two": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "String for the 'two' category (used in Arabic, Welsh, etc.)." }, - "required": ["value", "other"], - "unevaluatedProperties": false + "few": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "String for the 'few' category (e.g., small groups in Slavic languages)." + }, + "many": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "String for the 'many' category (e.g., large groups in various languages)." + }, + "other": { + "$ref": "common_types.json#/$defs/DynamicString", + "description": "The default/fallback string (used for general plural cases)." + } }, - "returnType": { - "const": "string" - } + "required": [ + "value", + "other" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "string" + } }, - "openUrl": { - "type": "object", - "description": "Opens the specified URL in a browser or handler. This function has no return value.", - "properties": { - "call": { - "const": "openUrl" - }, - "args": { - "type": "object", - "properties": { - "url": { - "type": "string", - "format": "uri", - "description": "The URL to open." - } - }, - "required": ["url"], - "additionalProperties": false + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "openUrl": { + "type": "object", + "description": "Opens the specified URL in a browser or handler. This function has no return value.", + "properties": { + "call": { + "const": "openUrl" + }, + "args": { + "type": "object", + "properties": { + "url": { + "type": "string", + "format": "uri", + "description": "The URL to open." + } }, - "returnType": { - "const": "void" - } + "required": [ + "url" + ], + "additionalProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "void" + } }, - "and": { - "type": "object", - "description": "Performs a logical AND operation on a list of boolean values.", - "properties": { - "call": { - "const": "and" - }, - "args": { - "type": "object", - "properties": { - "values": { - "type": "array", - "description": "The list of boolean values to evaluate.", - "items": { - "$ref": "common_types.json#/$defs/DynamicBoolean" - }, - "minItems": 2 - } - }, - "required": ["values"], - "unevaluatedProperties": false + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "and": { + "type": "object", + "description": "Performs a logical AND operation on a list of boolean values.", + "properties": { + "call": { + "const": "and" + }, + "args": { + "type": "object", + "properties": { + "values": { + "type": "array", + "description": "The list of boolean values to evaluate.", + "items": { + "$ref": "common_types.json#/$defs/DynamicBoolean" + }, + "minItems": 2 + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "values" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "boolean" + } }, - "or": { - "type": "object", - "description": "Performs a logical OR operation on a list of boolean values.", - "properties": { - "call": { - "const": "or" - }, - "args": { - "type": "object", - "properties": { - "values": { - "type": "array", - "description": "The list of boolean values to evaluate.", - "items": { - "$ref": "common_types.json#/$defs/DynamicBoolean" - }, - "minItems": 2 - } - }, - "required": ["values"], - "unevaluatedProperties": false + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "or": { + "type": "object", + "description": "Performs a logical OR operation on a list of boolean values.", + "properties": { + "call": { + "const": "or" + }, + "args": { + "type": "object", + "properties": { + "values": { + "type": "array", + "description": "The list of boolean values to evaluate.", + "items": { + "$ref": "common_types.json#/$defs/DynamicBoolean" + }, + "minItems": 2 + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "values" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false + "returnType": { + "const": "boolean" + } }, - "not": { - "type": "object", - "description": "Performs a logical NOT operation on a boolean value.", - "properties": { - "call": { - "const": "not" - }, - "args": { - "type": "object", - "properties": { - "value": { - "$ref": "common_types.json#/$defs/DynamicBoolean", - "description": "The boolean value to negate." - } - }, - "required": ["value"], - "unevaluatedProperties": false + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + }, + "not": { + "type": "object", + "description": "Performs a logical NOT operation on a boolean value.", + "properties": { + "call": { + "const": "not" + }, + "args": { + "type": "object", + "properties": { + "value": { + "$ref": "common_types.json#/$defs/DynamicBoolean", + "description": "The boolean value to negate." + } }, - "returnType": { - "const": "boolean" - } + "required": [ + "value" + ], + "unevaluatedProperties": false }, - "required": ["call", "args"], - "unevaluatedProperties": false - } - }, - "theme": { - "primaryColor": { - "type": "string", - "description": "The primary brand color used for highlights (e.g., primary buttons, active borders). Renderers may generate variants of this color for different contexts. Format: Hexadecimal code (e.g., '#00BFFF').", - "pattern": "^#[0-9a-fA-F]{6}$" - }, - "iconUrl": { - "type": "string", - "format": "uri", - "description": "A URL for an image that identifies the agent or tool associated with the surface." + "returnType": { + "const": "boolean" + } }, - "agentDisplayName": { - "type": "string", - "description": "Text to be displayed next to the surface to identify the agent or tool that created it." - } + "required": [ + "call", + "args" + ], + "unevaluatedProperties": false + } +}, +"theme": { + "primaryColor": { + "type": "string", + "description": "The primary brand color used for highlights (e.g., primary buttons, active borders). Renderers may generate variants of this color for different contexts. Format: Hexadecimal code (e.g., '#00BFFF').", + "pattern": "^#[0-9a-fA-F]{6}$" }, - "$defs": { - "CatalogComponentCommon": { - "type": "object", - "properties": { - "weight": { - "type": "number", - "description": "The relative weight of this component within a Row or Column. This is similar to the CSS 'flex-grow' property. Note: this may ONLY be set when the component is a direct descendant of a Row or Column." - } + "iconUrl": { + "type": "string", + "format": "uri", + "description": "A URL for an image that identifies the agent or tool associated with the surface." + }, + "agentDisplayName": { + "type": "string", + "description": "Text to be displayed next to the surface to identify the agent or tool that created it." + } +}, +"$defs": { + "CatalogComponentCommon": { + "type": "object", + "properties": { + "weight": { + "type": "number", + "description": "The relative weight of this component within a Row or Column. This is similar to the CSS 'flex-grow' property. Note: this may ONLY be set when the component is a direct descendant of a Row or Column." } - }, - "anyComponent": { - "oneOf": [ - { "$ref": "#/components/Text" }, - { "$ref": "#/components/Image" }, - { "$ref": "#/components/Icon" }, - { "$ref": "#/components/Video" }, - { "$ref": "#/components/AudioPlayer" }, - { "$ref": "#/components/Row" }, - { "$ref": "#/components/Column" }, - { "$ref": "#/components/List" }, - { "$ref": "#/components/Card" }, - { "$ref": "#/components/Tabs" }, - { "$ref": "#/components/Modal" }, - { "$ref": "#/components/Divider" }, - { "$ref": "#/components/Button" }, - { "$ref": "#/components/TextField" }, - { "$ref": "#/components/CheckBox" }, - { "$ref": "#/components/ChoicePicker" }, - { "$ref": "#/components/Slider" }, - { "$ref": "#/components/DateTimeInput" } - ], - "discriminator": { - "propertyName": "component" + } + }, + "anyComponent": { + "oneOf": [ + { + "$ref": "#/components/Text" + }, + { + "$ref": "#/components/Image" + }, + { + "$ref": "#/components/Icon" + }, + { + "$ref": "#/components/Video" + }, + { + "$ref": "#/components/AudioPlayer" + }, + { + "$ref": "#/components/Row" + }, + { + "$ref": "#/components/Column" + }, + { + "$ref": "#/components/List" + }, + { + "$ref": "#/components/Card" + }, + { + "$ref": "#/components/Tabs" + }, + { + "$ref": "#/components/Modal" + }, + { + "$ref": "#/components/Divider" + }, + { + "$ref": "#/components/Button" + }, + { + "$ref": "#/components/TextField" + }, + { + "$ref": "#/components/CheckBox" + }, + { + "$ref": "#/components/ChoicePicker" + }, + { + "$ref": "#/components/Slider" + }, + { + "$ref": "#/components/DateTimeInput" } - }, - "anyFunction": { - "oneOf": [ - { "$ref": "#/functions/required" }, - { "$ref": "#/functions/regex" }, - { "$ref": "#/functions/length" }, - { "$ref": "#/functions/numeric" }, - { "$ref": "#/functions/email" }, - { "$ref": "#/functions/formatString" }, - { "$ref": "#/functions/formatNumber" }, - { "$ref": "#/functions/formatCurrency" }, - { "$ref": "#/functions/formatDate" }, - { "$ref": "#/functions/pluralize" }, - { "$ref": "#/functions/openUrl" }, - { "$ref": "#/functions/and" }, - { "$ref": "#/functions/or" }, - { "$ref": "#/functions/not" } - ] + ], + "discriminator": { + "propertyName": "component" } + }, + "anyFunction": { + "oneOf": [ + { + "$ref": "#/functions/required" + }, + { + "$ref": "#/functions/regex" + }, + { + "$ref": "#/functions/length" + }, + { + "$ref": "#/functions/numeric" + }, + { + "$ref": "#/functions/email" + }, + { + "$ref": "#/functions/formatString" + }, + { + "$ref": "#/functions/formatNumber" + }, + { + "$ref": "#/functions/formatCurrency" + }, + { + "$ref": "#/functions/formatDate" + }, + { + "$ref": "#/functions/pluralize" + }, + { + "$ref": "#/functions/openUrl" + }, + { + "$ref": "#/functions/and" + }, + { + "$ref": "#/functions/or" + }, + { + "$ref": "#/functions/not" + } + ] } } +} \ No newline at end of file