@golemui/gui-mcp 1.2.1 → 1.3.0-rc.0

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.
@@ -0,0 +1,3539 @@
1
+ import Ajv2020 from "ajv/dist/2020.js";
2
+ import addFormats from "ajv-formats";
3
+ const $schema$H = "https://json-schema.org/draft/2020-12/schema";
4
+ const $id$H = "https://golemui.com/schemas/gui/core/common.schema.json";
5
+ const $comment$5 = "Owned by @golemui/schemas (libs/schemas/src/lib/core/). Implementation trees contain a generated vendored copy, identical apart from an `$id` rebased onto the implementation's own tree. Edit the source file, then run `npm run generate:schemas`.";
6
+ const title$H = "Golem Common Definitions";
7
+ const $defs$F = { "reactiveExpression": { "type": "string", "description": "A reactive expression string. Use `$form` to access form data e.g. `$form.termsAccepted === true`" }, "dotPath": { "type": "string", "description": "A dot-separated path to a property in the form data" }, "uid": { "type": "string", "description": "Unique identifier for the widget" }, "chunkRef": { "type": "object", "description": "A reference to an external chunk file whose widget array will be inlined at this position in the form", "properties": { "$ref": { "type": "string", "description": "Relative path to a JSON chunk file" } }, "required": ["$ref"], "additionalProperties": false }, "localizable": { "description": "A value that can be a plain string or an i18n key object. Use a plain string for static text, or `{key, default, params}` to reference a translation key.", "oneOf": [{ "type": "string" }, { "type": "object", "properties": { "key": { "type": "string", "description": "The i18n translation key" }, "default": { "type": "string", "description": "Fallback text shown when the translation key is not found" }, "params": { "type": "object", "description": "Interpolation parameters passed to the translation function" } }, "required": ["key"], "additionalProperties": false }] }, "include": { "description": "Show this widget only in certain form states (`{in: [stateNames]}`) or when a reactive expression is true (`{when: expr}`). If omitted the widget is always shown.", "oneOf": [{ "type": "object", "properties": { "in": { "type": "array", "items": { "type": "string" }, "description": "List of state names (defined in the form `states` map) in which this widget should be visible" } }, "required": ["in"], "additionalProperties": false }, { "type": "object", "properties": { "when": { "$ref": "#/$defs/reactiveExpression" } }, "required": ["when"], "additionalProperties": false }] }, "exclude": { "description": "Hide this widget in certain form states (`{from: [stateNames]}`) or when a reactive expression is true (`{when: expr}`). If omitted the widget is never hidden.", "oneOf": [{ "type": "object", "properties": { "from": { "type": "array", "items": { "type": "string" }, "description": "List of state names (defined in the form `states` map) in which this widget should be hidden" } }, "required": ["from"], "additionalProperties": false }, { "type": "object", "properties": { "when": { "$ref": "#/$defs/reactiveExpression" } }, "required": ["when"], "additionalProperties": false }] }, "boolOrWhen": { "description": "A static boolean or a conditional `{when: reactiveExpression}` object evaluated at runtime. Use `{when: '$form.someField === true'}` for dynamic behavior.", "oneOf": [{ "type": "boolean" }, { "type": "object", "properties": { "when": { "$ref": "#/$defs/reactiveExpression" } }, "required": ["when"], "additionalProperties": false }] }, "on": { "type": "object", "description": 'Event handlers for this widget. Values are action names dispatched to the form\'s event bus. Each key also accepts a state-suffixed variant (`"click.<stateName>"`) that overrides the base handler when the named state is active.', "properties": { "load": { "type": "string", "description": "Action dispatched when the widget is first mounted" }, "click": { "type": "string", "description": "Action dispatched when the user clicks the widget" }, "change": { "type": "string", "description": "Action dispatched when the widget value changes" }, "filter": { "type": "string", "description": "Action dispatched on search/filter input, typically used with async data sources" }, "blur": { "type": "string", "description": "Action dispatched when the widget loses focus" } }, "patternProperties": { "^load\\.[^.]+$": { "type": "string", "description": 'State-suffixed load handler: used instead of `load` when the named state is active (e.g. `"load.myState"`)' }, "^click\\.[^.]+$": { "type": "string", "description": 'State-suffixed click handler: used instead of `click` when the named state is active (e.g. `"click.myState"`)' }, "^change\\.[^.]+$": { "type": "string", "description": 'State-suffixed change handler: used instead of `change` when the named state is active (e.g. `"change.myState"`)' }, "^filter\\.[^.]+$": { "type": "string", "description": 'State-suffixed filter handler: used instead of `filter` when the named state is active (e.g. `"filter.myState"`)' }, "^blur\\.[^.]+$": { "type": "string", "description": 'State-suffixed blur handler: used instead of `blur` when the named state is active (e.g. `"blur.myState"`)' } }, "additionalProperties": false }, "baseWidget": { "type": "object", "description": 'Base properties shared by all widgets. Root-level props that support state-suffixing (e.g. `"label.myState"`) are: `label`, `disabled`, `readonly`, `validator`, `size`. Any key inside `props` can also be suffixed. State names must be declared in the form `states` map.', "properties": { "$schema": { "type": "string" }, "uid": { "$ref": "#/$defs/uid" }, "type": { "type": "string" }, "size": { "type": "number", "description": "Column span in the form grid (1-12). Defaults to full width when omitted.", "minimum": 1, "maximum": 12 }, "include": { "$ref": "#/$defs/include" }, "exclude": { "$ref": "#/$defs/exclude" } }, "required": ["type"] } };
8
+ const commonSchemaJson = {
9
+ $schema: $schema$H,
10
+ $id: $id$H,
11
+ $comment: $comment$5,
12
+ title: title$H,
13
+ $defs: $defs$F
14
+ };
15
+ const $schema$G = "https://json-schema.org/draft/2020-12/schema";
16
+ const $id$G = "https://golemui.com/schemas/gui/ranges.schema.json";
17
+ const $comment$4 = "Owned by @golemui/gui-schemas (libs/gui/schemas/src/lib/). Handwritten, edit directly. Shared date and time range definitions used by the gui component schemas.";
18
+ const title$G = "GolemUI Range Definitions";
19
+ const $defs$E = { "dateRange": { "type": "object", "description": "A single date range. Used as the value of the range calendar and range date widgets, and by calendar/date-picker widgets to mark days as disabled.", "properties": { "start": { "type": "string", "description": "ISO-8601 date string for the start of the range (inclusive)" }, "end": { "type": "string", "description": "ISO-8601 date string for the end of the range (inclusive). Omit to cover a single day." } }, "required": ["start"], "additionalProperties": false }, "dateTimeRange": { "type": "object", "description": "A single date-time range (two ISO date-times). Used as the value of the range date-time widgets, and by those widgets for disabled instant spans.", "properties": { "start": { "type": "string", "description": "ISO-8601 date-time string for the start of the range (inclusive)" }, "end": { "type": "string", "description": "ISO-8601 date-time string for the end of the range (inclusive). Omit to cover the single instant at start." } }, "required": ["start"], "additionalProperties": false }, "isoTime": { "type": "string", "description": "A time of day as HH:MM or HH:MM:SS on a 24-hour clock", "pattern": "^([01][0-9]|2[0-3]):[0-5][0-9](:[0-5][0-9])?$" }, "timeRange": { "type": "object", "description": "A single time-of-day range. Used as the value of the range time widgets, and by time-picker widgets to mark times as disabled.", "properties": { "start": { "$ref": "#/$defs/isoTime" }, "end": { "$ref": "#/$defs/isoTime" } }, "required": ["start", "end"], "additionalProperties": false }, "scopedTimeRange": { "type": "object", "description": "A time-of-day range that optionally applies only on one date or on given weekdays. Used by date-time widgets to mark times as disabled.", "properties": { "start": { "$ref": "#/$defs/isoTime" }, "end": { "$ref": "#/$defs/isoTime" }, "date": { "type": "string", "pattern": "^\\d{4}-\\d{2}-\\d{2}$", "description": "ISO date: the range only applies on that date" }, "weekdays": { "type": "array", "items": { "type": "integer", "minimum": 0, "maximum": 6 }, "description": "Date.prototype.getDay() numbering: 0=Sunday to 6=Saturday" } }, "required": ["start", "end"], "additionalProperties": false } };
20
+ const rangesSchemaJson = {
21
+ $schema: $schema$G,
22
+ $id: $id$G,
23
+ $comment: $comment$4,
24
+ title: title$G,
25
+ $defs: $defs$E
26
+ };
27
+ const $schema$F = "https://json-schema.org/draft/2020-12/schema";
28
+ const $id$F = "https://golemui.com/schemas/gui/validators.schema.json";
29
+ const $comment$3 = "Owned by @golemui/gui-schemas (libs/gui/schemas/src/lib/). Handwritten, edit directly. Each implementation publishes its own validators schema exposing the #/$defs/validator entry pointer.";
30
+ const title$F = "GolemUI Validator Definitions";
31
+ const $defs$D = { "localizable": { "$ref": "./core/common.schema.json#/$defs/localizable" }, "stringValidator": { "type": "object", "properties": { "type": { "const": "string" }, "required": { "type": "boolean", "description": "Makes the field mandatory - validation fails if the value is empty or absent" }, "minLength": { "type": "number", "description": "Minimum number of characters the string must contain" }, "maxLength": { "type": "number", "description": "Maximum number of characters the string may contain" }, "pattern": { "type": "string", "description": "A regular expression pattern the value must match" }, "format": { "type": "string", "description": "A named format the string must conform to (e.g. `email`, `url`, `date`, `uuid`)", "enum": ["email", "hostname", "ipv4", "ipv6", "url", "uuid", "date", "time", "date-time", "duration"] }, "const": { "description": "The string must equal exactly this value" }, "enum": { "type": "array", "description": "The string must be one of these allowed values" }, "messages": { "type": "object", "description": "Custom error messages that override the default text for each constraint violation", "properties": { "invalid": { "$ref": "#/$defs/localizable", "description": "Shown when the value fails general type validation" }, "required": { "$ref": "#/$defs/localizable", "description": "Shown when a required field is empty" }, "minLength": { "$ref": "#/$defs/localizable", "description": "Shown when the value is shorter than `minLength`" }, "maxLength": { "$ref": "#/$defs/localizable", "description": "Shown when the value is longer than `maxLength`" }, "pattern": { "$ref": "#/$defs/localizable", "description": "Shown when the value does not match the `pattern` regex" }, "format": { "$ref": "#/$defs/localizable", "description": "Shown when the value does not conform to the specified `format`" }, "enum": { "$ref": "#/$defs/localizable", "description": "Shown when the value is not in the `enum` list" }, "const": { "$ref": "#/$defs/localizable", "description": "Shown when the value does not equal `const`" } }, "additionalProperties": false } }, "required": ["type"], "additionalProperties": false }, "numberValidator": { "type": "object", "properties": { "type": { "type": "string", "enum": ["number", "integer"] }, "required": { "type": "boolean", "description": "Makes the field mandatory - validation fails if the value is absent" }, "minimum": { "type": "number", "description": "The value must be greater than or equal to this number (inclusive)" }, "maximum": { "type": "number", "description": "The value must be less than or equal to this number (inclusive)" }, "exclusiveMinimum": { "type": "number", "description": "The value must be strictly greater than this number (exclusive)" }, "exclusiveMaximum": { "type": "number", "description": "The value must be strictly less than this number (exclusive)" }, "multipleOf": { "type": "number", "description": "The value must be a multiple of this number" }, "const": { "description": "The value must equal exactly this number" }, "enum": { "type": "array", "description": "The value must be one of these allowed numbers" }, "messages": { "type": "object", "description": "Custom error messages that override the default text for each constraint violation", "properties": { "invalid": { "$ref": "#/$defs/localizable", "description": "Shown when the value fails general type validation" }, "minimum": { "$ref": "#/$defs/localizable", "description": "Shown when the value is below `minimum`" }, "maximum": { "$ref": "#/$defs/localizable", "description": "Shown when the value exceeds `maximum`" }, "exclusiveMinimum": { "$ref": "#/$defs/localizable", "description": "Shown when the value is not strictly above `exclusiveMinimum`" }, "exclusiveMaximum": { "$ref": "#/$defs/localizable", "description": "Shown when the value is not strictly below `exclusiveMaximum`" }, "multipleOf": { "$ref": "#/$defs/localizable", "description": "Shown when the value is not a multiple of `multipleOf`" }, "enum": { "$ref": "#/$defs/localizable", "description": "Shown when the value is not in the `enum` list" }, "const": { "$ref": "#/$defs/localizable", "description": "Shown when the value does not equal `const`" } }, "additionalProperties": false } }, "required": ["type"], "additionalProperties": false }, "booleanValidator": { "type": "object", "properties": { "type": { "const": "boolean" }, "required": { "type": "boolean", "description": "Makes the field mandatory - validation fails if the value is absent or false (e.g. an unchecked required checkbox)" }, "const": { "description": "The value must equal exactly this boolean (e.g. `true` to require acceptance)" }, "messages": { "type": "object", "description": "Custom error messages that override the default text for each constraint violation", "properties": { "invalid": { "$ref": "#/$defs/localizable", "description": "Shown when the value fails general type validation" }, "const": { "$ref": "#/$defs/localizable", "description": "Shown when the value does not equal `const`" } }, "additionalProperties": false } }, "required": ["type"], "additionalProperties": false }, "arrayValidator": { "type": "object", "properties": { "type": { "const": "array" }, "required": { "type": "boolean", "description": "Makes the field mandatory - validation fails if the array is empty or absent" }, "minItems": { "type": "number", "description": "The array must contain at least this many items" }, "maxItems": { "type": "number", "description": "The array must contain no more than this many items" }, "uniqueItems": { "type": "boolean", "description": "When true, all items in the array must be distinct values" }, "messages": { "type": "object", "description": "Custom error messages that override the default text for each constraint violation", "properties": { "invalid": { "$ref": "#/$defs/localizable", "description": "Shown when the value fails general type validation" }, "required": { "$ref": "#/$defs/localizable", "description": "Shown when a required array is empty or absent" }, "minItems": { "$ref": "#/$defs/localizable", "description": "Shown when the array has fewer items than `minItems`" }, "maxItems": { "$ref": "#/$defs/localizable", "description": "Shown when the array has more items than `maxItems`" } }, "additionalProperties": false } }, "required": ["type"], "additionalProperties": false }, "customValidator": { "type": "object", "description": "A custom validator that delegates validation to application code. The registered validator function receives these constraint keys and must return a Standard Schema V1-compliant schema object (https://standardschema.dev). Add arbitrary constraint keys alongside `type` - they are passed as-is to the registered validator function.", "properties": { "type": { "const": "custom" }, "required": { "type": "boolean", "description": "Makes the field mandatory - evaluation is still delegated to the custom validator" } }, "required": ["type"], "additionalProperties": true }, "validator": { "description": "Validation rules for this field. The `type` discriminant selects the validator: `string`, `number`, `integer`, `boolean`, `array`, or `custom`.", "oneOf": [{ "$ref": "#/$defs/stringValidator" }, { "$ref": "#/$defs/numberValidator" }, { "$ref": "#/$defs/booleanValidator" }, { "$ref": "#/$defs/arrayValidator" }, { "$ref": "#/$defs/customValidator" }] } };
32
+ const validatorsSchemaJson = {
33
+ $schema: $schema$F,
34
+ $id: $id$F,
35
+ $comment: $comment$3,
36
+ title: title$F,
37
+ $defs: $defs$D
38
+ };
39
+ const $schema$E = "https://json-schema.org/draft/2020-12/schema";
40
+ const $id$E = "https://golemui.com/schemas/gui/form.schema.json";
41
+ const $comment$2 = "GENERATED by libs/gui/schemas/tools/generate-schemas.ts from src/lib/widget-manifest.ts. DO NOT EDIT. Regenerate with `npm run generate:schemas`.";
42
+ const title$E = "Golem Form DSL";
43
+ const type$C = "object";
44
+ const properties$B = { "$schema": { "type": "string" }, "states": { "type": "object", "description": 'Named boolean conditions keyed by state name, each mapping to a reactive expression. States serve two purposes: (1) gating widget visibility via `include.in` / `exclude.from`; (2) overriding individual widget properties when a state is active by appending `".<stateName>"` to any property key - e.g. `"label.myState": "Active label"` or `"props.hint.myState": "Active hint"`. Root-level suffixable props: `label`, `disabled`, `readonly`, `validator`, `size`. Any key inside `props` can also be suffixed.', "additionalProperties": { "$ref": "./core/common.schema.json#/$defs/reactiveExpression" } }, "form": { "type": "array", "description": "The ordered list of widgets that make up the form body", "items": { "$ref": "./widgets.schema.json#/$defs/formWidget" } }, "autocomplete": { "type": "string", "description": "HTML `autocomplete` attribute applied to the `<form>` element (e.g. `on`, `off`)" } };
45
+ const required$B = ["form"];
46
+ const additionalProperties = false;
47
+ const formSchemaJson = {
48
+ $schema: $schema$E,
49
+ $id: $id$E,
50
+ $comment: $comment$2,
51
+ title: title$E,
52
+ type: type$C,
53
+ properties: properties$B,
54
+ required: required$B,
55
+ additionalProperties
56
+ };
57
+ const $schema$D = "https://json-schema.org/draft/2020-12/schema";
58
+ const $id$D = "https://golemui.com/schemas/gui/layout-widget.schema.json";
59
+ const $comment$1 = "GENERATED by libs/gui/schemas/tools/generate-schemas.ts from src/lib/widget-manifest.ts. DO NOT EDIT. Regenerate with `npm run generate:schemas`.";
60
+ const title$D = "Golem Layout Widget";
61
+ const oneOf$1 = [{ "$ref": "./components/accordion.schema.json" }, { "$ref": "./components/flex.schema.json" }, { "$ref": "./components/grid.schema.json" }, { "$ref": "./components/tabs.schema.json" }];
62
+ const layoutWidgetSchemaJson = {
63
+ $schema: $schema$D,
64
+ $id: $id$D,
65
+ $comment: $comment$1,
66
+ title: title$D,
67
+ oneOf: oneOf$1
68
+ };
69
+ const $schema$C = "https://json-schema.org/draft/2020-12/schema";
70
+ const $id$C = "https://golemui.com/schemas/gui/widgets.schema.json";
71
+ const $comment = "GENERATED by libs/gui/schemas/tools/generate-schemas.ts from src/lib/widget-manifest.ts. DO NOT EDIT. Regenerate with `npm run generate:schemas`.";
72
+ const title$C = "Golem gui widgets";
73
+ const $defs$C = { "knownWidgetTypes": { "description": "Built-in widget `type` identifiers. Used to exclude built-ins from the custom-widget fallback so every widget matches exactly one schema. Types listed here without a component schema are not expressible in JSON and are rejected entirely instead of validating as custom widgets.", "enum": ["calendar", "dateTimeCalendar", "checkbox", "currency", "dateInput", "datePicker", "dateTimeInput", "dateTimePicker", "dropdown", "list", "markdown", "number", "password", "radiogroup", "rangeCalendar", "rangeDateInput", "rangeDatePicker", "rangeDateTimeInput", "rangeDateTimeCalendar", "rangeDateTimePicker", "rangeTimeInput", "rangeTimePicker", "repeater", "select", "tags", "textarea", "textinput", "timeInput", "timePicker", "toggle", "accordion", "flex", "grid", "tabs", "alert", "markdownText", "renderer", "button"] }, "formWidget": { "description": "A form widget: one of the built-in component schemas, the custom-widget fallback, or a reference to an external chunk file.", "oneOf": [{ "$ref": "./components/calendar.schema.json" }, { "$ref": "./components/datetimecalendar.schema.json" }, { "$ref": "./components/checkbox.schema.json" }, { "$ref": "./components/currency.schema.json" }, { "$ref": "./components/dateinput.schema.json" }, { "$ref": "./components/datepicker.schema.json" }, { "$ref": "./components/datetimeinput.schema.json" }, { "$ref": "./components/datetimepicker.schema.json" }, { "$ref": "./components/dropdown.schema.json" }, { "$ref": "./components/list.schema.json" }, { "$ref": "./components/markdown.schema.json" }, { "$ref": "./components/number.schema.json" }, { "$ref": "./components/password.schema.json" }, { "$ref": "./components/radiogroup.schema.json" }, { "$ref": "./components/rangecalendar.schema.json" }, { "$ref": "./components/rangedateinput.schema.json" }, { "$ref": "./components/rangedatepicker.schema.json" }, { "$ref": "./components/rangedatetimeinput.schema.json" }, { "$ref": "./components/rangedatetimecalendar.schema.json" }, { "$ref": "./components/rangedatetimepicker.schema.json" }, { "$ref": "./components/rangetimeinput.schema.json" }, { "$ref": "./components/rangetimepicker.schema.json" }, { "$ref": "./components/repeater.schema.json" }, { "$ref": "./components/select.schema.json" }, { "$ref": "./components/tags.schema.json" }, { "$ref": "./components/textarea.schema.json" }, { "$ref": "./components/textinput.schema.json" }, { "$ref": "./components/timeinput.schema.json" }, { "$ref": "./components/timepicker.schema.json" }, { "$ref": "./components/toggle.schema.json" }, { "$ref": "./components/accordion.schema.json" }, { "$ref": "./components/flex.schema.json" }, { "$ref": "./components/grid.schema.json" }, { "$ref": "./components/tabs.schema.json" }, { "$ref": "./components/alert.schema.json" }, { "$ref": "./components/markdowntext.schema.json" }, { "$ref": "./components/button.schema.json" }, { "$ref": "./components/custom.schema.json" }, { "$ref": "./core/common.schema.json#/$defs/chunkRef" }] } };
74
+ const widgetsSchemaJson = {
75
+ $schema: $schema$C,
76
+ $id: $id$C,
77
+ $comment,
78
+ title: title$C,
79
+ $defs: $defs$C
80
+ };
81
+ const $schema$B = "https://json-schema.org/draft/2020-12/schema";
82
+ const $id$B = "https://golemui.com/schemas/gui/components/calendar.schema.json";
83
+ const title$B = "Calendar Widget";
84
+ const type$B = "object";
85
+ const $defs$B = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "description": "Formatting of day numbers in the calendar grid (`numeric` = 1-31, `2-digit` = 01-31)", "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "description": "Formatting of weekday column headers (`short` = Mon, `long` = Monday, `narrow` = M)", "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "description": "Formatting of the month heading (`long` = January, `short` = Jan, `narrow` = J, `numeric` = 1, `2-digit` = 01)", "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "minDateProp": { "type": "string", "description": "ISO-8601 date string for the earliest selectable date (inclusive)" }, "maxDateProp": { "type": "string", "description": "ISO-8601 date string for the latest selectable date (inclusive)" }, "numberOfMonthsProp": { "type": "number", "description": "Number of month panels to display side by side. Defaults to 1." }, "disabledRangesProp": { "type": "array", "description": "Date ranges that are shown but cannot be selected", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } } };
86
+ const allOf$B = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
87
+ const properties$A = { "kind": { "const": "input" }, "type": { "const": "calendar" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" } }, "additionalProperties": false } };
88
+ const patternProperties$u = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
89
+ const required$A = ["kind", "type", "path"];
90
+ const unevaluatedProperties$B = false;
91
+ const calendarSchemaJson = {
92
+ $schema: $schema$B,
93
+ $id: $id$B,
94
+ title: title$B,
95
+ type: type$B,
96
+ $defs: $defs$B,
97
+ allOf: allOf$B,
98
+ properties: properties$A,
99
+ patternProperties: patternProperties$u,
100
+ required: required$A,
101
+ unevaluatedProperties: unevaluatedProperties$B
102
+ };
103
+ const $schema$A = "https://json-schema.org/draft/2020-12/schema";
104
+ const $id$A = "https://golemui.com/schemas/gui/components/datetimecalendar.schema.json";
105
+ const title$A = "DateTimeCalendar Widget";
106
+ const type$A = "object";
107
+ const $defs$A = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "description": "Formatting of day numbers in the calendar grid (`numeric` = 1-31, `2-digit` = 01-31)", "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "description": "Formatting of weekday column headers (`short` = Mon, `long` = Monday, `narrow` = M)", "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "description": "Formatting of the month heading (`long` = January, `short` = Jan, `narrow` = J, `numeric` = 1, `2-digit` = 01)", "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "minDateProp": { "type": "string", "description": "ISO-8601 date string for the earliest selectable date (inclusive)" }, "maxDateProp": { "type": "string", "description": "ISO-8601 date string for the latest selectable date (inclusive)" }, "numberOfMonthsProp": { "type": "number", "description": "Number of month panels to display side by side. Defaults to 1. The time row and grid render on the first panel only." }, "disabledRangesProp": { "type": "array", "description": "Date ranges that are shown but cannot be selected", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } }, "hourFormatProp": { "enum": ["12", "24"] }, "allowCustomTimeProp": { "type": "boolean" }, "minuteStepProp": { "type": "number", "minimum": 1 }, "isoTimeProp": { "$ref": "../ranges.schema.json#/$defs/isoTime" }, "disabledTimeRangesProp": { "type": "array", "description": "Time ranges rendered disabled. Entries optionally scope to a date or given weekdays", "items": { "$ref": "../ranges.schema.json#/$defs/scopedTimeRange" } } };
108
+ const allOf$A = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
109
+ const properties$z = { "kind": { "const": "input" }, "type": { "const": "dateTimeCalendar" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "minTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledTimeRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "noAvailableTimesMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hint": { "$ref": "#/$defs/hintProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "minTime": { "$ref": "#/$defs/isoTimeProp" }, "maxTime": { "$ref": "#/$defs/isoTimeProp" }, "disabledTimeRanges": { "$ref": "#/$defs/disabledTimeRangesProp" }, "allowCustomTime": { "$ref": "#/$defs/allowCustomTimeProp" } }, "patternProperties": { "^minTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledTimeRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^noAvailableTimesMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^minTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^maxTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^disabledTimeRanges\\.[^.]+$": { "$ref": "#/$defs/disabledTimeRangesProp" }, "^allowCustomTime\\.[^.]+$": { "$ref": "#/$defs/allowCustomTimeProp" } }, "additionalProperties": false } };
110
+ const patternProperties$t = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
111
+ const required$z = ["kind", "type", "path"];
112
+ const unevaluatedProperties$A = false;
113
+ const datetimecalendarSchemaJson = {
114
+ $schema: $schema$A,
115
+ $id: $id$A,
116
+ title: title$A,
117
+ type: type$A,
118
+ $defs: $defs$A,
119
+ allOf: allOf$A,
120
+ properties: properties$z,
121
+ patternProperties: patternProperties$t,
122
+ required: required$z,
123
+ unevaluatedProperties: unevaluatedProperties$A
124
+ };
125
+ const $schema$z = "https://json-schema.org/draft/2020-12/schema";
126
+ const $id$z = "https://golemui.com/schemas/gui/components/checkbox.schema.json";
127
+ const title$z = "Checkbox Widget";
128
+ const type$z = "object";
129
+ const $defs$z = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "checkboxPositionProp": { "enum": ["left", "right"], "default": "left" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
130
+ const allOf$z = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
131
+ const properties$y = { "kind": { "const": "input" }, "type": { "const": "checkbox" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "boolean" }, "props": { "type": "object", "properties": { "checkboxPosition": { "$ref": "#/$defs/checkboxPositionProp" }, "hint": { "$ref": "#/$defs/hintProp" } }, "patternProperties": { "^checkboxPosition\\.[^.]+$": { "$ref": "#/$defs/checkboxPositionProp" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" } }, "additionalProperties": false } };
132
+ const patternProperties$s = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
133
+ const required$y = ["kind", "type", "path"];
134
+ const unevaluatedProperties$z = false;
135
+ const checkboxSchemaJson = {
136
+ $schema: $schema$z,
137
+ $id: $id$z,
138
+ title: title$z,
139
+ type: type$z,
140
+ $defs: $defs$z,
141
+ allOf: allOf$z,
142
+ properties: properties$y,
143
+ patternProperties: patternProperties$s,
144
+ required: required$y,
145
+ unevaluatedProperties: unevaluatedProperties$z
146
+ };
147
+ const $schema$y = "https://json-schema.org/draft/2020-12/schema";
148
+ const $id$y = "https://golemui.com/schemas/gui/components/currency.schema.json";
149
+ const title$y = "Currency Widget";
150
+ const type$y = "object";
151
+ const $defs$y = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "currencyProp": { "type": "string" }, "stepProp": { "type": "number" }, "maximumFractionDigitsProp": { "type": "number" }, "minimumFractionDigitsProp": { "type": "number" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "autocompleteProp": { "type": "string" } };
152
+ const allOf$y = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
153
+ const properties$x = { "kind": { "const": "input" }, "type": { "const": "currency" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "number" }, "props": { "type": "object", "properties": { "currency": { "$ref": "#/$defs/currencyProp" }, "step": { "$ref": "#/$defs/stepProp" }, "maximumFractionDigits": { "$ref": "#/$defs/maximumFractionDigitsProp" }, "minimumFractionDigits": { "$ref": "#/$defs/minimumFractionDigitsProp" }, "hint": { "$ref": "#/$defs/hintProp" }, "placeholder": { "$ref": "#/$defs/placeholderProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^currency\\.[^.]+$": { "$ref": "#/$defs/currencyProp" }, "^step\\.[^.]+$": { "$ref": "#/$defs/stepProp" }, "^maximumFractionDigits\\.[^.]+$": { "$ref": "#/$defs/maximumFractionDigitsProp" }, "^minimumFractionDigits\\.[^.]+$": { "$ref": "#/$defs/minimumFractionDigitsProp" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
154
+ const patternProperties$r = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
155
+ const required$x = ["kind", "type", "path"];
156
+ const unevaluatedProperties$y = false;
157
+ const currencySchemaJson = {
158
+ $schema: $schema$y,
159
+ $id: $id$y,
160
+ title: title$y,
161
+ type: type$y,
162
+ $defs: $defs$y,
163
+ allOf: allOf$y,
164
+ properties: properties$x,
165
+ patternProperties: patternProperties$r,
166
+ required: required$x,
167
+ unevaluatedProperties: unevaluatedProperties$y
168
+ };
169
+ const $schema$x = "https://json-schema.org/draft/2020-12/schema";
170
+ const $id$x = "https://golemui.com/schemas/gui/components/dateinput.schema.json";
171
+ const title$x = "DateInput Widget";
172
+ const type$x = "object";
173
+ const $defs$x = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "minDateProp": { "type": "string" }, "maxDateProp": { "type": "string" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
174
+ const allOf$x = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
175
+ const properties$w = { "kind": { "const": "input" }, "type": { "const": "dateInput" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "invalidDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "minDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" } }, "patternProperties": { "^invalidDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^minDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" } }, "additionalProperties": false } };
176
+ const patternProperties$q = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
177
+ const required$w = ["kind", "type", "path"];
178
+ const unevaluatedProperties$x = false;
179
+ const dateinputSchemaJson = {
180
+ $schema: $schema$x,
181
+ $id: $id$x,
182
+ title: title$x,
183
+ type: type$x,
184
+ $defs: $defs$x,
185
+ allOf: allOf$x,
186
+ properties: properties$w,
187
+ patternProperties: patternProperties$q,
188
+ required: required$w,
189
+ unevaluatedProperties: unevaluatedProperties$x
190
+ };
191
+ const $schema$w = "https://json-schema.org/draft/2020-12/schema";
192
+ const $id$w = "https://golemui.com/schemas/gui/components/datepicker.schema.json";
193
+ const title$w = "DatePicker Widget";
194
+ const type$w = "object";
195
+ const $defs$w = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "toggleAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "minDateProp": { "type": "string" }, "maxDateProp": { "type": "string" }, "numberOfMonthsProp": { "type": "number" }, "disabledRangesProp": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } } };
196
+ const allOf$w = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
197
+ const properties$v = { "kind": { "const": "input" }, "type": { "const": "datePicker" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "invalidDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDateRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "toggleAriaLabel": { "$ref": "#/$defs/toggleAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" } }, "patternProperties": { "^invalidDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledDateRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^toggleAriaLabel\\.[^.]+$": { "$ref": "#/$defs/toggleAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" } }, "additionalProperties": false } };
198
+ const patternProperties$p = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
199
+ const required$v = ["kind", "type", "path"];
200
+ const unevaluatedProperties$w = false;
201
+ const datepickerSchemaJson = {
202
+ $schema: $schema$w,
203
+ $id: $id$w,
204
+ title: title$w,
205
+ type: type$w,
206
+ $defs: $defs$w,
207
+ allOf: allOf$w,
208
+ properties: properties$v,
209
+ patternProperties: patternProperties$p,
210
+ required: required$v,
211
+ unevaluatedProperties: unevaluatedProperties$w
212
+ };
213
+ const $schema$v = "https://json-schema.org/draft/2020-12/schema";
214
+ const $id$v = "https://golemui.com/schemas/gui/components/datetimeinput.schema.json";
215
+ const title$v = "DateTimeInput Widget";
216
+ const type$v = "object";
217
+ const $defs$v = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "minDateProp": { "type": "string" }, "maxDateProp": { "type": "string" }, "minTimeProp": { "type": "string" }, "maxTimeProp": { "type": "string" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
218
+ const allOf$v = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
219
+ const properties$u = { "kind": { "const": "input" }, "type": { "const": "dateTimeInput" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "invalidDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "minTime": { "$ref": "#/$defs/minTimeProp" }, "maxTime": { "$ref": "#/$defs/maxTimeProp" }, "minDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "patternProperties": { "^invalidDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^minTime\\.[^.]+$": { "$ref": "#/$defs/minTimeProp" }, "^maxTime\\.[^.]+$": { "$ref": "#/$defs/maxTimeProp" }, "^minDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "additionalProperties": false } };
220
+ const patternProperties$o = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
221
+ const required$u = ["kind", "type", "path"];
222
+ const unevaluatedProperties$v = false;
223
+ const datetimeinputSchemaJson = {
224
+ $schema: $schema$v,
225
+ $id: $id$v,
226
+ title: title$v,
227
+ type: type$v,
228
+ $defs: $defs$v,
229
+ allOf: allOf$v,
230
+ properties: properties$u,
231
+ patternProperties: patternProperties$o,
232
+ required: required$u,
233
+ unevaluatedProperties: unevaluatedProperties$v
234
+ };
235
+ const $schema$u = "https://json-schema.org/draft/2020-12/schema";
236
+ const $id$u = "https://golemui.com/schemas/gui/components/datetimepicker.schema.json";
237
+ const title$u = "DateTimePicker Widget";
238
+ const type$u = "object";
239
+ const $defs$u = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "toggleAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "description": "Formatting of day numbers in the calendar grid (`numeric` = 1-31, `2-digit` = 01-31)", "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "description": "Formatting of weekday column headers (`short` = Mon, `long` = Monday, `narrow` = M)", "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "description": "Formatting of the month heading (`long` = January, `short` = Jan, `narrow` = J, `numeric` = 1, `2-digit` = 01)", "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "minDateProp": { "type": "string", "description": "ISO-8601 date string for the earliest selectable date (inclusive)" }, "maxDateProp": { "type": "string", "description": "ISO-8601 date string for the latest selectable date (inclusive)" }, "numberOfMonthsProp": { "type": "number", "description": "Number of month panels to display side by side. Defaults to 1. The time row and grid render on the first panel only." }, "disabledRangesProp": { "type": "array", "description": "Date ranges that are shown but cannot be selected", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } }, "hourFormatProp": { "enum": ["12", "24"] }, "allowCustomTimeProp": { "type": "boolean" }, "minuteStepProp": { "type": "number", "minimum": 1 }, "isoTimeProp": { "$ref": "../ranges.schema.json#/$defs/isoTime" }, "disabledTimeRangesProp": { "type": "array", "description": "Time ranges rendered disabled. Entries optionally scope to a date or given weekdays", "items": { "$ref": "../ranges.schema.json#/$defs/scopedTimeRange" } } };
240
+ const allOf$u = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
241
+ const properties$t = { "kind": { "const": "input" }, "type": { "const": "dateTimePicker" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "invalidDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDateRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledTimeRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "noAvailableTimesMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "toggleAriaLabel": { "$ref": "#/$defs/toggleAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "minTime": { "$ref": "#/$defs/isoTimeProp" }, "maxTime": { "$ref": "#/$defs/isoTimeProp" }, "disabledTimeRanges": { "$ref": "#/$defs/disabledTimeRangesProp" }, "allowCustomTime": { "$ref": "#/$defs/allowCustomTimeProp" } }, "patternProperties": { "^invalidDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledDateRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledTimeRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^noAvailableTimesMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^toggleAriaLabel\\.[^.]+$": { "$ref": "#/$defs/toggleAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^minTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^maxTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^disabledTimeRanges\\.[^.]+$": { "$ref": "#/$defs/disabledTimeRangesProp" }, "^allowCustomTime\\.[^.]+$": { "$ref": "#/$defs/allowCustomTimeProp" } }, "additionalProperties": false } };
242
+ const patternProperties$n = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
243
+ const required$t = ["kind", "type", "path"];
244
+ const unevaluatedProperties$u = false;
245
+ const datetimepickerSchemaJson = {
246
+ $schema: $schema$u,
247
+ $id: $id$u,
248
+ title: title$u,
249
+ type: type$u,
250
+ $defs: $defs$u,
251
+ allOf: allOf$u,
252
+ properties: properties$t,
253
+ patternProperties: patternProperties$n,
254
+ required: required$t,
255
+ unevaluatedProperties: unevaluatedProperties$u
256
+ };
257
+ const $schema$t = "https://json-schema.org/draft/2020-12/schema";
258
+ const $id$t = "https://golemui.com/schemas/gui/components/dropdown.schema.json";
259
+ const title$t = "Dropdown Widget";
260
+ const type$t = "object";
261
+ const $defs$t = { "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "itemsProp": { "type": "array", "description": "Items are either primitive values (string/number) or arbitrary record objects (paired with `labelField`/`valueField`/`itemRenderer` for custom rendering). Note: widget templates inside items are only supported on `repeater`, not here.", "items": { "type": ["string", "number", "object"] } }, "labelFieldProp": { "type": "string", "description": 'Object property used as the display label when items are objects (e.g. `"name"` reads `item.name`)' }, "valueFieldProp": { "type": "string", "description": 'Object property used as the stored value when items are objects (e.g. `"id"` stores `item.id`)' }, "searchFieldsProp": { "type": "array", "description": "Object properties searched when the user types in the filter box. Defaults to `labelField` when omitted.", "items": { "type": "string" } }, "heightProp": { "type": "number", "description": "Fixed pixel height of the dropdown list panel (enables virtual scrolling for large lists)" }, "itemHeightProp": { "type": "number", "description": "Fixed pixel height of each item row, required for virtual scrolling when `height` is set" }, "itemRendererProp": { "type": "string", "description": "Name of a registered custom item renderer component used to display each option" }, "inputDebounceProp": { "type": "number", "description": "Milliseconds to debounce the filter input before firing the `on.filter` event (default: 0)" }, "autocompleteProp": { "type": "string", "description": "HTML `autocomplete` attribute applied to the underlying input element" } };
262
+ const allOf$t = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
263
+ const properties$s = { "kind": { "const": "input" }, "type": { "const": "dropdown" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": ["string", "number"] }, "props": { "type": "object", "required": ["items"], "properties": { "placeholder": { "$ref": "#/$defs/placeholderProp" }, "hint": { "$ref": "#/$defs/hintProp" }, "items": { "$ref": "#/$defs/itemsProp" }, "labelField": { "$ref": "#/$defs/labelFieldProp" }, "valueField": { "$ref": "#/$defs/valueFieldProp" }, "searchFields": { "$ref": "#/$defs/searchFieldsProp" }, "height": { "$ref": "#/$defs/heightProp" }, "itemHeight": { "$ref": "#/$defs/itemHeightProp" }, "itemRenderer": { "$ref": "#/$defs/itemRendererProp" }, "inputDebounce": { "$ref": "#/$defs/inputDebounceProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^items\\.[^.]+$": { "$ref": "#/$defs/itemsProp" }, "^labelField\\.[^.]+$": { "$ref": "#/$defs/labelFieldProp" }, "^valueField\\.[^.]+$": { "$ref": "#/$defs/valueFieldProp" }, "^searchFields\\.[^.]+$": { "$ref": "#/$defs/searchFieldsProp" }, "^height\\.[^.]+$": { "$ref": "#/$defs/heightProp" }, "^itemHeight\\.[^.]+$": { "$ref": "#/$defs/itemHeightProp" }, "^itemRenderer\\.[^.]+$": { "$ref": "#/$defs/itemRendererProp" }, "^inputDebounce\\.[^.]+$": { "$ref": "#/$defs/inputDebounceProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
264
+ const patternProperties$m = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
265
+ const required$s = ["kind", "type", "path", "props"];
266
+ const unevaluatedProperties$t = false;
267
+ const dropdownSchemaJson = {
268
+ $schema: $schema$t,
269
+ $id: $id$t,
270
+ title: title$t,
271
+ type: type$t,
272
+ $defs: $defs$t,
273
+ allOf: allOf$t,
274
+ properties: properties$s,
275
+ patternProperties: patternProperties$m,
276
+ required: required$s,
277
+ unevaluatedProperties: unevaluatedProperties$t
278
+ };
279
+ const $schema$s = "https://json-schema.org/draft/2020-12/schema";
280
+ const $id$s = "https://golemui.com/schemas/gui/components/list.schema.json";
281
+ const title$s = "List Widget";
282
+ const type$s = "object";
283
+ const $defs$s = { "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "itemsProp": { "type": "array", "description": "Items are either primitive values (string/number) or arbitrary record objects (paired with `labelField`/`valueField`/`itemRenderer` for custom rendering). Note: widget templates inside items are only supported on `repeater`, not here.", "items": { "type": ["string", "number", "object"] } }, "labelFieldProp": { "type": "string" }, "valueFieldProp": { "type": "string" }, "heightProp": { "type": "number" }, "itemHeightProp": { "type": "number" }, "itemRendererProp": { "type": "string" } };
284
+ const allOf$s = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
285
+ const properties$r = { "kind": { "const": "input" }, "type": { "const": "list" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": ["string", "number"] }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "items": { "$ref": "#/$defs/itemsProp" }, "labelField": { "$ref": "#/$defs/labelFieldProp" }, "valueField": { "$ref": "#/$defs/valueFieldProp" }, "height": { "$ref": "#/$defs/heightProp" }, "itemHeight": { "$ref": "#/$defs/itemHeightProp" }, "itemRenderer": { "$ref": "#/$defs/itemRendererProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^items\\.[^.]+$": { "$ref": "#/$defs/itemsProp" }, "^labelField\\.[^.]+$": { "$ref": "#/$defs/labelFieldProp" }, "^valueField\\.[^.]+$": { "$ref": "#/$defs/valueFieldProp" }, "^height\\.[^.]+$": { "$ref": "#/$defs/heightProp" }, "^itemHeight\\.[^.]+$": { "$ref": "#/$defs/itemHeightProp" }, "^itemRenderer\\.[^.]+$": { "$ref": "#/$defs/itemRendererProp" } }, "additionalProperties": false } };
286
+ const patternProperties$l = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
287
+ const required$r = ["kind", "type", "path"];
288
+ const unevaluatedProperties$s = false;
289
+ const listSchemaJson = {
290
+ $schema: $schema$s,
291
+ $id: $id$s,
292
+ title: title$s,
293
+ type: type$s,
294
+ $defs: $defs$s,
295
+ allOf: allOf$s,
296
+ properties: properties$r,
297
+ patternProperties: patternProperties$l,
298
+ required: required$r,
299
+ unevaluatedProperties: unevaluatedProperties$s
300
+ };
301
+ const $schema$r = "https://json-schema.org/draft/2020-12/schema";
302
+ const $id$r = "https://golemui.com/schemas/gui/components/markdown.schema.json";
303
+ const title$r = "Markdown Widget";
304
+ const type$r = "object";
305
+ const $defs$r = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "counterModeProp": { "enum": ["remaining", "current"] }, "minimumHeightProp": { "type": "number" }, "autoGrowProp": { "type": "boolean" }, "defaultOpenPreviewProp": { "type": "boolean" }, "maxLengthProp": { "type": "number" }, "toolsProp": { "type": "array", "items": { "enum": ["H", "B", "I", "Q", "L", "OL", "UL", "|"] } }, "splitViewTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "toolbarAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "headingTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "boldTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "italicTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "strikethroughTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "quoteTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "linkTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "orderedListTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "unorderedListTitleProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "autocompleteProp": { "type": "string" } };
306
+ const allOf$r = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
307
+ const properties$q = { "kind": { "const": "input" }, "type": { "const": "markdown" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "placeholder": { "$ref": "#/$defs/placeholderProp" }, "counterMode": { "$ref": "#/$defs/counterModeProp" }, "minimumHeight": { "$ref": "#/$defs/minimumHeightProp" }, "autoGrow": { "$ref": "#/$defs/autoGrowProp" }, "defaultOpenPreview": { "$ref": "#/$defs/defaultOpenPreviewProp" }, "maxLength": { "$ref": "#/$defs/maxLengthProp" }, "tools": { "$ref": "#/$defs/toolsProp" }, "splitViewTitle": { "$ref": "#/$defs/splitViewTitleProp" }, "toolbarAriaLabel": { "$ref": "#/$defs/toolbarAriaLabelProp" }, "headingTitle": { "$ref": "#/$defs/headingTitleProp" }, "boldTitle": { "$ref": "#/$defs/boldTitleProp" }, "italicTitle": { "$ref": "#/$defs/italicTitleProp" }, "strikethroughTitle": { "$ref": "#/$defs/strikethroughTitleProp" }, "quoteTitle": { "$ref": "#/$defs/quoteTitleProp" }, "linkTitle": { "$ref": "#/$defs/linkTitleProp" }, "orderedListTitle": { "$ref": "#/$defs/orderedListTitleProp" }, "unorderedListTitle": { "$ref": "#/$defs/unorderedListTitleProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^counterMode\\.[^.]+$": { "$ref": "#/$defs/counterModeProp" }, "^minimumHeight\\.[^.]+$": { "$ref": "#/$defs/minimumHeightProp" }, "^autoGrow\\.[^.]+$": { "$ref": "#/$defs/autoGrowProp" }, "^defaultOpenPreview\\.[^.]+$": { "$ref": "#/$defs/defaultOpenPreviewProp" }, "^maxLength\\.[^.]+$": { "$ref": "#/$defs/maxLengthProp" }, "^tools\\.[^.]+$": { "$ref": "#/$defs/toolsProp" }, "^splitViewTitle\\.[^.]+$": { "$ref": "#/$defs/splitViewTitleProp" }, "^toolbarAriaLabel\\.[^.]+$": { "$ref": "#/$defs/toolbarAriaLabelProp" }, "^headingTitle\\.[^.]+$": { "$ref": "#/$defs/headingTitleProp" }, "^boldTitle\\.[^.]+$": { "$ref": "#/$defs/boldTitleProp" }, "^italicTitle\\.[^.]+$": { "$ref": "#/$defs/italicTitleProp" }, "^strikethroughTitle\\.[^.]+$": { "$ref": "#/$defs/strikethroughTitleProp" }, "^quoteTitle\\.[^.]+$": { "$ref": "#/$defs/quoteTitleProp" }, "^linkTitle\\.[^.]+$": { "$ref": "#/$defs/linkTitleProp" }, "^orderedListTitle\\.[^.]+$": { "$ref": "#/$defs/orderedListTitleProp" }, "^unorderedListTitle\\.[^.]+$": { "$ref": "#/$defs/unorderedListTitleProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
308
+ const patternProperties$k = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
309
+ const required$q = ["kind", "type", "path"];
310
+ const unevaluatedProperties$r = false;
311
+ const markdownSchemaJson = {
312
+ $schema: $schema$r,
313
+ $id: $id$r,
314
+ title: title$r,
315
+ type: type$r,
316
+ $defs: $defs$r,
317
+ allOf: allOf$r,
318
+ properties: properties$q,
319
+ patternProperties: patternProperties$k,
320
+ required: required$q,
321
+ unevaluatedProperties: unevaluatedProperties$r
322
+ };
323
+ const $schema$q = "https://json-schema.org/draft/2020-12/schema";
324
+ const $id$q = "https://golemui.com/schemas/gui/components/number.schema.json";
325
+ const title$q = "Number Widget";
326
+ const type$q = "object";
327
+ const $defs$q = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "stepProp": { "type": "number" }, "minimumProp": { "type": "number" }, "maximumProp": { "type": "number" }, "autoGrowProp": { "type": "boolean" }, "autocompleteProp": { "type": "string" } };
328
+ const allOf$q = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
329
+ const properties$p = { "kind": { "const": "input" }, "type": { "const": "number" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "number" }, "props": { "type": "object", "properties": { "placeholder": { "$ref": "#/$defs/placeholderProp" }, "hint": { "$ref": "#/$defs/hintProp" }, "step": { "$ref": "#/$defs/stepProp" }, "minimum": { "$ref": "#/$defs/minimumProp" }, "maximum": { "$ref": "#/$defs/maximumProp" }, "autoGrow": { "$ref": "#/$defs/autoGrowProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^step\\.[^.]+$": { "$ref": "#/$defs/stepProp" }, "^minimum\\.[^.]+$": { "$ref": "#/$defs/minimumProp" }, "^maximum\\.[^.]+$": { "$ref": "#/$defs/maximumProp" }, "^autoGrow\\.[^.]+$": { "$ref": "#/$defs/autoGrowProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
330
+ const patternProperties$j = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
331
+ const required$p = ["kind", "type", "path"];
332
+ const unevaluatedProperties$q = false;
333
+ const numberSchemaJson = {
334
+ $schema: $schema$q,
335
+ $id: $id$q,
336
+ title: title$q,
337
+ type: type$q,
338
+ $defs: $defs$q,
339
+ allOf: allOf$q,
340
+ properties: properties$p,
341
+ patternProperties: patternProperties$j,
342
+ required: required$p,
343
+ unevaluatedProperties: unevaluatedProperties$q
344
+ };
345
+ const $schema$p = "https://json-schema.org/draft/2020-12/schema";
346
+ const $id$p = "https://golemui.com/schemas/gui/components/password.schema.json";
347
+ const title$p = "Password Widget";
348
+ const type$p = "object";
349
+ const $defs$p = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "showPasswordIconProp": { "type": "string" }, "hidePasswordIconProp": { "type": "string" }, "showPasswordLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hidePasswordLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "autocompleteProp": { "type": "string" } };
350
+ const allOf$p = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
351
+ const properties$o = { "kind": { "const": "input" }, "type": { "const": "password" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "placeholder": { "$ref": "#/$defs/placeholderProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "showPasswordIcon": { "$ref": "#/$defs/showPasswordIconProp" }, "hidePasswordIcon": { "$ref": "#/$defs/hidePasswordIconProp" }, "showPasswordLabel": { "$ref": "#/$defs/showPasswordLabelProp" }, "hidePasswordLabel": { "$ref": "#/$defs/hidePasswordLabelProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^showPasswordIcon\\.[^.]+$": { "$ref": "#/$defs/showPasswordIconProp" }, "^hidePasswordIcon\\.[^.]+$": { "$ref": "#/$defs/hidePasswordIconProp" }, "^showPasswordLabel\\.[^.]+$": { "$ref": "#/$defs/showPasswordLabelProp" }, "^hidePasswordLabel\\.[^.]+$": { "$ref": "#/$defs/hidePasswordLabelProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
352
+ const patternProperties$i = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
353
+ const required$o = ["kind", "type", "path"];
354
+ const unevaluatedProperties$p = false;
355
+ const passwordSchemaJson = {
356
+ $schema: $schema$p,
357
+ $id: $id$p,
358
+ title: title$p,
359
+ type: type$p,
360
+ $defs: $defs$p,
361
+ allOf: allOf$p,
362
+ properties: properties$o,
363
+ patternProperties: patternProperties$i,
364
+ required: required$o,
365
+ unevaluatedProperties: unevaluatedProperties$p
366
+ };
367
+ const $schema$o = "https://json-schema.org/draft/2020-12/schema";
368
+ const $id$o = "https://golemui.com/schemas/gui/components/radiogroup.schema.json";
369
+ const title$o = "RadioGroup Widget";
370
+ const type$o = "object";
371
+ const $defs$o = { "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "optionsProp": { "type": "array", "description": "Options may be primitive values (string/number), structured `{ label, value }` records, or arbitrary objects (paired with `labelField`/`valueField` for custom rendering).", "items": { "type": ["string", "number", "object"] } }, "labelFieldProp": { "type": "string", "description": 'Object property used as the display label when options are objects (e.g. `"name"` reads `item.name`)' }, "valueFieldProp": { "type": "string", "description": 'Object property used as the stored value when options are objects (e.g. `"id"` stores `item.id`)' }, "directionProp": { "description": "Layout direction for the radio buttons (`row` = horizontal, `column` = vertical). Defaults to `column`.", "enum": ["row", "column"], "default": "column" } };
372
+ const allOf$o = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
373
+ const properties$n = { "kind": { "const": "input" }, "type": { "const": "radiogroup" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": ["string", "number"] }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "options": { "$ref": "#/$defs/optionsProp" }, "labelField": { "$ref": "#/$defs/labelFieldProp" }, "valueField": { "$ref": "#/$defs/valueFieldProp" }, "direction": { "$ref": "#/$defs/directionProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^options\\.[^.]+$": { "$ref": "#/$defs/optionsProp" }, "^labelField\\.[^.]+$": { "$ref": "#/$defs/labelFieldProp" }, "^valueField\\.[^.]+$": { "$ref": "#/$defs/valueFieldProp" }, "^direction\\.[^.]+$": { "$ref": "#/$defs/directionProp" } }, "additionalProperties": false } };
374
+ const patternProperties$h = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
375
+ const required$n = ["kind", "type", "path"];
376
+ const unevaluatedProperties$o = false;
377
+ const radiogroupSchemaJson = {
378
+ $schema: $schema$o,
379
+ $id: $id$o,
380
+ title: title$o,
381
+ type: type$o,
382
+ $defs: $defs$o,
383
+ allOf: allOf$o,
384
+ properties: properties$n,
385
+ patternProperties: patternProperties$h,
386
+ required: required$n,
387
+ unevaluatedProperties: unevaluatedProperties$o
388
+ };
389
+ const $schema$n = "https://json-schema.org/draft/2020-12/schema";
390
+ const $id$n = "https://golemui.com/schemas/gui/components/rangecalendar.schema.json";
391
+ const title$n = "RangeCalendar Widget";
392
+ const type$n = "object";
393
+ const $defs$n = { "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "description": "Accessible label for the button that clears the selected range pill", "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "description": "Formatting of day numbers in the calendar grid (`numeric` = 1-31, `2-digit` = 01-31)", "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "description": "Formatting of weekday column headers (`short` = Mon, `long` = Monday, `narrow` = M)", "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "description": "Formatting of the month heading (`long` = January, `short` = Jan, `narrow` = J, `numeric` = 1, `2-digit` = 01)", "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "minDateProp": { "type": "string", "description": "ISO-8601 date string for the earliest selectable date (inclusive)" }, "maxDateProp": { "type": "string", "description": "ISO-8601 date string for the latest selectable date (inclusive)" }, "numberOfMonthsProp": { "type": "number", "description": "Number of month panels to display side by side. Defaults to 1." }, "disabledRangesProp": { "type": "array", "description": "Date ranges that are shown but cannot be selected", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } } };
394
+ const allOf$n = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
395
+ const properties$m = { "kind": { "const": "input" }, "type": { "const": "rangeCalendar" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" }, "disabledDateRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" }, "^disabledDateRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" } }, "additionalProperties": false } };
396
+ const patternProperties$g = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
397
+ const required$m = ["kind", "type", "path"];
398
+ const unevaluatedProperties$n = false;
399
+ const rangecalendarSchemaJson = {
400
+ $schema: $schema$n,
401
+ $id: $id$n,
402
+ title: title$n,
403
+ type: type$n,
404
+ $defs: $defs$n,
405
+ allOf: allOf$n,
406
+ properties: properties$m,
407
+ patternProperties: patternProperties$g,
408
+ required: required$m,
409
+ unevaluatedProperties: unevaluatedProperties$n
410
+ };
411
+ const $schema$m = "https://json-schema.org/draft/2020-12/schema";
412
+ const $id$m = "https://golemui.com/schemas/gui/components/rangedateinput.schema.json";
413
+ const title$m = "RangeDateInput Widget";
414
+ const type$m = "object";
415
+ const $defs$m = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "separatorProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "startDateAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endDateAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
416
+ const allOf$m = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
417
+ const properties$l = { "kind": { "const": "input" }, "type": { "const": "rangeDateInput" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } }, "props": { "type": "object", "properties": { "invalidDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "separator": { "$ref": "#/$defs/separatorProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "startDateAriaLabel": { "$ref": "#/$defs/startDateAriaLabelProp" }, "endDateAriaLabel": { "$ref": "#/$defs/endDateAriaLabelProp" }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" } }, "patternProperties": { "^invalidDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^separator\\.[^.]+$": { "$ref": "#/$defs/separatorProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^startDateAriaLabel\\.[^.]+$": { "$ref": "#/$defs/startDateAriaLabelProp" }, "^endDateAriaLabel\\.[^.]+$": { "$ref": "#/$defs/endDateAriaLabelProp" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" } }, "additionalProperties": false } };
418
+ const patternProperties$f = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
419
+ const required$l = ["kind", "type", "path"];
420
+ const unevaluatedProperties$m = false;
421
+ const rangedateinputSchemaJson = {
422
+ $schema: $schema$m,
423
+ $id: $id$m,
424
+ title: title$m,
425
+ type: type$m,
426
+ $defs: $defs$m,
427
+ allOf: allOf$m,
428
+ properties: properties$l,
429
+ patternProperties: patternProperties$f,
430
+ required: required$l,
431
+ unevaluatedProperties: unevaluatedProperties$m
432
+ };
433
+ const $schema$l = "https://json-schema.org/draft/2020-12/schema";
434
+ const $id$l = "https://golemui.com/schemas/gui/components/rangedatepicker.schema.json";
435
+ const title$l = "RangeDatePicker Widget";
436
+ const type$l = "object";
437
+ const $defs$l = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "separatorProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "startDateAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endDateAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "toggleAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "minDateProp": { "type": "string" }, "maxDateProp": { "type": "string" }, "numberOfMonthsProp": { "type": "number" }, "disabledRangesProp": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } } };
438
+ const allOf$l = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
439
+ const properties$k = { "kind": { "const": "input" }, "type": { "const": "rangeDatePicker" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateRange" } }, "props": { "type": "object", "properties": { "invalidDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDateRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "separator": { "$ref": "#/$defs/separatorProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "startDateAriaLabel": { "$ref": "#/$defs/startDateAriaLabelProp" }, "endDateAriaLabel": { "$ref": "#/$defs/endDateAriaLabelProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "toggleAriaLabel": { "$ref": "#/$defs/toggleAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "minDate": { "$ref": "#/$defs/minDateProp" }, "maxDate": { "$ref": "#/$defs/maxDateProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" } }, "patternProperties": { "^invalidDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledDateRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^separator\\.[^.]+$": { "$ref": "#/$defs/separatorProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^startDateAriaLabel\\.[^.]+$": { "$ref": "#/$defs/startDateAriaLabelProp" }, "^endDateAriaLabel\\.[^.]+$": { "$ref": "#/$defs/endDateAriaLabelProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^toggleAriaLabel\\.[^.]+$": { "$ref": "#/$defs/toggleAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^minDate\\.[^.]+$": { "$ref": "#/$defs/minDateProp" }, "^maxDate\\.[^.]+$": { "$ref": "#/$defs/maxDateProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" } }, "additionalProperties": false } };
440
+ const patternProperties$e = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
441
+ const required$k = ["kind", "type", "path"];
442
+ const unevaluatedProperties$l = false;
443
+ const rangedatepickerSchemaJson = {
444
+ $schema: $schema$l,
445
+ $id: $id$l,
446
+ title: title$l,
447
+ type: type$l,
448
+ $defs: $defs$l,
449
+ allOf: allOf$l,
450
+ properties: properties$k,
451
+ patternProperties: patternProperties$e,
452
+ required: required$k,
453
+ unevaluatedProperties: unevaluatedProperties$l
454
+ };
455
+ const $schema$k = "https://json-schema.org/draft/2020-12/schema";
456
+ const $id$k = "https://golemui.com/schemas/gui/components/rangedatetimeinput.schema.json";
457
+ const title$k = "RangeDateTimeInput Widget";
458
+ const type$k = "object";
459
+ const $defs$k = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "separatorProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "startDateTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endDateTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "minDateTimeProp": { "type": "string", "description": "ISO-8601 date-time string for the earliest selectable date-time (inclusive). Each endpoint of the value is an instant, so the bound is an instant too." }, "maxDateTimeProp": { "type": "string", "description": "ISO-8601 date-time string for the latest selectable date-time (inclusive)" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
460
+ const allOf$k = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
461
+ const properties$j = { "kind": { "const": "input" }, "type": { "const": "rangeDateTimeInput" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateTimeRange" } }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "separator": { "$ref": "#/$defs/separatorProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "startDateTimeAriaLabel": { "$ref": "#/$defs/startDateTimeAriaLabelProp" }, "endDateTimeAriaLabel": { "$ref": "#/$defs/endDateTimeAriaLabelProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "invalidDateMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minDateTime": { "$ref": "#/$defs/minDateTimeProp" }, "maxDateTime": { "$ref": "#/$defs/maxDateTimeProp" }, "minDateTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^separator\\.[^.]+$": { "$ref": "#/$defs/separatorProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^startDateTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/startDateTimeAriaLabelProp" }, "^endDateTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/endDateTimeAriaLabelProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^invalidDateMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDateTime\\.[^.]+$": { "$ref": "#/$defs/minDateTimeProp" }, "^maxDateTime\\.[^.]+$": { "$ref": "#/$defs/maxDateTimeProp" }, "^minDateTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "additionalProperties": false } };
462
+ const patternProperties$d = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
463
+ const required$j = ["kind", "type", "path"];
464
+ const unevaluatedProperties$k = false;
465
+ const rangedatetimeinputSchemaJson = {
466
+ $schema: $schema$k,
467
+ $id: $id$k,
468
+ title: title$k,
469
+ type: type$k,
470
+ $defs: $defs$k,
471
+ allOf: allOf$k,
472
+ properties: properties$j,
473
+ patternProperties: patternProperties$d,
474
+ required: required$j,
475
+ unevaluatedProperties: unevaluatedProperties$k
476
+ };
477
+ const $schema$j = "https://json-schema.org/draft/2020-12/schema";
478
+ const $id$j = "https://golemui.com/schemas/gui/components/rangedatetimecalendar.schema.json";
479
+ const title$j = "RangeDateTimeCalendar Widget";
480
+ const type$j = "object";
481
+ const $defs$j = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "description": "Formatting of day numbers in the calendar grid (`numeric` = 1-31, `2-digit` = 01-31)", "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "description": "Formatting of weekday column headers (`short` = Mon, `long` = Monday, `narrow` = M)", "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "description": "Formatting of the month heading (`long` = January, `short` = Jan, `narrow` = J, `numeric` = 1, `2-digit` = 01)", "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "numberOfMonthsProp": { "type": "number", "description": "Number of month panels to display side by side. Defaults to 1. The time row renders on the first panel only." }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "allowCustomTimeProp": { "type": "boolean" }, "minDateTimeProp": { "type": "string", "description": "ISO-8601 date-time string for the earliest selectable instant (inclusive). Endpoints are instants, so the bound is an instant too." }, "maxDateTimeProp": { "type": "string", "description": "ISO-8601 date-time string for the latest selectable instant (inclusive)" }, "disabledRangesProp": { "type": "array", "description": "Disabled instant spans (in this widget's DateTimeRange coordinate system). Blocking a whole day is a span of 00:00:00-23:59:59.", "items": { "$ref": "../ranges.schema.json#/$defs/dateTimeRange" } } };
482
+ const allOf$j = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
483
+ const properties$i = { "kind": { "const": "input" }, "type": { "const": "rangeDateTimeCalendar" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateTimeRange" } }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "allowCustomTime": { "$ref": "#/$defs/allowCustomTimeProp" }, "startTimeLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endTimeLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minDateTime": { "$ref": "#/$defs/minDateTimeProp" }, "maxDateTime": { "$ref": "#/$defs/maxDateTimeProp" }, "minDateTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" }, "disabledRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "noAvailableTimesMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a half-finished range selection behind; the committed pills are untouched, the injected issue alone flags the field." }, "dayCountAriaLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDayCountAriaLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^allowCustomTime\\.[^.]+$": { "$ref": "#/$defs/allowCustomTimeProp" }, "^startTimeLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^endTimeLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDateTime\\.[^.]+$": { "$ref": "#/$defs/minDateTimeProp" }, "^maxDateTime\\.[^.]+$": { "$ref": "#/$defs/maxDateTimeProp" }, "^minDateTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" }, "^disabledRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^noAvailableTimesMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^dayCountAriaLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledDayCountAriaLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" } }, "additionalProperties": false } };
484
+ const patternProperties$c = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
485
+ const required$i = ["kind", "type", "path"];
486
+ const unevaluatedProperties$j = false;
487
+ const rangedatetimecalendarSchemaJson = {
488
+ $schema: $schema$j,
489
+ $id: $id$j,
490
+ title: title$j,
491
+ type: type$j,
492
+ $defs: $defs$j,
493
+ allOf: allOf$j,
494
+ properties: properties$i,
495
+ patternProperties: patternProperties$c,
496
+ required: required$i,
497
+ unevaluatedProperties: unevaluatedProperties$j
498
+ };
499
+ const $schema$i = "https://json-schema.org/draft/2020-12/schema";
500
+ const $id$i = "https://golemui.com/schemas/gui/components/rangedatetimepicker.schema.json";
501
+ const title$i = "RangeDateTimePicker Widget";
502
+ const type$i = "object";
503
+ const $defs$i = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "separatorProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "startDateTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endDateTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "invalidDateMessageProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "prevMonthIconProp": { "type": "string" }, "nextMonthIconProp": { "type": "string" }, "prevMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "nextMonthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "toggleAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "selectYearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearGridAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "monthAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "yearAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayFormatProp": { "description": "Formatting of day numbers in the calendar grid (`numeric` = 1-31, `2-digit` = 01-31)", "enum": ["numeric", "2-digit"] }, "weekdayFormatProp": { "description": "Formatting of weekday column headers (`short` = Mon, `long` = Monday, `narrow` = M)", "enum": ["short", "long", "narrow"] }, "monthFormatProp": { "description": "Formatting of the month heading (`long` = January, `short` = Jan, `narrow` = J, `numeric` = 1, `2-digit` = 01)", "enum": ["numeric", "2-digit", "long", "short", "narrow"] }, "numberOfMonthsProp": { "type": "number", "description": "Number of month panels to display side by side. Defaults to 1. The time row renders on the first panel only." }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "allowCustomTimeProp": { "type": "boolean" }, "minDateTimeProp": { "type": "string", "description": "ISO-8601 date-time string for the earliest selectable instant (inclusive). Endpoints are instants, so the bound is an instant too." }, "maxDateTimeProp": { "type": "string", "description": "ISO-8601 date-time string for the latest selectable instant (inclusive)" }, "disabledRangesProp": { "type": "array", "description": "Disabled instant spans (in this widget's DateTimeRange coordinate system). Blocking a whole day is a span of 00:00:00-23:59:59.", "items": { "$ref": "../ranges.schema.json#/$defs/dateTimeRange" } } };
504
+ const allOf$i = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
505
+ const properties$h = { "kind": { "const": "input" }, "type": { "const": "rangeDateTimePicker" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/dateTimeRange" } }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "separator": { "$ref": "#/$defs/separatorProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "startDateTimeAriaLabel": { "$ref": "#/$defs/startDateTimeAriaLabelProp" }, "endDateTimeAriaLabel": { "$ref": "#/$defs/endDateTimeAriaLabelProp" }, "invalidDateMessage": { "$ref": "#/$defs/invalidDateMessageProp" }, "prevMonthIcon": { "$ref": "#/$defs/prevMonthIconProp" }, "nextMonthIcon": { "$ref": "#/$defs/nextMonthIconProp" }, "prevMonthAriaLabel": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "nextMonthAriaLabel": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "toggleAriaLabel": { "$ref": "#/$defs/toggleAriaLabelProp" }, "selectYearAriaLabel": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "yearGridAriaLabel": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "dayAriaLabel": { "$ref": "#/$defs/dayAriaLabelProp" }, "monthAriaLabel": { "$ref": "#/$defs/monthAriaLabelProp" }, "yearAriaLabel": { "$ref": "#/$defs/yearAriaLabelProp" }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" }, "dayFormat": { "$ref": "#/$defs/dayFormatProp" }, "weekdayFormat": { "$ref": "#/$defs/weekdayFormatProp" }, "monthFormat": { "$ref": "#/$defs/monthFormatProp" }, "numberOfMonths": { "$ref": "#/$defs/numberOfMonthsProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "allowCustomTime": { "$ref": "#/$defs/allowCustomTimeProp" }, "startTimeLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endTimeLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minDateTime": { "$ref": "#/$defs/minDateTimeProp" }, "maxDateTime": { "$ref": "#/$defs/maxDateTimeProp" }, "minDateTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxDateTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" }, "disabledRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "noAvailableTimesMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "dayCountAriaLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDayCountAriaLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^separator\\.[^.]+$": { "$ref": "#/$defs/separatorProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^startDateTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/startDateTimeAriaLabelProp" }, "^endDateTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/endDateTimeAriaLabelProp" }, "^invalidDateMessage\\.[^.]+$": { "$ref": "#/$defs/invalidDateMessageProp" }, "^prevMonthIcon\\.[^.]+$": { "$ref": "#/$defs/prevMonthIconProp" }, "^nextMonthIcon\\.[^.]+$": { "$ref": "#/$defs/nextMonthIconProp" }, "^prevMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/prevMonthAriaLabelProp" }, "^nextMonthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/nextMonthAriaLabelProp" }, "^toggleAriaLabel\\.[^.]+$": { "$ref": "#/$defs/toggleAriaLabelProp" }, "^selectYearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/selectYearAriaLabelProp" }, "^yearGridAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearGridAriaLabelProp" }, "^dayAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayAriaLabelProp" }, "^monthAriaLabel\\.[^.]+$": { "$ref": "#/$defs/monthAriaLabelProp" }, "^yearAriaLabel\\.[^.]+$": { "$ref": "#/$defs/yearAriaLabelProp" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" }, "^dayFormat\\.[^.]+$": { "$ref": "#/$defs/dayFormatProp" }, "^weekdayFormat\\.[^.]+$": { "$ref": "#/$defs/weekdayFormatProp" }, "^monthFormat\\.[^.]+$": { "$ref": "#/$defs/monthFormatProp" }, "^numberOfMonths\\.[^.]+$": { "$ref": "#/$defs/numberOfMonthsProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^allowCustomTime\\.[^.]+$": { "$ref": "#/$defs/allowCustomTimeProp" }, "^startTimeLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^endTimeLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^minDateTime\\.[^.]+$": { "$ref": "#/$defs/minDateTimeProp" }, "^maxDateTime\\.[^.]+$": { "$ref": "#/$defs/maxDateTimeProp" }, "^minDateTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxDateTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" }, "^disabledRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^noAvailableTimesMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^dayCountAriaLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledDayCountAriaLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" } }, "additionalProperties": false } };
506
+ const patternProperties$b = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
507
+ const required$h = ["kind", "type", "path"];
508
+ const unevaluatedProperties$i = false;
509
+ const rangedatetimepickerSchemaJson = {
510
+ $schema: $schema$i,
511
+ $id: $id$i,
512
+ title: title$i,
513
+ type: type$i,
514
+ $defs: $defs$i,
515
+ allOf: allOf$i,
516
+ properties: properties$h,
517
+ patternProperties: patternProperties$b,
518
+ required: required$h,
519
+ unevaluatedProperties: unevaluatedProperties$i
520
+ };
521
+ const $schema$h = "https://json-schema.org/draft/2020-12/schema";
522
+ const $id$h = "https://golemui.com/schemas/gui/components/rangetimeinput.schema.json";
523
+ const title$h = "RangeTimeInput Widget";
524
+ const type$h = "object";
525
+ const $defs$h = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "separatorProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "startTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "isoTimeProp": { "$ref": "../ranges.schema.json#/$defs/isoTime" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
526
+ const allOf$h = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
527
+ const properties$g = { "kind": { "const": "input" }, "type": { "const": "rangeTimeInput" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/timeRange" } }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "separator": { "$ref": "#/$defs/separatorProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "startTimeAriaLabel": { "$ref": "#/$defs/startTimeAriaLabelProp" }, "endTimeAriaLabel": { "$ref": "#/$defs/endTimeAriaLabelProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "minTime": { "$ref": "#/$defs/isoTimeProp" }, "maxTime": { "$ref": "#/$defs/isoTimeProp" }, "minTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "rangeOrderMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^separator\\.[^.]+$": { "$ref": "#/$defs/separatorProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^startTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/startTimeAriaLabelProp" }, "^endTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/endTimeAriaLabelProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^minTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^maxTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^minTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^rangeOrderMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "additionalProperties": false } };
528
+ const patternProperties$a = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
529
+ const required$g = ["kind", "type", "path"];
530
+ const unevaluatedProperties$h = false;
531
+ const rangetimeinputSchemaJson = {
532
+ $schema: $schema$h,
533
+ $id: $id$h,
534
+ title: title$h,
535
+ type: type$h,
536
+ $defs: $defs$h,
537
+ allOf: allOf$h,
538
+ properties: properties$g,
539
+ patternProperties: patternProperties$a,
540
+ required: required$g,
541
+ unevaluatedProperties: unevaluatedProperties$h
542
+ };
543
+ const $schema$g = "https://json-schema.org/draft/2020-12/schema";
544
+ const $id$g = "https://golemui.com/schemas/gui/components/rangetimepicker.schema.json";
545
+ const title$g = "RangeTimePicker Widget";
546
+ const type$g = "object";
547
+ const $defs$g = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "separatorProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removePillAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "startTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endTimeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "isoTimeProp": { "$ref": "../ranges.schema.json#/$defs/isoTime" }, "disabledRangesProp": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/timeRange" } }, "allowCustomTimeProp": { "type": "boolean" }, "sizeProp": { "type": "number" }, "toggleAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
548
+ const allOf$g = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
549
+ const properties$f = { "kind": { "const": "input" }, "type": { "const": "rangeTimePicker" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/timeRange" } }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "separator": { "$ref": "#/$defs/separatorProp" }, "removePillAriaLabel": { "$ref": "#/$defs/removePillAriaLabelProp" }, "startTimeAriaLabel": { "$ref": "#/$defs/startTimeAriaLabelProp" }, "endTimeAriaLabel": { "$ref": "#/$defs/endTimeAriaLabelProp" }, "startTimeLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "endTimeLabel": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "minTime": { "$ref": "#/$defs/isoTimeProp" }, "maxTime": { "$ref": "#/$defs/isoTimeProp" }, "minTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "rangeOrderMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" }, "allowCustomTime": { "$ref": "#/$defs/allowCustomTimeProp" }, "height": { "$ref": "#/$defs/sizeProp" }, "itemHeight": { "$ref": "#/$defs/sizeProp" }, "disabledRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "noAvailableTimesMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "toggleAriaLabel": { "$ref": "#/$defs/toggleAriaLabelProp" }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^separator\\.[^.]+$": { "$ref": "#/$defs/separatorProp" }, "^removePillAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removePillAriaLabelProp" }, "^startTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/startTimeAriaLabelProp" }, "^endTimeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/endTimeAriaLabelProp" }, "^startTimeLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^endTimeLabel\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^minTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^maxTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^minTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^rangeOrderMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" }, "^allowCustomTime\\.[^.]+$": { "$ref": "#/$defs/allowCustomTimeProp" }, "^height\\.[^.]+$": { "$ref": "#/$defs/sizeProp" }, "^itemHeight\\.[^.]+$": { "$ref": "#/$defs/sizeProp" }, "^disabledRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^noAvailableTimesMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^toggleAriaLabel\\.[^.]+$": { "$ref": "#/$defs/toggleAriaLabelProp" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "additionalProperties": false } };
550
+ const patternProperties$9 = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
551
+ const required$f = ["kind", "type", "path"];
552
+ const unevaluatedProperties$g = false;
553
+ const rangetimepickerSchemaJson = {
554
+ $schema: $schema$g,
555
+ $id: $id$g,
556
+ title: title$g,
557
+ type: type$g,
558
+ $defs: $defs$g,
559
+ allOf: allOf$g,
560
+ properties: properties$f,
561
+ patternProperties: patternProperties$9,
562
+ required: required$f,
563
+ unevaluatedProperties: unevaluatedProperties$g
564
+ };
565
+ const $schema$f = "https://json-schema.org/draft/2020-12/schema";
566
+ const $id$f = "https://golemui.com/schemas/gui/components/repeater.schema.json";
567
+ const title$f = "Repeater Widget";
568
+ const type$f = "object";
569
+ const $defs$f = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "addLabelProp": { "description": "Label for the button that adds a new repeated item", "$ref": "../core/common.schema.json#/$defs/localizable" }, "removeLabelProp": { "description": "Label for the button that removes an existing repeated item", "$ref": "../core/common.schema.json#/$defs/localizable" }, "limitProp": { "type": "number", "description": "Maximum number of items the user can add. No limit when omitted." }, "templateProp": { "description": "Widget tree used as the template for each repeated item. Paths inside are resolved relative to the item's index in the array. Widgets inside the template can reference the current item in reactive expressions ('when' conditions, '{{}}' interpolation slots, and i18n params) through the scope variables '$item' (the item object, e.g. '$item.quantity') and '$index' (the item's zero-based position). For nested repeaters these bind to the innermost enclosing item.", "$ref": "../layout-widget.schema.json" }, "titleProp": { "description": "Title displayed in the header of each item panel.", "$ref": "../core/common.schema.json#/$defs/localizable" }, "addButtonIconProp": { "type": "string", "description": "Icon name or CSS class for the add-item button icon" }, "removeButtonIconProp": { "type": "string", "description": "Icon name or CSS class for the remove-item button icon" } };
570
+ const allOf$f = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
571
+ const properties$e = { "kind": { "const": "input" }, "type": { "const": "repeater" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "type": "object" } }, "props": { "type": "object", "properties": { "addLabel": { "$ref": "#/$defs/addLabelProp" }, "removeLabel": { "$ref": "#/$defs/removeLabelProp" }, "limit": { "$ref": "#/$defs/limitProp" }, "template": { "$ref": "#/$defs/templateProp" }, "title": { "$ref": "#/$defs/titleProp" }, "addButtonIcon": { "$ref": "#/$defs/addButtonIconProp" }, "removeButtonIcon": { "$ref": "#/$defs/removeButtonIconProp" } }, "required": ["template"], "patternProperties": { "^addLabel\\.[^.]+$": { "$ref": "#/$defs/addLabelProp" }, "^removeLabel\\.[^.]+$": { "$ref": "#/$defs/removeLabelProp" }, "^limit\\.[^.]+$": { "$ref": "#/$defs/limitProp" }, "^template\\.[^.]+$": { "$ref": "#/$defs/templateProp" }, "^title\\.[^.]+$": { "$ref": "#/$defs/titleProp" }, "^addButtonIcon\\.[^.]+$": { "$ref": "#/$defs/addButtonIconProp" }, "^removeButtonIcon\\.[^.]+$": { "$ref": "#/$defs/removeButtonIconProp" } }, "additionalProperties": false } };
572
+ const patternProperties$8 = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
573
+ const required$e = ["kind", "type", "path", "props"];
574
+ const unevaluatedProperties$f = false;
575
+ const repeaterSchemaJson = {
576
+ $schema: $schema$f,
577
+ $id: $id$f,
578
+ title: title$f,
579
+ type: type$f,
580
+ $defs: $defs$f,
581
+ allOf: allOf$f,
582
+ properties: properties$e,
583
+ patternProperties: patternProperties$8,
584
+ required: required$e,
585
+ unevaluatedProperties: unevaluatedProperties$f
586
+ };
587
+ const $schema$e = "https://json-schema.org/draft/2020-12/schema";
588
+ const $id$e = "https://golemui.com/schemas/gui/components/select.schema.json";
589
+ const title$e = "Select Widget";
590
+ const type$e = "object";
591
+ const $defs$e = { "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "optionsProp": { "type": "array", "description": "Options may be primitive values (string/number), structured `{ label, value }` records, or arbitrary objects (paired with `labelField`/`valueField` for custom rendering).", "items": { "type": ["string", "number", "object"] } }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "labelFieldProp": { "type": "string", "description": 'Object property used as the display label when options are objects (e.g. `"name"` reads `item.name`)' }, "valueFieldProp": { "type": "string", "description": 'Object property used as the stored value when options are objects (e.g. `"id"` stores `item.id`)' }, "autocompleteProp": { "type": "string", "description": "HTML `autocomplete` attribute applied to the underlying input element" } };
592
+ const allOf$e = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
593
+ const properties$d = { "kind": { "const": "input" }, "type": { "const": "select" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": ["string", "number"] }, "props": { "type": "object", "properties": { "invalidOptionMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "options": { "$ref": "#/$defs/optionsProp" }, "placeholder": { "$ref": "#/$defs/placeholderProp" }, "labelField": { "$ref": "#/$defs/labelFieldProp" }, "valueField": { "$ref": "#/$defs/valueFieldProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^invalidOptionMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^options\\.[^.]+$": { "$ref": "#/$defs/optionsProp" }, "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^labelField\\.[^.]+$": { "$ref": "#/$defs/labelFieldProp" }, "^valueField\\.[^.]+$": { "$ref": "#/$defs/valueFieldProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
594
+ const patternProperties$7 = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
595
+ const required$d = ["kind", "type", "path"];
596
+ const unevaluatedProperties$e = false;
597
+ const selectSchemaJson = {
598
+ $schema: $schema$e,
599
+ $id: $id$e,
600
+ title: title$e,
601
+ type: type$e,
602
+ $defs: $defs$e,
603
+ allOf: allOf$e,
604
+ properties: properties$d,
605
+ patternProperties: patternProperties$7,
606
+ required: required$d,
607
+ unevaluatedProperties: unevaluatedProperties$e
608
+ };
609
+ const $schema$d = "https://json-schema.org/draft/2020-12/schema";
610
+ const $id$d = "https://golemui.com/schemas/gui/components/tags.schema.json";
611
+ const title$d = "Tags Widget";
612
+ const type$d = "object";
613
+ const $defs$d = { "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "separatorsProp": { "type": "array", "description": 'Characters or strings that trigger a new tag when typed (e.g. `[",", " "]`). Defaults to Enter key only.', "items": { "type": "string" } }, "allowDuplicatesProp": { "type": "boolean", "description": "When true, the same tag value may be added more than once. Defaults to false." }, "trimProp": { "type": "boolean", "description": "When true, whitespace is trimmed from each tag before it is added. Defaults to true." }, "limitProp": { "type": "number", "description": "Maximum number of tags the user can add. No limit when omitted." }, "removeAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "removeIconProp": { "type": "string" } };
614
+ const allOf$d = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
615
+ const properties$c = { "kind": { "const": "input" }, "type": { "const": "tags" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "array", "items": { "type": "string" } }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "placeholder": { "$ref": "#/$defs/placeholderProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "separators": { "$ref": "#/$defs/separatorsProp" }, "allowDuplicates": { "$ref": "#/$defs/allowDuplicatesProp" }, "trim": { "$ref": "#/$defs/trimProp" }, "limit": { "$ref": "#/$defs/limitProp" }, "removeAriaLabel": { "$ref": "#/$defs/removeAriaLabelProp" }, "removeIcon": { "$ref": "#/$defs/removeIconProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^separators\\.[^.]+$": { "$ref": "#/$defs/separatorsProp" }, "^allowDuplicates\\.[^.]+$": { "$ref": "#/$defs/allowDuplicatesProp" }, "^trim\\.[^.]+$": { "$ref": "#/$defs/trimProp" }, "^limit\\.[^.]+$": { "$ref": "#/$defs/limitProp" }, "^removeAriaLabel\\.[^.]+$": { "$ref": "#/$defs/removeAriaLabelProp" }, "^removeIcon\\.[^.]+$": { "$ref": "#/$defs/removeIconProp" } }, "additionalProperties": false } };
616
+ const patternProperties$6 = { "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
617
+ const required$c = ["kind", "type", "path"];
618
+ const unevaluatedProperties$d = false;
619
+ const tagsSchemaJson = {
620
+ $schema: $schema$d,
621
+ $id: $id$d,
622
+ title: title$d,
623
+ type: type$d,
624
+ $defs: $defs$d,
625
+ allOf: allOf$d,
626
+ properties: properties$c,
627
+ patternProperties: patternProperties$6,
628
+ required: required$c,
629
+ unevaluatedProperties: unevaluatedProperties$d
630
+ };
631
+ const $schema$c = "https://json-schema.org/draft/2020-12/schema";
632
+ const $id$c = "https://golemui.com/schemas/gui/components/textarea.schema.json";
633
+ const title$c = "TextArea Widget";
634
+ const type$c = "object";
635
+ const $defs$c = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "counterModeProp": { "enum": ["remaining", "current"] }, "minimumHeightProp": { "type": "number" }, "autoGrowProp": { "type": "boolean" }, "maxLengthProp": { "type": "number" }, "autocompleteProp": { "type": "string" } };
636
+ const allOf$c = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
637
+ const properties$b = { "kind": { "const": "input" }, "type": { "const": "textarea" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "placeholder": { "$ref": "#/$defs/placeholderProp" }, "counterMode": { "$ref": "#/$defs/counterModeProp" }, "minimumHeight": { "$ref": "#/$defs/minimumHeightProp" }, "autoGrow": { "$ref": "#/$defs/autoGrowProp" }, "maxLength": { "$ref": "#/$defs/maxLengthProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^counterMode\\.[^.]+$": { "$ref": "#/$defs/counterModeProp" }, "^minimumHeight\\.[^.]+$": { "$ref": "#/$defs/minimumHeightProp" }, "^autoGrow\\.[^.]+$": { "$ref": "#/$defs/autoGrowProp" }, "^maxLength\\.[^.]+$": { "$ref": "#/$defs/maxLengthProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
638
+ const patternProperties$5 = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
639
+ const required$b = ["kind", "type", "path"];
640
+ const unevaluatedProperties$c = false;
641
+ const textareaSchemaJson = {
642
+ $schema: $schema$c,
643
+ $id: $id$c,
644
+ title: title$c,
645
+ type: type$c,
646
+ $defs: $defs$c,
647
+ allOf: allOf$c,
648
+ properties: properties$b,
649
+ patternProperties: patternProperties$5,
650
+ required: required$b,
651
+ unevaluatedProperties: unevaluatedProperties$c
652
+ };
653
+ const $schema$b = "https://json-schema.org/draft/2020-12/schema";
654
+ const $id$b = "https://golemui.com/schemas/gui/components/textinput.schema.json";
655
+ const title$b = "TextInput Widget";
656
+ const type$b = "object";
657
+ const $defs$b = { "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "placeholderProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "autocompleteProp": { "type": "string" } };
658
+ const allOf$b = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
659
+ const properties$a = { "kind": { "const": "input" }, "type": { "const": "textinput" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "placeholder": { "$ref": "#/$defs/placeholderProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "autocomplete": { "$ref": "#/$defs/autocompleteProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^placeholder\\.[^.]+$": { "$ref": "#/$defs/placeholderProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^autocomplete\\.[^.]+$": { "$ref": "#/$defs/autocompleteProp" } }, "additionalProperties": false } };
660
+ const patternProperties$4 = { "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
661
+ const required$a = ["kind", "type", "path"];
662
+ const unevaluatedProperties$b = false;
663
+ const textinputSchemaJson = {
664
+ $schema: $schema$b,
665
+ $id: $id$b,
666
+ title: title$b,
667
+ type: type$b,
668
+ $defs: $defs$b,
669
+ allOf: allOf$b,
670
+ properties: properties$a,
671
+ patternProperties: patternProperties$4,
672
+ required: required$a,
673
+ unevaluatedProperties: unevaluatedProperties$b
674
+ };
675
+ const $schema$a = "https://json-schema.org/draft/2020-12/schema";
676
+ const $id$a = "https://golemui.com/schemas/gui/components/timeinput.schema.json";
677
+ const title$a = "TimeInput Widget";
678
+ const type$a = "object";
679
+ const $defs$a = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "minTimeProp": { "type": "string" }, "maxTimeProp": { "type": "string" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
680
+ const allOf$a = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
681
+ const properties$9 = { "kind": { "const": "input" }, "type": { "const": "timeInput" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "minTime": { "$ref": "#/$defs/minTimeProp" }, "maxTime": { "$ref": "#/$defs/maxTimeProp" }, "minTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "patternProperties": { "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^minTime\\.[^.]+$": { "$ref": "#/$defs/minTimeProp" }, "^maxTime\\.[^.]+$": { "$ref": "#/$defs/maxTimeProp" }, "^minTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "additionalProperties": false } };
682
+ const patternProperties$3 = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
683
+ const required$9 = ["kind", "type", "path"];
684
+ const unevaluatedProperties$a = false;
685
+ const timeinputSchemaJson = {
686
+ $schema: $schema$a,
687
+ $id: $id$a,
688
+ title: title$a,
689
+ type: type$a,
690
+ $defs: $defs$a,
691
+ allOf: allOf$a,
692
+ properties: properties$9,
693
+ patternProperties: patternProperties$3,
694
+ required: required$9,
695
+ unevaluatedProperties: unevaluatedProperties$a
696
+ };
697
+ const $schema$9 = "https://json-schema.org/draft/2020-12/schema";
698
+ const $id$9 = "https://golemui.com/schemas/gui/components/timepicker.schema.json";
699
+ const title$9 = "TimePicker Widget";
700
+ const type$9 = "object";
701
+ const $defs$9 = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "iconProp": { "type": "string" }, "hourFormatProp": { "enum": ["12", "24"] }, "minuteStepProp": { "type": "number", "minimum": 1 }, "isoTimeProp": { "$ref": "../ranges.schema.json#/$defs/isoTime" }, "disabledRangesProp": { "type": "array", "items": { "$ref": "../ranges.schema.json#/$defs/timeRange" } }, "allowCustomTimeProp": { "type": "boolean" }, "sizeProp": { "type": "number" }, "toggleAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "hourAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "minuteAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "dayPeriodAriaLabelProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
702
+ const allOf$9 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
703
+ const properties$8 = { "kind": { "const": "input" }, "type": { "const": "timePicker" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "string" }, "props": { "type": "object", "properties": { "minTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "maxTimeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledRangeMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "noAvailableTimesMessage": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "incompleteMessage": { "$ref": "../core/common.schema.json#/$defs/localizable", "description": "Error surfaced when focus leaves the widget with a partially filled entry behind; the value goes to null so validators report it even on non-required fields." }, "hint": { "$ref": "#/$defs/hintProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "hourFormat": { "$ref": "#/$defs/hourFormatProp" }, "minuteStep": { "$ref": "#/$defs/minuteStepProp" }, "minTime": { "$ref": "#/$defs/isoTimeProp" }, "maxTime": { "$ref": "#/$defs/isoTimeProp" }, "disabledRanges": { "$ref": "#/$defs/disabledRangesProp" }, "allowCustomTime": { "$ref": "#/$defs/allowCustomTimeProp" }, "height": { "$ref": "#/$defs/sizeProp" }, "itemHeight": { "$ref": "#/$defs/sizeProp" }, "toggleAriaLabel": { "$ref": "#/$defs/toggleAriaLabelProp" }, "hourAriaLabel": { "$ref": "#/$defs/hourAriaLabelProp" }, "minuteAriaLabel": { "$ref": "#/$defs/minuteAriaLabelProp" }, "dayPeriodAriaLabel": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "patternProperties": { "^minTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^maxTimeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabledRangeMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^noAvailableTimesMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^incompleteMessage\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^hourFormat\\.[^.]+$": { "$ref": "#/$defs/hourFormatProp" }, "^minuteStep\\.[^.]+$": { "$ref": "#/$defs/minuteStepProp" }, "^minTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^maxTime\\.[^.]+$": { "$ref": "#/$defs/isoTimeProp" }, "^disabledRanges\\.[^.]+$": { "$ref": "#/$defs/disabledRangesProp" }, "^allowCustomTime\\.[^.]+$": { "$ref": "#/$defs/allowCustomTimeProp" }, "^height\\.[^.]+$": { "$ref": "#/$defs/sizeProp" }, "^itemHeight\\.[^.]+$": { "$ref": "#/$defs/sizeProp" }, "^toggleAriaLabel\\.[^.]+$": { "$ref": "#/$defs/toggleAriaLabelProp" }, "^hourAriaLabel\\.[^.]+$": { "$ref": "#/$defs/hourAriaLabelProp" }, "^minuteAriaLabel\\.[^.]+$": { "$ref": "#/$defs/minuteAriaLabelProp" }, "^dayPeriodAriaLabel\\.[^.]+$": { "$ref": "#/$defs/dayPeriodAriaLabelProp" } }, "additionalProperties": false } };
704
+ const patternProperties$2 = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
705
+ const required$8 = ["kind", "type", "path"];
706
+ const unevaluatedProperties$9 = false;
707
+ const timepickerSchemaJson = {
708
+ $schema: $schema$9,
709
+ $id: $id$9,
710
+ title: title$9,
711
+ type: type$9,
712
+ $defs: $defs$9,
713
+ allOf: allOf$9,
714
+ properties: properties$8,
715
+ patternProperties: patternProperties$2,
716
+ required: required$8,
717
+ unevaluatedProperties: unevaluatedProperties$9
718
+ };
719
+ const $schema$8 = "https://json-schema.org/draft/2020-12/schema";
720
+ const $id$8 = "https://golemui.com/schemas/gui/components/toggle.schema.json";
721
+ const title$8 = "Toggle Widget";
722
+ const type$8 = "object";
723
+ const $defs$8 = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonlyDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "togglePositionProp": { "enum": ["left", "right"], "default": "left" }, "hintProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
724
+ const allOf$8 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
725
+ const properties$7 = { "kind": { "const": "input" }, "type": { "const": "toggle" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "readonly": { "$ref": "#/$defs/readonlyDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": { "type": "boolean" }, "props": { "type": "object", "properties": { "togglePosition": { "$ref": "#/$defs/togglePositionProp" }, "hint": { "$ref": "#/$defs/hintProp" } }, "patternProperties": { "^togglePosition\\.[^.]+$": { "$ref": "#/$defs/togglePositionProp" }, "^hint\\.[^.]+$": { "$ref": "#/$defs/hintProp" } }, "additionalProperties": false } };
726
+ const patternProperties$1 = { "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" }, "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^readonly\\.[^.]+$": { "$ref": "#/$defs/readonlyDef" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } };
727
+ const required$7 = ["kind", "type", "path"];
728
+ const unevaluatedProperties$8 = false;
729
+ const toggleSchemaJson = {
730
+ $schema: $schema$8,
731
+ $id: $id$8,
732
+ title: title$8,
733
+ type: type$8,
734
+ $defs: $defs$8,
735
+ allOf: allOf$8,
736
+ properties: properties$7,
737
+ patternProperties: patternProperties$1,
738
+ required: required$7,
739
+ unevaluatedProperties: unevaluatedProperties$8
740
+ };
741
+ const $schema$7 = "https://json-schema.org/draft/2020-12/schema";
742
+ const $id$7 = "https://golemui.com/schemas/gui/components/accordion.schema.json";
743
+ const title$7 = "Accordion Widget";
744
+ const type$7 = "object";
745
+ const $defs$7 = { "singleOpenProp": { "type": "boolean", "description": "When true, opening one section automatically closes all others. Defaults to false." }, "defaultOpenProp": { "type": "object", "description": "Map of section UIDs to booleans indicating which sections are open on initial render", "additionalProperties": { "type": "boolean" }, "minProperties": 1 }, "renderModeProp": { "description": "Controls when section content is rendered: `all` keeps all sections in the DOM, `activeOnly` unmounts inactive ones", "enum": ["all", "activeOnly"] }, "sectionsProp": { "type": "array", "description": "Ordered list of section definitions. Each section's `uid` must match the widget UIDs used in `children`.", "minItems": 1, "items": { "type": "object", "properties": { "label": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "uid": { "type": "string", "description": "Unique identifier linking this section definition to its widgets in `children`" } }, "required": ["label", "uid"], "additionalProperties": false } } };
746
+ const allOf$7 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
747
+ const properties$6 = { "kind": { "const": "layout" }, "type": { "const": "accordion" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "children": { "type": "array", "description": "Flat list of widgets belonging to all sections. Each widget must have a `uid` matching one of the section UIDs in `props.sections`.", "minItems": 1, "items": { "$ref": "../widgets.schema.json#/$defs/formWidget" } }, "props": { "type": "object", "properties": { "singleOpen": { "$ref": "#/$defs/singleOpenProp" }, "defaultOpen": { "$ref": "#/$defs/defaultOpenProp" }, "renderMode": { "$ref": "#/$defs/renderModeProp" }, "sections": { "$ref": "#/$defs/sectionsProp" } }, "required": ["sections"], "patternProperties": { "^singleOpen\\.[^.]+$": { "$ref": "#/$defs/singleOpenProp" }, "^defaultOpen\\.[^.]+$": { "$ref": "#/$defs/defaultOpenProp" }, "^renderMode\\.[^.]+$": { "$ref": "#/$defs/renderModeProp" }, "^sections\\.[^.]+$": { "$ref": "#/$defs/sectionsProp" } }, "additionalProperties": false } };
748
+ const required$6 = ["kind", "type", "children", "props"];
749
+ const unevaluatedProperties$7 = false;
750
+ const accordionSchemaJson = {
751
+ $schema: $schema$7,
752
+ $id: $id$7,
753
+ title: title$7,
754
+ type: type$7,
755
+ $defs: $defs$7,
756
+ allOf: allOf$7,
757
+ properties: properties$6,
758
+ required: required$6,
759
+ unevaluatedProperties: unevaluatedProperties$7
760
+ };
761
+ const $schema$6 = "https://json-schema.org/draft/2020-12/schema";
762
+ const $id$6 = "https://golemui.com/schemas/gui/components/flex.schema.json";
763
+ const title$6 = "Flex Widget";
764
+ const type$6 = "object";
765
+ const $defs$6 = { "directionProp": { "enum": ["row", "row-reverse", "column", "column-reverse"] }, "justifyProp": { "enum": ["center", "start", "end", "stretch"] }, "alignProp": { "enum": ["center", "start", "end", "space-between", "space-around", "space-evenly"] }, "gapProp": { "type": "number" } };
766
+ const allOf$6 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
767
+ const properties$5 = { "kind": { "const": "layout" }, "type": { "const": "flex" }, "children": { "type": "array", "minItems": 1, "items": { "$ref": "../widgets.schema.json#/$defs/formWidget" } }, "props": { "type": "object", "properties": { "direction": { "$ref": "#/$defs/directionProp" }, "justify": { "$ref": "#/$defs/justifyProp" }, "align": { "$ref": "#/$defs/alignProp" }, "gap": { "$ref": "#/$defs/gapProp" } }, "patternProperties": { "^direction\\.[^.]+$": { "$ref": "#/$defs/directionProp" }, "^justify\\.[^.]+$": { "$ref": "#/$defs/justifyProp" }, "^align\\.[^.]+$": { "$ref": "#/$defs/alignProp" }, "^gap\\.[^.]+$": { "$ref": "#/$defs/gapProp" } }, "additionalProperties": false } };
768
+ const required$5 = ["kind", "type", "children"];
769
+ const unevaluatedProperties$6 = false;
770
+ const flexSchemaJson = {
771
+ $schema: $schema$6,
772
+ $id: $id$6,
773
+ title: title$6,
774
+ type: type$6,
775
+ $defs: $defs$6,
776
+ allOf: allOf$6,
777
+ properties: properties$5,
778
+ required: required$5,
779
+ unevaluatedProperties: unevaluatedProperties$6
780
+ };
781
+ const $schema$5 = "https://json-schema.org/draft/2020-12/schema";
782
+ const $id$5 = "https://golemui.com/schemas/gui/components/grid.schema.json";
783
+ const title$5 = "Grid Widget";
784
+ const type$5 = "object";
785
+ const $defs$5 = { "directionProp": { "enum": ["row", "column"] }, "columnGapProp": { "type": "number" }, "rowGapProp": { "type": "number" }, "autoFitProp": { "type": "boolean" }, "alignProp": { "enum": ["center", "start", "end", "space-between", "space-around", "space-evenly", "stretch"] }, "justifyProp": { "enum": ["center", "start", "end", "stretch"] } };
786
+ const allOf$5 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
787
+ const properties$4 = { "kind": { "const": "layout" }, "type": { "const": "grid" }, "children": { "type": "array", "minItems": 1, "items": { "$ref": "../widgets.schema.json#/$defs/formWidget" } }, "props": { "type": "object", "properties": { "direction": { "$ref": "#/$defs/directionProp" }, "columnGap": { "$ref": "#/$defs/columnGapProp" }, "rowGap": { "$ref": "#/$defs/rowGapProp" }, "autoFit": { "$ref": "#/$defs/autoFitProp" }, "align": { "$ref": "#/$defs/alignProp" }, "justify": { "$ref": "#/$defs/justifyProp" } }, "patternProperties": { "^direction\\.[^.]+$": { "$ref": "#/$defs/directionProp" }, "^columnGap\\.[^.]+$": { "$ref": "#/$defs/columnGapProp" }, "^rowGap\\.[^.]+$": { "$ref": "#/$defs/rowGapProp" }, "^autoFit\\.[^.]+$": { "$ref": "#/$defs/autoFitProp" }, "^align\\.[^.]+$": { "$ref": "#/$defs/alignProp" }, "^justify\\.[^.]+$": { "$ref": "#/$defs/justifyProp" } }, "additionalProperties": false } };
788
+ const required$4 = ["kind", "type", "children"];
789
+ const unevaluatedProperties$5 = false;
790
+ const gridSchemaJson = {
791
+ $schema: $schema$5,
792
+ $id: $id$5,
793
+ title: title$5,
794
+ type: type$5,
795
+ $defs: $defs$5,
796
+ allOf: allOf$5,
797
+ properties: properties$4,
798
+ required: required$4,
799
+ unevaluatedProperties: unevaluatedProperties$5
800
+ };
801
+ const $schema$4 = "https://json-schema.org/draft/2020-12/schema";
802
+ const $id$4 = "https://golemui.com/schemas/gui/components/tabs.schema.json";
803
+ const title$4 = "Tabs Widget";
804
+ const type$4 = "object";
805
+ const $defs$4 = { "defaultOpenProp": { "type": "string", "description": "UID of the tab that is active on initial render. Defaults to the first tab." }, "renderModeProp": { "description": "Controls when tab content is rendered: `all` keeps all tabs in the DOM, `activeOnly` unmounts inactive ones", "enum": ["all", "activeOnly"] }, "tabsProp": { "type": "array", "description": "Ordered list of tab definitions. Each tab's `uid` must match the widget UIDs used in `children`.", "minItems": 1, "items": { "type": "object", "properties": { "label": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "uid": { "type": "string", "description": "Unique identifier linking this tab definition to its widgets in `children`" } }, "required": ["label", "uid"], "additionalProperties": false } } };
806
+ const allOf$4 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
807
+ const properties$3 = { "kind": { "const": "layout" }, "type": { "const": "tabs" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "children": { "type": "array", "description": "Flat list of widgets belonging to all tabs. Each widget must have a `uid` matching one of the tab UIDs in `props.tabs`.", "minItems": 1, "items": { "$ref": "../widgets.schema.json#/$defs/formWidget" } }, "props": { "type": "object", "properties": { "defaultOpen": { "$ref": "#/$defs/defaultOpenProp" }, "renderMode": { "$ref": "#/$defs/renderModeProp" }, "tabs": { "$ref": "#/$defs/tabsProp" } }, "required": ["tabs"], "patternProperties": { "^defaultOpen\\.[^.]+$": { "$ref": "#/$defs/defaultOpenProp" }, "^renderMode\\.[^.]+$": { "$ref": "#/$defs/renderModeProp" }, "^tabs\\.[^.]+$": { "$ref": "#/$defs/tabsProp" } }, "additionalProperties": false } };
808
+ const required$3 = ["kind", "type", "children", "props"];
809
+ const unevaluatedProperties$4 = false;
810
+ const tabsSchemaJson = {
811
+ $schema: $schema$4,
812
+ $id: $id$4,
813
+ title: title$4,
814
+ type: type$4,
815
+ $defs: $defs$4,
816
+ allOf: allOf$4,
817
+ properties: properties$3,
818
+ required: required$3,
819
+ unevaluatedProperties: unevaluatedProperties$4
820
+ };
821
+ const $schema$3 = "https://json-schema.org/draft/2020-12/schema";
822
+ const $id$3 = "https://golemui.com/schemas/gui/components/alert.schema.json";
823
+ const title$3 = "Alert Widget";
824
+ const type$3 = "object";
825
+ const $defs$3 = { "textProp": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "levelProp": { "enum": ["default", "info", "success", "warning", "error"] } };
826
+ const allOf$3 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
827
+ const properties$2 = { "kind": { "const": "display" }, "type": { "const": "alert" }, "props": { "type": "object", "properties": { "text": { "$ref": "#/$defs/textProp" }, "level": { "$ref": "#/$defs/levelProp" } }, "patternProperties": { "^text\\.[^.]+$": { "$ref": "#/$defs/textProp" }, "^level\\.[^.]+$": { "$ref": "#/$defs/levelProp" } }, "required": ["text"], "additionalProperties": false } };
828
+ const required$2 = ["kind", "type", "props"];
829
+ const unevaluatedProperties$3 = false;
830
+ const alertSchemaJson = {
831
+ $schema: $schema$3,
832
+ $id: $id$3,
833
+ title: title$3,
834
+ type: type$3,
835
+ $defs: $defs$3,
836
+ allOf: allOf$3,
837
+ properties: properties$2,
838
+ required: required$2,
839
+ unevaluatedProperties: unevaluatedProperties$3
840
+ };
841
+ const $schema$2 = "https://json-schema.org/draft/2020-12/schema";
842
+ const $id$2 = "https://golemui.com/schemas/gui/components/markdowntext.schema.json";
843
+ const title$2 = "MarkdownText Widget";
844
+ const type$2 = "object";
845
+ const $defs$2 = { "mdProp": { "$ref": "../core/common.schema.json#/$defs/localizable" } };
846
+ const allOf$2 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
847
+ const properties$1 = { "kind": { "const": "display" }, "type": { "const": "markdownText" }, "props": { "type": "object", "properties": { "md": { "$ref": "#/$defs/mdProp" } }, "patternProperties": { "^md\\.[^.]+$": { "$ref": "#/$defs/mdProp" } }, "required": ["md"], "additionalProperties": false } };
848
+ const required$1 = ["kind", "type", "props"];
849
+ const unevaluatedProperties$2 = false;
850
+ const markdowntextSchemaJson = {
851
+ $schema: $schema$2,
852
+ $id: $id$2,
853
+ title: title$2,
854
+ type: type$2,
855
+ $defs: $defs$2,
856
+ allOf: allOf$2,
857
+ properties: properties$1,
858
+ required: required$1,
859
+ unevaluatedProperties: unevaluatedProperties$2
860
+ };
861
+ const $schema$1 = "https://json-schema.org/draft/2020-12/schema";
862
+ const $id$1 = "https://golemui.com/schemas/gui/components/button.schema.json";
863
+ const title$1 = "Button Widget";
864
+ const type$1 = "object";
865
+ const $defs$1 = { "labelDef": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabledDef": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "variantProp": { "enum": ["filled", "outlined", "link"] }, "iconProp": { "type": "string" }, "iconPositionProp": { "enum": ["left", "right"] } };
866
+ const allOf$1 = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }];
867
+ const properties = { "kind": { "const": "action" }, "type": { "const": "button" }, "actionType": { "enum": ["button", "submit"] }, "label": { "$ref": "#/$defs/labelDef" }, "disabled": { "$ref": "#/$defs/disabledDef" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "props": { "type": "object", "properties": { "variant": { "$ref": "#/$defs/variantProp" }, "icon": { "$ref": "#/$defs/iconProp" }, "iconPosition": { "$ref": "#/$defs/iconPositionProp" } }, "patternProperties": { "^variant\\.[^.]+$": { "$ref": "#/$defs/variantProp" }, "^icon\\.[^.]+$": { "$ref": "#/$defs/iconProp" }, "^iconPosition\\.[^.]+$": { "$ref": "#/$defs/iconPositionProp" } }, "additionalProperties": false } };
868
+ const patternProperties = { "^disabled\\.[^.]+$": { "$ref": "#/$defs/disabledDef" }, "^label\\.[^.]+$": { "$ref": "#/$defs/labelDef" } };
869
+ const required = ["kind", "type"];
870
+ const unevaluatedProperties$1 = false;
871
+ const buttonSchemaJson = {
872
+ $schema: $schema$1,
873
+ $id: $id$1,
874
+ title: title$1,
875
+ type: type$1,
876
+ $defs: $defs$1,
877
+ allOf: allOf$1,
878
+ properties,
879
+ patternProperties,
880
+ required,
881
+ unevaluatedProperties: unevaluatedProperties$1
882
+ };
883
+ const $schema = "https://json-schema.org/draft/2020-12/schema";
884
+ const $id = "https://golemui.com/schemas/gui/components/custom.schema.json";
885
+ const title = "Custom Widget";
886
+ const description = "Fallback for user-registered custom components. Matches any widget whose `type` is NOT a built-in. Structural fields required by the widget's `kind` are validated (input -> path, layout -> children); `props` is an open object validated at runtime by the custom component itself.";
887
+ const type = "object";
888
+ const allOf = [{ "$ref": "../core/common.schema.json#/$defs/baseWidget" }, { "properties": { "type": { "not": { "$ref": "../widgets.schema.json#/$defs/knownWidgetTypes" } } } }];
889
+ const oneOf = [{ "$ref": "#/$defs/customInput" }, { "$ref": "#/$defs/customDisplay" }, { "$ref": "#/$defs/customAction" }, { "$ref": "#/$defs/customLayout" }];
890
+ const unevaluatedProperties = false;
891
+ const $defs = { "customInput": { "type": "object", "description": "Custom input widget. Binds to form data via `path`; `props` is open.", "properties": { "kind": { "const": "input" }, "type": { "type": "string" }, "path": { "$ref": "../core/common.schema.json#/$defs/dotPath" }, "label": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabled": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "readonly": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "validator": { "$ref": "../validators.schema.json#/$defs/validator" }, "defaultValue": true, "props": { "type": "object" } }, "patternProperties": { "^label\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabled\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "^readonly\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "^validator\\.[^.]+$": { "$ref": "../validators.schema.json#/$defs/validator" } }, "required": ["kind", "type", "path"] }, "customDisplay": { "type": "object", "description": "Custom display widget. No data binding; `props` is open.", "properties": { "kind": { "const": "display" }, "type": { "type": "string" }, "props": { "type": "object" } }, "required": ["kind", "type"] }, "customAction": { "type": "object", "description": "Custom action widget; `props` is open.", "properties": { "kind": { "const": "action" }, "type": { "type": "string" }, "label": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "disabled": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" }, "on": { "$ref": "../core/common.schema.json#/$defs/on" }, "props": { "type": "object" } }, "patternProperties": { "^label\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/localizable" }, "^disabled\\.[^.]+$": { "$ref": "../core/common.schema.json#/$defs/boolOrWhen" } }, "required": ["kind", "type"] }, "customLayout": { "type": "object", "description": "Custom layout widget. Contains `children`; `props` is open.", "properties": { "kind": { "const": "layout" }, "type": { "type": "string" }, "children": { "type": "array", "minItems": 1, "items": { "$ref": "../widgets.schema.json#/$defs/formWidget" } }, "props": { "type": "object" } }, "required": ["kind", "type", "children"] } };
892
+ const customSchemaJson = {
893
+ $schema,
894
+ $id,
895
+ title,
896
+ description,
897
+ type,
898
+ allOf,
899
+ oneOf,
900
+ unevaluatedProperties,
901
+ $defs
902
+ };
903
+ const commonSchema = commonSchemaJson;
904
+ const rangesSchema = rangesSchemaJson;
905
+ const validatorsSchema = validatorsSchemaJson;
906
+ const formSchema = formSchemaJson;
907
+ const layoutWidgetSchema = layoutWidgetSchemaJson;
908
+ const widgetsSchema = widgetsSchemaJson;
909
+ const calendarSchema = calendarSchemaJson;
910
+ const datetimecalendarSchema = datetimecalendarSchemaJson;
911
+ const checkboxSchema = checkboxSchemaJson;
912
+ const currencySchema = currencySchemaJson;
913
+ const dateinputSchema = dateinputSchemaJson;
914
+ const datepickerSchema = datepickerSchemaJson;
915
+ const datetimeinputSchema = datetimeinputSchemaJson;
916
+ const datetimepickerSchema = datetimepickerSchemaJson;
917
+ const dropdownSchema = dropdownSchemaJson;
918
+ const listSchema = listSchemaJson;
919
+ const markdownSchema = markdownSchemaJson;
920
+ const numberSchema = numberSchemaJson;
921
+ const passwordSchema = passwordSchemaJson;
922
+ const radiogroupSchema = radiogroupSchemaJson;
923
+ const rangecalendarSchema = rangecalendarSchemaJson;
924
+ const rangedateinputSchema = rangedateinputSchemaJson;
925
+ const rangedatepickerSchema = rangedatepickerSchemaJson;
926
+ const rangedatetimeinputSchema = rangedatetimeinputSchemaJson;
927
+ const rangedatetimecalendarSchema = rangedatetimecalendarSchemaJson;
928
+ const rangedatetimepickerSchema = rangedatetimepickerSchemaJson;
929
+ const rangetimeinputSchema = rangetimeinputSchemaJson;
930
+ const rangetimepickerSchema = rangetimepickerSchemaJson;
931
+ const repeaterSchema = repeaterSchemaJson;
932
+ const selectSchema = selectSchemaJson;
933
+ const tagsSchema = tagsSchemaJson;
934
+ const textareaSchema = textareaSchemaJson;
935
+ const textinputSchema = textinputSchemaJson;
936
+ const timeinputSchema = timeinputSchemaJson;
937
+ const timepickerSchema = timepickerSchemaJson;
938
+ const toggleSchema = toggleSchemaJson;
939
+ const accordionSchema = accordionSchemaJson;
940
+ const flexSchema = flexSchemaJson;
941
+ const gridSchema = gridSchemaJson;
942
+ const tabsSchema = tabsSchemaJson;
943
+ const alertSchema = alertSchemaJson;
944
+ const markdowntextSchema = markdowntextSchemaJson;
945
+ const buttonSchema = buttonSchemaJson;
946
+ const customSchema = customSchemaJson;
947
+ const COMPONENT_SCHEMAS_BY_TYPE = {
948
+ calendar: calendarSchema,
949
+ dateTimeCalendar: datetimecalendarSchema,
950
+ checkbox: checkboxSchema,
951
+ currency: currencySchema,
952
+ dateInput: dateinputSchema,
953
+ datePicker: datepickerSchema,
954
+ dateTimeInput: datetimeinputSchema,
955
+ dateTimePicker: datetimepickerSchema,
956
+ dropdown: dropdownSchema,
957
+ list: listSchema,
958
+ markdown: markdownSchema,
959
+ number: numberSchema,
960
+ password: passwordSchema,
961
+ radiogroup: radiogroupSchema,
962
+ rangeCalendar: rangecalendarSchema,
963
+ rangeDateInput: rangedateinputSchema,
964
+ rangeDatePicker: rangedatepickerSchema,
965
+ rangeDateTimeInput: rangedatetimeinputSchema,
966
+ rangeDateTimeCalendar: rangedatetimecalendarSchema,
967
+ rangeDateTimePicker: rangedatetimepickerSchema,
968
+ rangeTimeInput: rangetimeinputSchema,
969
+ rangeTimePicker: rangetimepickerSchema,
970
+ repeater: repeaterSchema,
971
+ select: selectSchema,
972
+ tags: tagsSchema,
973
+ textarea: textareaSchema,
974
+ textinput: textinputSchema,
975
+ timeInput: timeinputSchema,
976
+ timePicker: timepickerSchema,
977
+ toggle: toggleSchema,
978
+ accordion: accordionSchema,
979
+ flex: flexSchema,
980
+ grid: gridSchema,
981
+ tabs: tabsSchema,
982
+ alert: alertSchema,
983
+ markdownText: markdowntextSchema,
984
+ button: buttonSchema
985
+ };
986
+ const COMMON_SCHEMA = commonSchema;
987
+ const FORM_SCHEMA = formSchema;
988
+ const WIDGETS_SCHEMA = widgetsSchema;
989
+ const LAYOUT_WIDGET_SCHEMA = layoutWidgetSchema;
990
+ const VALIDATORS_SCHEMA = validatorsSchema;
991
+ const RANGES_SCHEMA = rangesSchema;
992
+ const CUSTOM_SCHEMA = customSchema;
993
+ const COMPONENT_SCHEMAS = COMPONENT_SCHEMAS_BY_TYPE;
994
+ const ALL_SCHEMAS = [
995
+ COMMON_SCHEMA,
996
+ VALIDATORS_SCHEMA,
997
+ RANGES_SCHEMA,
998
+ WIDGETS_SCHEMA,
999
+ LAYOUT_WIDGET_SCHEMA,
1000
+ ...Object.values(COMPONENT_SCHEMAS),
1001
+ CUSTOM_SCHEMA,
1002
+ FORM_SCHEMA
1003
+ ];
1004
+ let cachedAjv = null;
1005
+ let cachedFormValidator = null;
1006
+ function buildAjv() {
1007
+ const ajv = new Ajv2020({
1008
+ allErrors: true,
1009
+ strict: false,
1010
+ verbose: true
1011
+ });
1012
+ addFormats(ajv);
1013
+ const registeredKeys = /* @__PURE__ */ new Set();
1014
+ for (const schema of ALL_SCHEMAS) {
1015
+ if (typeof schema.$id === "string" && !registeredKeys.has(schema.$id)) {
1016
+ registeredKeys.add(schema.$id);
1017
+ ajv.addSchema(schema);
1018
+ }
1019
+ }
1020
+ return ajv;
1021
+ }
1022
+ function getAjv() {
1023
+ if (!cachedAjv) {
1024
+ cachedAjv = buildAjv();
1025
+ }
1026
+ return cachedAjv;
1027
+ }
1028
+ function getFormValidator() {
1029
+ if (!cachedFormValidator) {
1030
+ cachedFormValidator = getAjv().compile(FORM_SCHEMA);
1031
+ }
1032
+ return cachedFormValidator;
1033
+ }
1034
+ const cache = /* @__PURE__ */ new Map();
1035
+ const validatorBranchCache = /* @__PURE__ */ new Map();
1036
+ const customKindCache = /* @__PURE__ */ new Map();
1037
+ let chunkRefValidator = null;
1038
+ const VALIDATOR_TYPE_TO_DEF = {
1039
+ string: "stringValidator",
1040
+ number: "numberValidator",
1041
+ integer: "numberValidator",
1042
+ boolean: "booleanValidator",
1043
+ array: "arrayValidator",
1044
+ custom: "customValidator"
1045
+ };
1046
+ function getValidatorBranches() {
1047
+ return Object.keys(VALIDATOR_TYPE_TO_DEF);
1048
+ }
1049
+ function getValidatorBranchValidator(validatorType) {
1050
+ const defKey = VALIDATOR_TYPE_TO_DEF[validatorType];
1051
+ if (!defKey) return null;
1052
+ if (validatorBranchCache.has(defKey)) return validatorBranchCache.get(defKey);
1053
+ const defs = VALIDATORS_SCHEMA.$defs ?? {};
1054
+ const branch = defs[defKey];
1055
+ if (!branch) return null;
1056
+ const cloned = {
1057
+ ...JSON.parse(JSON.stringify(branch)),
1058
+ $defs: JSON.parse(JSON.stringify(defs))
1059
+ };
1060
+ rewriteRefs(cloned, VALIDATORS_SCHEMA.$id);
1061
+ const ajv = getAjv();
1062
+ const v = ajv.compile(cloned);
1063
+ validatorBranchCache.set(defKey, v);
1064
+ return v;
1065
+ }
1066
+ function getChunkRefValidator() {
1067
+ if (!chunkRefValidator) {
1068
+ const ajv = getAjv();
1069
+ chunkRefValidator = ajv.compile({ $ref: `${COMMON_SCHEMA.$id}#/$defs/chunkRef` });
1070
+ }
1071
+ return chunkRefValidator;
1072
+ }
1073
+ const CUSTOM_KIND_TO_DEF = {
1074
+ input: "customInput",
1075
+ display: "customDisplay",
1076
+ action: "customAction",
1077
+ layout: "customLayout"
1078
+ };
1079
+ function getCustomWidgetKinds() {
1080
+ return Object.keys(CUSTOM_KIND_TO_DEF);
1081
+ }
1082
+ function getCustomWidgetValidator(kind) {
1083
+ const defKey = CUSTOM_KIND_TO_DEF[kind];
1084
+ if (!defKey) return null;
1085
+ if (customKindCache.has(defKey)) return customKindCache.get(defKey);
1086
+ const cloned = JSON.parse(JSON.stringify(CUSTOM_SCHEMA));
1087
+ rewriteRefs(cloned, CUSTOM_SCHEMA.$id);
1088
+ delete cloned["$id"];
1089
+ delete cloned["oneOf"];
1090
+ cloned["allOf"] = [
1091
+ ...cloned["allOf"] ?? [],
1092
+ { $ref: `#/$defs/${defKey}` }
1093
+ ];
1094
+ loosenNestedContent(cloned["$defs"]);
1095
+ const ajv = getAjv();
1096
+ const validator = ajv.compile(cloned);
1097
+ customKindCache.set(defKey, validator);
1098
+ return validator;
1099
+ }
1100
+ function loosenNestedContent(defs) {
1101
+ const layoutProps = defs?.["customLayout"]?.properties;
1102
+ if (layoutProps?.["children"]) {
1103
+ layoutProps["children"] = { type: "array" };
1104
+ }
1105
+ const customInput = defs?.["customInput"];
1106
+ if (customInput?.properties?.["validator"]) {
1107
+ customInput.properties["validator"] = { type: "object" };
1108
+ }
1109
+ const patternProps = customInput?.patternProperties;
1110
+ if (patternProps) {
1111
+ for (const key of Object.keys(patternProps)) {
1112
+ if (key.startsWith("^validator\\.")) {
1113
+ patternProps[key] = { type: "object" };
1114
+ }
1115
+ }
1116
+ }
1117
+ }
1118
+ function getShallowWidgetValidator(widgetType) {
1119
+ if (cache.has(widgetType)) return cache.get(widgetType);
1120
+ const schema = COMPONENT_SCHEMAS[widgetType];
1121
+ if (!schema) return null;
1122
+ const shallow = makeShallow(schema, schema.$id);
1123
+ const ajv = getAjv();
1124
+ const validator = ajv.compile(shallow);
1125
+ cache.set(widgetType, validator);
1126
+ return validator;
1127
+ }
1128
+ function makeShallow(schema, baseId) {
1129
+ const cloned = JSON.parse(JSON.stringify(schema));
1130
+ rewriteRefs(cloned, baseId);
1131
+ delete cloned["$id"];
1132
+ const props = cloned["properties"] ?? {};
1133
+ if (props["children"]) {
1134
+ props["children"] = { type: "array" };
1135
+ }
1136
+ if (props["validator"]) {
1137
+ props["validator"] = { type: "object" };
1138
+ }
1139
+ const patternProps = cloned["patternProperties"];
1140
+ if (patternProps) {
1141
+ for (const key of Object.keys(patternProps)) {
1142
+ if (key.startsWith("^validator\\.")) {
1143
+ patternProps[key] = { type: "object" };
1144
+ }
1145
+ }
1146
+ }
1147
+ const propsField = props["props"];
1148
+ if (propsField?.properties?.["template"]) {
1149
+ propsField.properties["template"] = { type: "object" };
1150
+ }
1151
+ return cloned;
1152
+ }
1153
+ function rewriteRefs(node, baseId) {
1154
+ if (node === null || typeof node !== "object") return;
1155
+ if (Array.isArray(node)) {
1156
+ for (const item of node) rewriteRefs(item, baseId);
1157
+ return;
1158
+ }
1159
+ const obj = node;
1160
+ if (typeof obj["$ref"] === "string") {
1161
+ const ref = obj["$ref"];
1162
+ if (!ref.startsWith("http") && !ref.startsWith("#")) {
1163
+ try {
1164
+ obj["$ref"] = new URL(ref, baseId).href;
1165
+ } catch {
1166
+ }
1167
+ }
1168
+ }
1169
+ for (const v of Object.values(obj)) rewriteRefs(v, baseId);
1170
+ }
1171
+ const STRING_FORMATS = [
1172
+ "email",
1173
+ "hostname",
1174
+ "ipv4",
1175
+ "ipv6",
1176
+ "url",
1177
+ "uuid",
1178
+ "date",
1179
+ "time",
1180
+ "date-time",
1181
+ "duration"
1182
+ ];
1183
+ const WIDGET_TYPES = Object.keys(COMPONENT_SCHEMAS);
1184
+ const SCHEMALESS_WIDGET_TYPES = new Set(
1185
+ (WIDGETS_SCHEMA["$defs"]?.["knownWidgetTypes"]?.enum ?? []).filter((type2) => !COMPONENT_SCHEMAS[type2])
1186
+ );
1187
+ function levenshtein(a, b) {
1188
+ if (a === b) return 0;
1189
+ if (!a.length) return b.length;
1190
+ if (!b.length) return a.length;
1191
+ let prev = new Array(b.length + 1);
1192
+ let curr = new Array(b.length + 1);
1193
+ for (let j = 0; j <= b.length; j++) prev[j] = j;
1194
+ for (let i = 1; i <= a.length; i++) {
1195
+ curr[0] = i;
1196
+ for (let j = 1; j <= b.length; j++) {
1197
+ const cost = a[i - 1] === b[j - 1] ? 0 : 1;
1198
+ const del = (prev[j] ?? 0) + 1;
1199
+ const ins = (curr[j - 1] ?? 0) + 1;
1200
+ const sub = (prev[j - 1] ?? 0) + cost;
1201
+ curr[j] = Math.min(del, ins, sub);
1202
+ }
1203
+ [prev, curr] = [curr, prev];
1204
+ }
1205
+ return prev[b.length] ?? 0;
1206
+ }
1207
+ function nearest(target, candidates, maxDistance) {
1208
+ let best;
1209
+ let bestDist = Infinity;
1210
+ for (const c of candidates) {
1211
+ const d = levenshtein(target.toLowerCase(), c.toLowerCase());
1212
+ if (d < bestDist) {
1213
+ bestDist = d;
1214
+ best = c;
1215
+ }
1216
+ }
1217
+ const budget = maxDistance ?? Math.max(2, Math.floor(target.length / 2));
1218
+ return bestDist <= budget ? best : void 0;
1219
+ }
1220
+ function widgetTypeDistance(widgetType) {
1221
+ return Math.max(1, Math.floor(widgetType.length / 3));
1222
+ }
1223
+ function suggestForAdditional(propertyName, instancePath) {
1224
+ if (/\/validator(\/|$)/.test(instancePath)) {
1225
+ const validatorKeys = [
1226
+ "type",
1227
+ "required",
1228
+ "minLength",
1229
+ "maxLength",
1230
+ "minimum",
1231
+ "maximum",
1232
+ "pattern",
1233
+ "format",
1234
+ "const",
1235
+ "enum",
1236
+ "messages",
1237
+ "minItems",
1238
+ "maxItems",
1239
+ "uniqueItems",
1240
+ "multipleOf",
1241
+ "exclusiveMinimum",
1242
+ "exclusiveMaximum"
1243
+ ];
1244
+ const guess = nearest(propertyName, validatorKeys);
1245
+ if (guess && guess !== propertyName) return `Did you mean \`${guess}\`?`;
1246
+ return void 0;
1247
+ }
1248
+ return void 0;
1249
+ }
1250
+ function suggestForEnum(value, allowed) {
1251
+ if (typeof value !== "string") return void 0;
1252
+ const stringAllowed = allowed.filter((v) => typeof v === "string");
1253
+ if (!stringAllowed.length) return void 0;
1254
+ const guess = nearest(value, stringAllowed);
1255
+ if (guess)
1256
+ return `Did you mean \`${guess}\`? Allowed values: ${stringAllowed.map((v) => `\`${v}\``).join(", ")}.`;
1257
+ return `Allowed values: ${stringAllowed.map((v) => `\`${v}\``).join(", ")}.`;
1258
+ }
1259
+ const VALIDATOR_TYPES = ["string", "number", "integer", "boolean", "array", "custom"];
1260
+ function suggestForConst(value, allowed, instancePath) {
1261
+ if (typeof value !== "string" || typeof allowed !== "string") return void 0;
1262
+ if (/^\/form\/\d+(?:\/children\/\d+|\/props\/template)*\/type$/.test(instancePath)) {
1263
+ const guess = nearest(value, WIDGET_TYPES, widgetTypeDistance(value));
1264
+ return guess ? `Did you mean \`type: '${guess}'\`?` : `Valid widget types: ${WIDGET_TYPES.map((v) => `\`${v}\``).join(", ")}.`;
1265
+ }
1266
+ if (instancePath.endsWith("/validator/type")) {
1267
+ const guess = nearest(value, VALIDATOR_TYPES);
1268
+ return guess ? `Did you mean \`type: '${guess}'\`?` : `Allowed validator types: ${VALIDATOR_TYPES.map((v) => `\`${v}\``).join(", ")}.`;
1269
+ }
1270
+ return void 0;
1271
+ }
1272
+ function describe(value) {
1273
+ if (value === null) return "null";
1274
+ if (Array.isArray(value)) return "array";
1275
+ if (typeof value === "object") return "object";
1276
+ return JSON.stringify(value);
1277
+ }
1278
+ function formatAjvErrors(errors, dataRoot) {
1279
+ if (!errors?.length && dataRoot === void 0) return { errors: [], warnings: [] };
1280
+ const collapsed = dataRoot !== void 0 ? collapseOneOfErrors(errors ?? [], dataRoot) : { errors, warnings: [] };
1281
+ const filtered = collapsed.errors;
1282
+ const out = [];
1283
+ for (const err of filtered) {
1284
+ const path = err.instancePath || "/";
1285
+ let message = err.message ?? "invalid value";
1286
+ let suggestion;
1287
+ switch (err.keyword) {
1288
+ case "additionalProperties":
1289
+ case "unevaluatedProperties": {
1290
+ const params = err.params;
1291
+ const prop = params.additionalProperty ?? params.unevaluatedProperty;
1292
+ if (prop) {
1293
+ message = `Unknown property \`${prop}\` at \`${path}\``;
1294
+ suggestion = suggestForAdditional(prop, path);
1295
+ }
1296
+ break;
1297
+ }
1298
+ case "required": {
1299
+ const prop = err.params.missingProperty;
1300
+ if (prop) {
1301
+ message = `Missing required property \`${prop}\` at \`${path}\``;
1302
+ }
1303
+ break;
1304
+ }
1305
+ case "enum": {
1306
+ const allowed = err.params.allowedValues ?? [];
1307
+ const v = describe(err.data);
1308
+ message = `Value ${v} at \`${path}\` is not one of the allowed values`;
1309
+ suggestion = suggestForEnum(err.data, allowed);
1310
+ break;
1311
+ }
1312
+ case "const": {
1313
+ const allowed = err.params.allowedValue;
1314
+ message = `Expected \`${describe(allowed)}\` at \`${path}\`, got \`${describe(err.data)}\``;
1315
+ suggestion = suggestForConst(err.data, allowed, path);
1316
+ break;
1317
+ }
1318
+ case "type": {
1319
+ const expected = err.params.type;
1320
+ message = `Expected type ${Array.isArray(expected) ? expected.join("|") : expected} at \`${path}\`, got ${describe(err.data)}`;
1321
+ break;
1322
+ }
1323
+ case "schemalessType": {
1324
+ const type2 = err.params.type;
1325
+ message = `Widget type \`${type2}\` at \`${path}\` is a built-in with no JSON representation, so it cannot appear in a JSON form definition`;
1326
+ suggestion = `Add this widget through the TS DX API instead (for example \`gui.displays.display(render)\`), or remove it from the JSON.`;
1327
+ break;
1328
+ }
1329
+ case "oneOf":
1330
+ case "anyOf": {
1331
+ message = `Value at \`${path}\` does not match any allowed variant`;
1332
+ break;
1333
+ }
1334
+ default:
1335
+ message = `${err.message ?? "invalid value"} at \`${path}\``;
1336
+ }
1337
+ if (path.endsWith("/validator/format") && err.keyword === "enum") {
1338
+ suggestion = `Allowed string formats: ${STRING_FORMATS.map((f) => `\`${f}\``).join(", ")}.`;
1339
+ }
1340
+ out.push({
1341
+ path,
1342
+ message,
1343
+ suggestion,
1344
+ keyword: err.keyword,
1345
+ params: err.params
1346
+ });
1347
+ }
1348
+ return { errors: dedupe(out), warnings: collapsed.warnings };
1349
+ }
1350
+ function extractWidgetPath(instancePath) {
1351
+ const m = instancePath.match(/^(\/form\/\d+(?:\/children\/\d+)*)/);
1352
+ return m ? m[1] : null;
1353
+ }
1354
+ function pickIntendedBranch(widget) {
1355
+ if (!widget || typeof widget !== "object") return null;
1356
+ const w = widget;
1357
+ const widgetType = typeof w.type === "string" ? w.type : void 0;
1358
+ const widgetKind = typeof w.kind === "string" ? w.kind : void 0;
1359
+ if (widgetType && COMPONENT_SCHEMAS[widgetType]) {
1360
+ return { $id: COMPONENT_SCHEMAS[widgetType].$id, type: widgetType };
1361
+ }
1362
+ if (!widgetType) return null;
1363
+ const kindMatched = Object.entries(COMPONENT_SCHEMAS).filter(([, schema]) => {
1364
+ const k = schema["properties"]?.["kind"]?.const;
1365
+ return k === widgetKind;
1366
+ });
1367
+ const pool = kindMatched.length ? kindMatched : Object.entries(COMPONENT_SCHEMAS);
1368
+ const candidateTypes = pool.map(([t]) => t);
1369
+ const match = nearest(widgetType, candidateTypes, widgetTypeDistance(widgetType));
1370
+ if (!match) return null;
1371
+ return { $id: COMPONENT_SCHEMAS[match].$id, type: match };
1372
+ }
1373
+ function collapseOneOfErrors(errors, dataRoot) {
1374
+ const topLevel = [];
1375
+ for (const err of errors) {
1376
+ if (extractWidgetPath(err.instancePath) === null) topLevel.push(err);
1377
+ }
1378
+ const widgetErrors = [];
1379
+ const warnings = [];
1380
+ const form = dataRoot?.form;
1381
+ if (Array.isArray(form)) {
1382
+ form.forEach((widget, i) => {
1383
+ collectWidgetErrors(widget, `/form/${i}`, widgetErrors, warnings);
1384
+ });
1385
+ }
1386
+ return { errors: [...topLevel, ...widgetErrors], warnings };
1387
+ }
1388
+ function isChunkRef(widget) {
1389
+ return typeof widget === "object" && widget !== null && !Array.isArray(widget) && "$ref" in widget;
1390
+ }
1391
+ function collectWidgetErrors(widget, widgetPath, out, warnings) {
1392
+ if (isChunkRef(widget)) {
1393
+ const chunkRefValidator2 = getChunkRefValidator();
1394
+ chunkRefValidator2(widget);
1395
+ for (const e of chunkRefValidator2.errors ?? []) {
1396
+ out.push({ ...e, instancePath: widgetPath + e.instancePath });
1397
+ }
1398
+ return;
1399
+ }
1400
+ const declaredType = widget?.type;
1401
+ if (typeof declaredType === "string" && SCHEMALESS_WIDGET_TYPES.has(declaredType)) {
1402
+ out.push({
1403
+ keyword: "schemalessType",
1404
+ instancePath: `${widgetPath}/type`,
1405
+ schemaPath: "",
1406
+ params: { type: declaredType },
1407
+ message: `Widget type \`${declaredType}\` has no JSON representation`
1408
+ });
1409
+ recurseIntoChildren(widget, widgetPath, out, warnings);
1410
+ return;
1411
+ }
1412
+ const intended = pickIntendedBranch(widget);
1413
+ if (!intended) {
1414
+ const widgetType = widget?.type;
1415
+ if (typeof widgetType !== "string" || !widgetType) {
1416
+ out.push({
1417
+ keyword: "required",
1418
+ instancePath: widgetPath,
1419
+ schemaPath: "",
1420
+ params: { missingProperty: "type" },
1421
+ message: `Widget at ${widgetPath} is missing or has an invalid \`type\``
1422
+ });
1423
+ } else {
1424
+ warnings.push({
1425
+ path: `${widgetPath}/type`,
1426
+ keyword: "customWidget",
1427
+ message: `Widget type \`${widgetType}\` at \`${widgetPath}\` is not a built-in GolemUI widget - assumed custom. Its props were not validated.`,
1428
+ suggestion: "Built-in widget types: " + Object.keys(COMPONENT_SCHEMAS).join(", ") + ". If this is intentional (a custom widget registered via the framework loader), you can ignore this warning.",
1429
+ params: { type: widgetType }
1430
+ });
1431
+ collectCustomWidgetErrors(widget, widgetPath, out);
1432
+ }
1433
+ recurseIntoChildren(widget, widgetPath, out, warnings);
1434
+ return;
1435
+ }
1436
+ const validator = getShallowWidgetValidator(intended.type);
1437
+ if (validator) {
1438
+ validator(widget);
1439
+ for (const e of validator.errors ?? []) {
1440
+ out.push({
1441
+ ...e,
1442
+ instancePath: widgetPath + e.instancePath
1443
+ });
1444
+ }
1445
+ }
1446
+ collectValidatorFieldErrors(widget, widgetPath, out);
1447
+ recurseIntoChildren(widget, widgetPath, out, warnings, intended.type);
1448
+ }
1449
+ function collectCustomWidgetErrors(widget, widgetPath, out) {
1450
+ const kind = widget?.kind;
1451
+ if (typeof kind !== "string") {
1452
+ out.push({
1453
+ keyword: "required",
1454
+ instancePath: widgetPath,
1455
+ schemaPath: "",
1456
+ params: { missingProperty: "kind" },
1457
+ message: `Widget at ${widgetPath} is missing or has an invalid \`kind\``
1458
+ });
1459
+ return;
1460
+ }
1461
+ const validator = getCustomWidgetValidator(kind);
1462
+ if (!validator) {
1463
+ out.push({
1464
+ keyword: "enum",
1465
+ instancePath: `${widgetPath}/kind`,
1466
+ schemaPath: "",
1467
+ params: { allowedValues: getCustomWidgetKinds() },
1468
+ message: `Widget kind is not one of ${getCustomWidgetKinds().join(", ")}`,
1469
+ data: kind
1470
+ });
1471
+ return;
1472
+ }
1473
+ validator(widget);
1474
+ const branchErrors = validator.errors ?? [];
1475
+ const hasSpecificError = branchErrors.some((e) => e.keyword !== "unevaluatedProperties");
1476
+ for (const e of branchErrors) {
1477
+ if (hasSpecificError && e.keyword === "unevaluatedProperties") continue;
1478
+ out.push({ ...e, instancePath: widgetPath + e.instancePath });
1479
+ }
1480
+ if (kind === "input") {
1481
+ collectValidatorFieldErrors(widget, widgetPath, out);
1482
+ }
1483
+ }
1484
+ function collectValidatorFieldErrors(widget, widgetPath, out) {
1485
+ if (!widget || typeof widget !== "object" || Array.isArray(widget)) return;
1486
+ const w = widget;
1487
+ if (w["validator"] && typeof w["validator"] === "object") {
1488
+ collectValidatorErrors(w["validator"], `${widgetPath}/validator`, out);
1489
+ }
1490
+ for (const [key, value] of Object.entries(w)) {
1491
+ if (key.startsWith("validator.") && value && typeof value === "object") {
1492
+ collectValidatorErrors(value, `${widgetPath}/${key}`, out);
1493
+ }
1494
+ }
1495
+ }
1496
+ function recurseIntoChildren(widget, widgetPath, out, warnings, resolvedType) {
1497
+ const w = widget;
1498
+ if (Array.isArray(w?.children)) {
1499
+ w.children.forEach((child, i) => {
1500
+ collectWidgetErrors(child, `${widgetPath}/children/${i}`, out, warnings);
1501
+ });
1502
+ }
1503
+ if ((resolvedType ?? w?.type) === "repeater" && w?.props?.template) {
1504
+ collectWidgetErrors(w.props.template, `${widgetPath}/props/template`, out, warnings);
1505
+ }
1506
+ }
1507
+ function collectValidatorErrors(validator, path, out) {
1508
+ const v = validator;
1509
+ const t = typeof v.type === "string" ? v.type : null;
1510
+ const branches = getValidatorBranches();
1511
+ const matchedType = t && branches.includes(t) ? t : t ? nearest(t, branches) : void 0;
1512
+ if (!matchedType) {
1513
+ out.push({
1514
+ keyword: "enum",
1515
+ instancePath: `${path}/type`,
1516
+ schemaPath: "",
1517
+ params: { allowedValues: branches },
1518
+ message: `Validator type is not one of ${branches.join(", ")}`,
1519
+ data: t
1520
+ });
1521
+ return;
1522
+ }
1523
+ const compiled = getValidatorBranchValidator(matchedType);
1524
+ if (!compiled) return;
1525
+ compiled(validator);
1526
+ for (const e of compiled.errors ?? []) {
1527
+ out.push({ ...e, instancePath: path + e.instancePath });
1528
+ }
1529
+ }
1530
+ function dedupe(errors) {
1531
+ const seen = /* @__PURE__ */ new Set();
1532
+ const result = [];
1533
+ for (const e of errors) {
1534
+ const key = `${e.path}|${e.keyword}|${e.message}`;
1535
+ if (seen.has(key)) continue;
1536
+ seen.add(key);
1537
+ result.push(e);
1538
+ }
1539
+ return result;
1540
+ }
1541
+ function lintReactiveExpressions(formDefinition) {
1542
+ const findings = [];
1543
+ walk$2(formDefinition, "", findings, false, false);
1544
+ return findings;
1545
+ }
1546
+ function checkReactiveExpression(expression, path = "", options = {}) {
1547
+ const out = [];
1548
+ checkExpression(expression, path, out, options.inRepeaterTemplate === true);
1549
+ return out;
1550
+ }
1551
+ function walk$2(node, path, out, inTemplate, propsOfRepeater) {
1552
+ if (node === null || typeof node !== "object") return;
1553
+ if (Array.isArray(node)) {
1554
+ node.forEach((item, i) => walk$2(item, `${path}/${i}`, out, inTemplate, false));
1555
+ return;
1556
+ }
1557
+ const obj = node;
1558
+ for (const key of ["include", "exclude"]) {
1559
+ const child = obj[key];
1560
+ if (child && typeof child === "object" && "when" in child) {
1561
+ const expr = child.when;
1562
+ if (typeof expr === "string") {
1563
+ checkExpression(expr, `${path}/${key}/when`, out, inTemplate);
1564
+ }
1565
+ }
1566
+ }
1567
+ if (path === "" && obj["states"] && typeof obj["states"] === "object") {
1568
+ for (const [name, expr] of Object.entries(obj["states"])) {
1569
+ if (typeof expr === "string") {
1570
+ checkExpression(expr, `/states/${name}`, out, false);
1571
+ }
1572
+ }
1573
+ }
1574
+ for (const [k, v] of Object.entries(obj)) {
1575
+ if (v && typeof v === "object" && !Array.isArray(v) && "when" in v) {
1576
+ const expr = v.when;
1577
+ if (typeof expr === "string" && k !== "include" && k !== "exclude") {
1578
+ checkExpression(expr, `${path}/${k}/when`, out, inTemplate);
1579
+ }
1580
+ }
1581
+ if (typeof v === "object" && v !== null) {
1582
+ const childInTemplate = inTemplate || propsOfRepeater && k === "template";
1583
+ walk$2(v, `${path}/${k}`, out, childInTemplate, obj["type"] === "repeater" && k === "props");
1584
+ }
1585
+ }
1586
+ }
1587
+ function checkExpression(expr, path, out, inTemplate) {
1588
+ const trimmed = expr.trim();
1589
+ if (!trimmed) {
1590
+ out.push({ path, expression: expr, message: "Expression is empty." });
1591
+ return;
1592
+ }
1593
+ const stack = [];
1594
+ const pairs = { ")": "(", "]": "[", "}": "{" };
1595
+ for (const ch of trimmed) {
1596
+ if ("([{".includes(ch)) stack.push(ch);
1597
+ else if (")]}".includes(ch)) {
1598
+ if (stack.pop() !== pairs[ch]) {
1599
+ out.push({
1600
+ path,
1601
+ expression: expr,
1602
+ message: `Unbalanced \`${ch}\` in reactive expression.`
1603
+ });
1604
+ return;
1605
+ }
1606
+ }
1607
+ }
1608
+ if (stack.length) {
1609
+ out.push({
1610
+ path,
1611
+ expression: expr,
1612
+ message: `Unclosed \`${stack[stack.length - 1]}\` in reactive expression.`
1613
+ });
1614
+ return;
1615
+ }
1616
+ const referencesItemScope = /\$item\b|\$index\b/.test(trimmed);
1617
+ const hasGlobalRoot = /\$form\b|\$meta\b|\$formIsInvalid\b|\$fn\b/.test(trimmed);
1618
+ if (referencesItemScope && !inTemplate) {
1619
+ out.push({
1620
+ path,
1621
+ expression: expr,
1622
+ message: "Expression references `$item` or `$index`, which are only available inside a repeater `props.template`.",
1623
+ suggestion: "Move the widget inside the repeater template, or read the data through `$form` (e.g. `$form.lineItems?.[0]?.quantity`)."
1624
+ });
1625
+ } else if (!hasGlobalRoot && !(inTemplate && referencesItemScope)) {
1626
+ out.push({
1627
+ path,
1628
+ expression: expr,
1629
+ message: "Expression does not reference `$form`, `$meta`, `$formIsInvalid`, or `$fn`.",
1630
+ suggestion: "GolemUI expressions read form data via `$form.fieldName`, form metadata via `$meta.key`, or the built-in `$formIsInvalid` boolean. Host-provided pure functions are callable via `$fn.functionName(...)` when the host passes a `functions` map in the form init config. Inside a repeater `props.template` the current item is available via `$item` and its position via `$index`. Did you forget the prefix?"
1631
+ });
1632
+ }
1633
+ if (/(?<![=!<>])=(?![=>])/.test(trimmed)) {
1634
+ out.push({
1635
+ path,
1636
+ expression: expr,
1637
+ message: "Expression contains a single `=` (assignment). Reactive expressions are read-only.",
1638
+ suggestion: "Use `===` for equality comparison."
1639
+ });
1640
+ }
1641
+ if (/(?<![&])&(?![&])/.test(trimmed) || /(?<![|])\|(?![|])/.test(trimmed)) {
1642
+ out.push({
1643
+ path,
1644
+ expression: expr,
1645
+ message: "Expression contains a single `&` or `|` (bitwise).",
1646
+ suggestion: "Use `&&` for logical AND, `||` for logical OR."
1647
+ });
1648
+ }
1649
+ if (/(?<![=!])==(?!=)/.test(trimmed) || /(?<![!])!=(?!=)/.test(trimmed)) {
1650
+ out.push({
1651
+ path,
1652
+ expression: expr,
1653
+ message: "Expression uses loose equality (`==` or `!=`).",
1654
+ suggestion: "Use strict equality `===` / `!==` to avoid type coercion (e.g. `$form.x !== undefined` rather than `$form.x != null`)."
1655
+ });
1656
+ }
1657
+ if (/(?<![=!])!\s*\$(?:form|meta|item)\b/.test(trimmed)) {
1658
+ out.push({
1659
+ path,
1660
+ expression: expr,
1661
+ message: "Expression negates a `$form`/`$meta`/`$item` reference (relies on truthy/falsy coercion).",
1662
+ suggestion: 'Form data values can be `undefined`. Pick the case you actually mean and write it explicitly — `$form.x === undefined`, `$form.x === null`, `$form.x === 0`, `$form.x === ""` — instead of `!$form.x`.'
1663
+ });
1664
+ }
1665
+ const refChainRe = /\$(?:form|meta|item)\b((?:\.[\w?]+)*)/g;
1666
+ let chainFlagged = false;
1667
+ let chainMatch;
1668
+ while ((chainMatch = refChainRe.exec(trimmed)) !== null) {
1669
+ const chain = chainMatch[1];
1670
+ if (!chain) continue;
1671
+ const segments = chain.split(".").filter(Boolean);
1672
+ let unsafe = false;
1673
+ for (let i = 0; i < segments.length - 1; i++) {
1674
+ const segment = segments[i];
1675
+ if (!segment || !segment.endsWith("?")) {
1676
+ unsafe = true;
1677
+ break;
1678
+ }
1679
+ }
1680
+ if (unsafe && !chainFlagged) {
1681
+ out.push({
1682
+ path,
1683
+ expression: expr,
1684
+ message: "Expression chains nested property access without optional chaining (e.g. `$form.user.name`).",
1685
+ suggestion: "Treat every nested property as possibly `undefined`. Use `?.` between segments: `$form.user?.name` instead of `$form.user.name`. The runtime throws if `$form.user` is undefined."
1686
+ });
1687
+ chainFlagged = true;
1688
+ }
1689
+ }
1690
+ const refOnly = /^\$(?:form|meta|item)(?:\.[\w?]+)*$/;
1691
+ const refBeforeBool = /\$(?:form|meta|item)(?:\.[\w?]+)*\s*(?:&&|\|\||\?(?![.?]))/;
1692
+ const refAfterBool = /(?:&&|\|\|)\s*\$(?:form|meta|item)(?:\.[\w?]+)*\s*$/;
1693
+ if (refOnly.test(trimmed) || refBeforeBool.test(trimmed) || refAfterBool.test(trimmed)) {
1694
+ out.push({
1695
+ path,
1696
+ expression: expr,
1697
+ message: "Expression uses `$form`/`$meta` directly as a boolean (relies on truthy/falsy coercion).",
1698
+ suggestion: 'Form data values can be `undefined`. Compare explicitly: `$form.x !== undefined`, `$form.x === "value"`, `$form.items?.length > 0`. For default values use nullish coalescing: `$form.x ?? defaultValue`.'
1699
+ });
1700
+ }
1701
+ const refForCmpRe = /\$(?:form|meta|item)(?:\.[\w?]+)+/g;
1702
+ let r5Flagged = false;
1703
+ let cmpMatch;
1704
+ while ((cmpMatch = refForCmpRe.exec(trimmed)) !== null) {
1705
+ const start = cmpMatch.index;
1706
+ const end = start + cmpMatch[0].length;
1707
+ const before = trimmed.slice(0, start).trimEnd();
1708
+ const after = trimmed.slice(end).trimStart();
1709
+ const opAfter = /^(?:<=?|>=?|[+\-*/%])(?!=)/.test(after);
1710
+ const opBefore = /(?<![=!])[<>+\-*/%]$/.test(before);
1711
+ if (!(opAfter || opBefore)) continue;
1712
+ if (/&&|\|\|/.test(before)) continue;
1713
+ if (!r5Flagged) {
1714
+ out.push({
1715
+ path,
1716
+ expression: expr,
1717
+ message: "Expression applies a comparison or arithmetic operator to a `$form`/`$meta` reference whose leaf may be `undefined`.",
1718
+ suggestion: "Guard the value first: `$form.x !== undefined && $form.x > 180`. Or default it: `($form.x ?? 0) > 180`. Strict equality (`$form.x === 180`) is also safe since it evaluates to `false` when undefined."
1719
+ });
1720
+ r5Flagged = true;
1721
+ }
1722
+ }
1723
+ }
1724
+ function checkBooleanValidatorRules(validator, path) {
1725
+ const findings = [];
1726
+ const requiredIsTrue = validator.required === true;
1727
+ const constPresent = "const" in validator && validator.const !== void 0;
1728
+ if (requiredIsTrue && !constPresent) {
1729
+ findings.push({
1730
+ path,
1731
+ message: "Boolean validator has `required: true` but no `const` — this does NOT force the checkbox to be checked: `false` is a valid boolean and passes; `required` only rejects a missing value (`undefined`/`null`).",
1732
+ suggestion: "If this checkbox must be checked (e.g. terms acceptance), add `const: true` and set `messages.invalid` and `messages.const` to the same user-facing text. If a false value is genuinely acceptable, ignore this warning."
1733
+ });
1734
+ }
1735
+ if (constPresent && !requiredIsTrue) {
1736
+ findings.push({
1737
+ path,
1738
+ message: "Boolean validator has `const` but no `required: true` — the pristine value passes: a never-touched checkbox holds `undefined`, and non-required validators skip validation entirely for `undefined`.",
1739
+ suggestion: "Add `required: true` so the untouched state fails too, and set `messages.invalid` and `messages.const` to the same user-facing text."
1740
+ });
1741
+ }
1742
+ return findings;
1743
+ }
1744
+ function lintBooleanValidators(formDefinition) {
1745
+ const findings = [];
1746
+ walk$1(formDefinition, "", findings);
1747
+ return findings;
1748
+ }
1749
+ function walk$1(node, path, out) {
1750
+ if (node === null || typeof node !== "object") return;
1751
+ if (Array.isArray(node)) {
1752
+ node.forEach((item, i) => walk$1(item, `${path}/${i}`, out));
1753
+ return;
1754
+ }
1755
+ const obj = node;
1756
+ for (const [key, value] of Object.entries(obj)) {
1757
+ if ((key === "validator" || key.startsWith("validator.")) && value !== null && typeof value === "object" && !Array.isArray(value) && value["type"] === "boolean") {
1758
+ out.push(...checkBooleanValidatorRules(value, `${path}/${key}`));
1759
+ }
1760
+ walk$1(value, `${path}/${key}`, out);
1761
+ }
1762
+ }
1763
+ function lintStringInterpolations(formDefinition) {
1764
+ const findings = [];
1765
+ walk(formDefinition, "", findings, false, false);
1766
+ return findings;
1767
+ }
1768
+ const SLOT_REGEX = /\{\{([^}]*(?:\}[^}]+)*)\}\}/g;
1769
+ function walk(node, path, out, inTemplate, propsOfRepeater) {
1770
+ if (node === null || typeof node !== "object") {
1771
+ return;
1772
+ }
1773
+ if (Array.isArray(node)) {
1774
+ node.forEach((item, i) => walk(item, `${path}/${i}`, out, inTemplate, false));
1775
+ return;
1776
+ }
1777
+ const obj = node;
1778
+ const isTranslationConfig = typeof obj["key"] === "string" && obj["params"] !== null && typeof obj["params"] === "object" && !Array.isArray(obj["params"]);
1779
+ if (isTranslationConfig) {
1780
+ const params = obj["params"];
1781
+ for (const [paramKey, paramValue] of Object.entries(params)) {
1782
+ if (typeof paramValue === "string") {
1783
+ checkParamExpression(paramValue, `${path}/params/${paramKey}`, out);
1784
+ }
1785
+ }
1786
+ }
1787
+ for (const [key, value] of Object.entries(obj)) {
1788
+ if (key === "params" && isTranslationConfig) {
1789
+ continue;
1790
+ }
1791
+ if (key === "defaultValue" || key.startsWith("defaultValue.")) {
1792
+ continue;
1793
+ }
1794
+ const childPath = `${path}/${key}`;
1795
+ if (typeof value === "string") {
1796
+ checkTemplate(value, childPath, out, inTemplate);
1797
+ } else {
1798
+ const childInTemplate = inTemplate || propsOfRepeater && key === "template";
1799
+ walk(value, childPath, out, childInTemplate, obj["type"] === "repeater" && key === "props");
1800
+ }
1801
+ }
1802
+ }
1803
+ function checkParamExpression(value, path, out) {
1804
+ if (value.includes("{{") || value.includes("}}")) {
1805
+ out.push({
1806
+ path,
1807
+ slot: value,
1808
+ message: "i18n param expression should not use `{{` / `}}` delimiters.",
1809
+ suggestion: 'Use a bare expression: `"$form.fieldName"` not `"{{$form.fieldName}}"`.'
1810
+ });
1811
+ return;
1812
+ }
1813
+ if (value.startsWith("$") && /(?<![=!<>])=(?![=>])/.test(value)) {
1814
+ out.push({
1815
+ path,
1816
+ slot: value,
1817
+ message: "i18n param expression contains a single `=` (assignment).",
1818
+ suggestion: "Param expressions are read-only. Did you mean `===` for equality?"
1819
+ });
1820
+ }
1821
+ }
1822
+ function checkTemplate(value, path, out, inTemplate) {
1823
+ const openCount = (value.match(/\{\{/g) ?? []).length;
1824
+ const closeCount = (value.match(/\}\}/g) ?? []).length;
1825
+ if (openCount !== closeCount) {
1826
+ out.push({
1827
+ path,
1828
+ slot: value,
1829
+ message: "String template has unbalanced `{{` / `}}` delimiters.",
1830
+ suggestion: "Every `{{` must have a matching `}}`."
1831
+ });
1832
+ return;
1833
+ }
1834
+ if (openCount === 0) return;
1835
+ let match;
1836
+ SLOT_REGEX.lastIndex = 0;
1837
+ while ((match = SLOT_REGEX.exec(value)) !== null) {
1838
+ const slot = match[0];
1839
+ const expr = match[1];
1840
+ checkSlot(expr, slot, path, out, inTemplate);
1841
+ }
1842
+ }
1843
+ function checkSlot(expr, slot, path, out, inTemplate) {
1844
+ const trimmed = expr.trim();
1845
+ if (!trimmed) {
1846
+ out.push({
1847
+ path,
1848
+ slot,
1849
+ message: "String interpolation slot is empty.",
1850
+ suggestion: "Add an expression, e.g. `{{$form.fieldName}}`."
1851
+ });
1852
+ return;
1853
+ }
1854
+ if (trimmed.includes("{{")) {
1855
+ out.push({
1856
+ path,
1857
+ slot,
1858
+ message: "Interpolation slot contains nested `{{`.",
1859
+ suggestion: "Slots cannot be nested. Check for a copy-paste error."
1860
+ });
1861
+ return;
1862
+ }
1863
+ const referencesItemScope = /\$item\b|\$index\b/.test(trimmed);
1864
+ const hasGlobalRoot = /\$form\b|\$meta\b|\$errors\b|\$formIsInvalid\b|\$fn\b/.test(trimmed);
1865
+ if (referencesItemScope && !inTemplate) {
1866
+ out.push({
1867
+ path,
1868
+ slot,
1869
+ message: "Interpolation slot references `$item` or `$index`, which are only available inside a repeater `props.template`.",
1870
+ suggestion: "Move the widget inside the repeater template, or read the data through `$form` (e.g. `$form.lineItems?.[0]?.quantity`)."
1871
+ });
1872
+ } else if (!hasGlobalRoot && !(inTemplate && referencesItemScope)) {
1873
+ out.push({
1874
+ path,
1875
+ slot,
1876
+ message: "Interpolation slot does not reference `$form`, `$meta`, `$errors`, `$formIsInvalid`, or `$fn`.",
1877
+ suggestion: "GolemUI template slots read data via `$form.fieldName`, metadata via `$meta.key`, validation errors via `$errors.fieldName`, or the built-in `$formIsInvalid` boolean. Host-provided pure functions are callable via `$fn.functionName(...)` when the host passes a `functions` map in the form init config. Inside a repeater `props.template` the current item is available via `$item` and its position via `$index`."
1878
+ });
1879
+ }
1880
+ if (/(?<![=!<>])=(?![=>])/.test(trimmed)) {
1881
+ out.push({
1882
+ path,
1883
+ slot,
1884
+ message: "Interpolation slot contains a single `=` (assignment).",
1885
+ suggestion: "Template slots are read-only. Did you mean `===` for equality?"
1886
+ });
1887
+ }
1888
+ }
1889
+ function validateFormDefinition(input) {
1890
+ const validate = getFormValidator();
1891
+ const ajvOk = validate(input.formDefinition);
1892
+ const { errors, warnings } = formatAjvErrors(validate.errors, input.formDefinition);
1893
+ const expressionWarnings = lintReactiveExpressions(input.formDefinition);
1894
+ const interpolationWarnings = lintStringInterpolations(input.formDefinition);
1895
+ if (!ajvOk && errors.length === 0) {
1896
+ errors.push({
1897
+ path: "/",
1898
+ keyword: "oneOf",
1899
+ message: "Form failed schema validation but no specific error could be localized. The form may contain a widget at a position the form schema does not allow, or a structural shape that our targeted validator missed. Verify each widget against its `json_get_widget_spec` entry."
1900
+ });
1901
+ }
1902
+ const booleanValidatorWarnings = lintBooleanValidators(input.formDefinition).map(
1903
+ (f) => ({
1904
+ path: f.path,
1905
+ message: f.message,
1906
+ suggestion: f.suggestion,
1907
+ keyword: "booleanValidator"
1908
+ })
1909
+ );
1910
+ return {
1911
+ valid: errors.length === 0,
1912
+ errors,
1913
+ warnings: [...warnings, ...booleanValidatorWarnings],
1914
+ expressionWarnings,
1915
+ interpolationWarnings
1916
+ };
1917
+ }
1918
+ const JSON_VALIDATE_FORM_DEFINITION_TOOL = {
1919
+ name: "json_validate_form_definition",
1920
+ description: 'Validate a GolemUI form definition against the bundled JSON Schemas. Use this AFTER generating or modifying a form definition to guarantee it is correct before the user pastes it into their codebase. Returns `{ valid, errors, warnings, expressionWarnings, interpolationWarnings }`. Hard mistakes (typos in widget `type`, missing required props, invalid validator shapes) show up in `errors` and flip `valid` to false. A chunk reference (`{"$ref": "./x.form-chunk.json"}`) is a legal widget entry and is accepted anywhere a widget can appear. Likely-custom widgets (a `type` value that isn\'t a built-in and isn\'t close to one) and semantic validator traps (a boolean validator with only half of the `required: true` + `const: true` pair — it will not force a mandatory checkbox to be checked) show up in `warnings` instead — they don\'t affect `valid`, but surface them and apply their `suggestion`. A custom widget still has to carry the fields its `kind` requires (`input` needs `path`, `layout` needs `children`), so a malformed one produces errors alongside its warning. Reactive expressions (`include.when`, `disabled.when`, etc.) are linted separately into `expressionWarnings`. String interpolation templates (`{{$form.x}}`, `{{$meta.y}}`, expressions like `{{$form.count + 1}}`, etc.) in widget props, and bare expressions inside i18n `params` objects, are linted into `interpolationWarnings`.',
1921
+ inputSchema: {
1922
+ type: "object",
1923
+ properties: {
1924
+ formDefinition: {
1925
+ type: "object",
1926
+ additionalProperties: true,
1927
+ description: "The full GolemUI form definition object, shaped as `{ form: [...widgets], states?: {...} }`. Pass the JSON object, not a stringified version."
1928
+ }
1929
+ },
1930
+ required: ["formDefinition"]
1931
+ }
1932
+ };
1933
+ const FORM_SCHEMA_URL = "https://golemui.com/schemas/form.schema.json";
1934
+ const SUPPORTED_STRING_FORMATS = /* @__PURE__ */ new Set([
1935
+ "email",
1936
+ "hostname",
1937
+ "ipv4",
1938
+ "ipv6",
1939
+ "url",
1940
+ "uuid",
1941
+ "date",
1942
+ "time",
1943
+ "date-time",
1944
+ "duration"
1945
+ ]);
1946
+ function buildStringValidator(s, required2) {
1947
+ const v = { type: "string" };
1948
+ let used = false;
1949
+ if (required2) {
1950
+ v.required = true;
1951
+ used = true;
1952
+ }
1953
+ if (typeof s.minLength === "number") {
1954
+ v.minLength = s.minLength;
1955
+ used = true;
1956
+ }
1957
+ if (typeof s.maxLength === "number") {
1958
+ v.maxLength = s.maxLength;
1959
+ used = true;
1960
+ }
1961
+ if (typeof s.pattern === "string") {
1962
+ v.pattern = s.pattern;
1963
+ used = true;
1964
+ }
1965
+ if (typeof s.format === "string" && SUPPORTED_STRING_FORMATS.has(s.format)) {
1966
+ if (s.format !== "date" && s.format !== "date-time") {
1967
+ v.format = s.format;
1968
+ used = true;
1969
+ }
1970
+ }
1971
+ if (s.const !== void 0) {
1972
+ v.const = s.const;
1973
+ used = true;
1974
+ }
1975
+ if (Array.isArray(s.enum)) {
1976
+ v.enum = s.enum;
1977
+ used = true;
1978
+ }
1979
+ return used ? v : void 0;
1980
+ }
1981
+ function buildNumberValidator(s, required2, t) {
1982
+ const v = { type: t };
1983
+ let used = false;
1984
+ if (required2) {
1985
+ v.required = true;
1986
+ used = true;
1987
+ }
1988
+ if (typeof s.minimum === "number") {
1989
+ v.minimum = s.minimum;
1990
+ used = true;
1991
+ }
1992
+ if (typeof s.maximum === "number") {
1993
+ v.maximum = s.maximum;
1994
+ used = true;
1995
+ }
1996
+ if (typeof s.exclusiveMinimum === "number") {
1997
+ v.exclusiveMinimum = s.exclusiveMinimum;
1998
+ used = true;
1999
+ }
2000
+ if (typeof s.exclusiveMaximum === "number") {
2001
+ v.exclusiveMaximum = s.exclusiveMaximum;
2002
+ used = true;
2003
+ }
2004
+ if (typeof s.multipleOf === "number") {
2005
+ v.multipleOf = s.multipleOf;
2006
+ used = true;
2007
+ }
2008
+ return used ? v : void 0;
2009
+ }
2010
+ function buildBooleanValidator(s, required2) {
2011
+ const v = { type: "boolean" };
2012
+ let used = false;
2013
+ if (required2) {
2014
+ v.required = true;
2015
+ used = true;
2016
+ }
2017
+ if (s.const !== void 0) {
2018
+ v.const = s.const;
2019
+ used = true;
2020
+ }
2021
+ return used ? v : void 0;
2022
+ }
2023
+ const SECRET_HINTS = /(password|secret|api[_-]?key|token)/i;
2024
+ const LONG_TEXT_MIN_LENGTH = 200;
2025
+ const SELECT_THRESHOLD = 6;
2026
+ function jsonSchemaToGui(schema, opts = {}) {
2027
+ const unmapped = [];
2028
+ const root = unwrap(schema);
2029
+ const fields = [];
2030
+ if (root.type === "object" || root.properties) {
2031
+ const required2 = new Set(root.required ?? []);
2032
+ for (const [name, propSchema] of Object.entries(root.properties ?? {})) {
2033
+ const widget = mapProperty(name, unwrap(propSchema), required2.has(name), "", unmapped);
2034
+ if (widget) fields.push(widget);
2035
+ }
2036
+ } else {
2037
+ unmapped.push({
2038
+ path: "",
2039
+ reason: "Top-level JSON Schema is not an object — only object schemas map to forms."
2040
+ });
2041
+ }
2042
+ if (opts.submitAction !== false) {
2043
+ fields.push({
2044
+ kind: "action",
2045
+ type: "button",
2046
+ actionType: "submit",
2047
+ label: opts.submitLabel ?? "Submit",
2048
+ props: { variant: "filled" }
2049
+ });
2050
+ }
2051
+ const wrapped = opts.layout && opts.layout !== "vertical" ? [
2052
+ {
2053
+ kind: "layout",
2054
+ type: opts.layout === "grid" ? "grid" : "flex",
2055
+ props: opts.layout === "grid" ? { columnGap: 12, rowGap: 12 } : { direction: "row", gap: 12 },
2056
+ children: fields
2057
+ }
2058
+ ] : fields;
2059
+ return {
2060
+ formDefinition: { $schema: FORM_SCHEMA_URL, form: wrapped },
2061
+ unmapped
2062
+ };
2063
+ }
2064
+ function unwrap(schema) {
2065
+ if (schema.oneOf?.length === 2) {
2066
+ const nonNull = schema.oneOf.find((s) => s.type !== "null");
2067
+ if (nonNull) return { ...nonNull, ...stripBranches(schema) };
2068
+ }
2069
+ if (schema.anyOf?.length === 2) {
2070
+ const nonNull = schema.anyOf.find((s) => s.type !== "null");
2071
+ if (nonNull) return { ...nonNull, ...stripBranches(schema) };
2072
+ }
2073
+ return schema;
2074
+ }
2075
+ function stripBranches(s) {
2076
+ const { oneOf: oneOf2, anyOf, ...rest } = s;
2077
+ return rest;
2078
+ }
2079
+ function mapProperty(name, schema, required2, parentPath, unmapped) {
2080
+ const path = parentPath ? `${parentPath}.${name}` : name;
2081
+ const label = humanLabel(schema.title ?? name);
2082
+ const t = Array.isArray(schema.type) ? schema.type.find((x) => x !== "null") : schema.type;
2083
+ if (Array.isArray(schema.enum) && schema.enum.every((v) => typeof v === "string")) {
2084
+ return buildEnumField(path, name, label, schema, required2);
2085
+ }
2086
+ switch (t) {
2087
+ case "string":
2088
+ return buildStringField(path, name, label, schema, required2);
2089
+ case "number":
2090
+ case "integer":
2091
+ return buildNumberField(path, label, schema, required2, t);
2092
+ case "boolean":
2093
+ return buildBooleanField(path, label, schema, required2);
2094
+ case "object":
2095
+ return buildObjectGroup(path, name, label, schema, unmapped);
2096
+ case "array":
2097
+ return buildArrayField(path, name, label, schema, required2, unmapped);
2098
+ default:
2099
+ unmapped.push({
2100
+ path,
2101
+ reason: `Unsupported JSON Schema type \`${schema.type ?? "undefined"}\`.`
2102
+ });
2103
+ return null;
2104
+ }
2105
+ }
2106
+ function buildStringField(path, name, label, schema, required2) {
2107
+ const validator = buildStringValidator(schema, required2);
2108
+ const isSecret = SECRET_HINTS.test(name);
2109
+ const isLong = (schema.maxLength ?? 0) >= LONG_TEXT_MIN_LENGTH;
2110
+ if (schema.format === "date") {
2111
+ return cleanFields({ kind: "input", type: "dateInput", path, label, validator });
2112
+ }
2113
+ if (schema.format === "date-time") {
2114
+ return cleanFields({ kind: "input", type: "datePicker", path, label, validator });
2115
+ }
2116
+ if (isSecret) {
2117
+ return cleanFields({ kind: "input", type: "password", path, label, validator });
2118
+ }
2119
+ if (isLong) {
2120
+ return cleanFields({
2121
+ kind: "input",
2122
+ type: "textarea",
2123
+ path,
2124
+ label,
2125
+ validator,
2126
+ props: schema.description ? { hint: schema.description } : void 0
2127
+ });
2128
+ }
2129
+ return cleanFields({
2130
+ kind: "input",
2131
+ type: "textinput",
2132
+ path,
2133
+ label,
2134
+ validator,
2135
+ props: schema.description ? { hint: schema.description } : void 0
2136
+ });
2137
+ }
2138
+ function buildEnumField(path, name, label, schema, required2) {
2139
+ const values = schema.enum ?? [];
2140
+ const validator = required2 ? { type: "string", required: true, enum: values } : { type: "string", enum: values };
2141
+ if (values.length <= SELECT_THRESHOLD) {
2142
+ return cleanFields({
2143
+ kind: "input",
2144
+ type: "select",
2145
+ path,
2146
+ label,
2147
+ validator,
2148
+ props: {
2149
+ options: values.map((v) => ({ label: humanLabel(v), value: v }))
2150
+ }
2151
+ });
2152
+ }
2153
+ return cleanFields({
2154
+ kind: "input",
2155
+ type: "dropdown",
2156
+ path,
2157
+ label,
2158
+ validator,
2159
+ props: {
2160
+ labelField: "label",
2161
+ valueField: "value",
2162
+ items: values.map((v) => ({ label: humanLabel(v), value: v }))
2163
+ }
2164
+ });
2165
+ }
2166
+ function buildNumberField(path, label, schema, required2, t) {
2167
+ const validator = buildNumberValidator(schema, required2, t);
2168
+ return cleanFields({
2169
+ kind: "input",
2170
+ type: "number",
2171
+ path,
2172
+ label,
2173
+ validator,
2174
+ props: schema.description ? { hint: schema.description } : void 0
2175
+ });
2176
+ }
2177
+ function buildBooleanField(path, label, schema, required2) {
2178
+ const validator = buildBooleanValidator(schema, required2);
2179
+ return cleanFields({ kind: "input", type: "checkbox", path, label, validator });
2180
+ }
2181
+ function buildObjectGroup(path, _name, _label, schema, unmapped) {
2182
+ const required2 = new Set(schema.required ?? []);
2183
+ const children = [];
2184
+ for (const [childName, childSchema] of Object.entries(schema.properties ?? {})) {
2185
+ const w = mapProperty(childName, unwrap(childSchema), required2.has(childName), path, unmapped);
2186
+ if (w) children.push(w);
2187
+ }
2188
+ if (!children.length) {
2189
+ unmapped.push({ path, reason: "Object has no mappable properties." });
2190
+ return null;
2191
+ }
2192
+ return {
2193
+ kind: "layout",
2194
+ type: "flex",
2195
+ props: { direction: "column", gap: 8 },
2196
+ children
2197
+ };
2198
+ }
2199
+ function buildArrayField(path, _name, label, schema, required2, unmapped) {
2200
+ const items = schema.items ? unwrap(schema.items) : void 0;
2201
+ if (!items) {
2202
+ unmapped.push({ path, reason: "Array without `items` schema cannot be mapped." });
2203
+ return null;
2204
+ }
2205
+ if (items.type === "object") {
2206
+ const templateChildren = [];
2207
+ const required22 = new Set(items.required ?? []);
2208
+ const childParent = `${path}.items`;
2209
+ for (const [childName, childSchema] of Object.entries(items.properties ?? {})) {
2210
+ const w = mapProperty(
2211
+ childName,
2212
+ unwrap(childSchema),
2213
+ required22.has(childName),
2214
+ childParent,
2215
+ unmapped
2216
+ );
2217
+ if (w) templateChildren.push(w);
2218
+ }
2219
+ if (!templateChildren.length) {
2220
+ unmapped.push({ path, reason: "Array of objects has no mappable item properties." });
2221
+ return null;
2222
+ }
2223
+ return {
2224
+ kind: "input",
2225
+ type: "repeater",
2226
+ path,
2227
+ label,
2228
+ props: {
2229
+ addLabel: `Add ${singular(label).toLowerCase()}`,
2230
+ removeLabel: "Remove",
2231
+ template: {
2232
+ kind: "layout",
2233
+ type: "flex",
2234
+ props: { direction: "column", gap: 8 },
2235
+ children: templateChildren
2236
+ }
2237
+ }
2238
+ };
2239
+ }
2240
+ if (items.type === "string" || items.type === "number" || items.type === "integer") {
2241
+ const validator = buildArrayValidator(schema, required2);
2242
+ return cleanFields({
2243
+ kind: "input",
2244
+ type: "tags",
2245
+ path,
2246
+ label,
2247
+ validator,
2248
+ props: schema.description ? { placeholder: "Add and press Enter", hint: schema.description } : { placeholder: "Add and press Enter" }
2249
+ });
2250
+ }
2251
+ unmapped.push({
2252
+ path,
2253
+ reason: "Array shape is not mappable (only arrays of objects → repeater, or arrays of strings/numbers → tags)."
2254
+ });
2255
+ return null;
2256
+ }
2257
+ function buildArrayValidator(s, required2) {
2258
+ const v = { type: "array" };
2259
+ let used = false;
2260
+ if (required2) {
2261
+ v.required = true;
2262
+ used = true;
2263
+ }
2264
+ if (typeof s.minItems === "number") {
2265
+ v.minItems = s.minItems;
2266
+ used = true;
2267
+ }
2268
+ if (typeof s.maxItems === "number") {
2269
+ v.maxItems = s.maxItems;
2270
+ used = true;
2271
+ }
2272
+ if (s.uniqueItems === true) {
2273
+ v.uniqueItems = true;
2274
+ used = true;
2275
+ }
2276
+ return used ? v : void 0;
2277
+ }
2278
+ function humanLabel(name) {
2279
+ if (!name) return "";
2280
+ return name.replace(/[_-]+/g, " ").replace(/([a-z0-9])([A-Z])/g, "$1 $2").replace(/\s+/g, " ").trim().replace(/^./, (c) => c.toUpperCase());
2281
+ }
2282
+ function singular(label) {
2283
+ if (label.endsWith("ies") && label.length > 3) return label.slice(0, -3) + "y";
2284
+ if (label.endsWith("s") && !label.endsWith("ss")) return label.slice(0, -1);
2285
+ return label;
2286
+ }
2287
+ function cleanFields(o) {
2288
+ for (const k of Object.keys(o)) {
2289
+ if (o[k] === void 0) delete o[k];
2290
+ }
2291
+ return o;
2292
+ }
2293
+ function generateFromJsonSchema(input) {
2294
+ const opts = {
2295
+ submitAction: input.submitAction,
2296
+ submitLabel: input.submitLabel,
2297
+ layout: input.layout
2298
+ };
2299
+ const { formDefinition, unmapped } = jsonSchemaToGui(input.jsonSchema, opts);
2300
+ const validation = validateFormDefinition({ formDefinition });
2301
+ return { formDefinition, unmapped, validation };
2302
+ }
2303
+ const JSON_GENERATE_FROM_SCHEMA_TOOL = {
2304
+ name: "json_generate_from_schema",
2305
+ description: "Generate a GolemUI form definition from a JSON Schema describing the form data shape (typically an API request body or a Zod-derived schema). The result is validated against the GolemUI JSON Schemas before being returned, so it is guaranteed to be syntactically correct. Anything the mapper cannot handle is reported in `unmapped` rather than silently dropped — use that list to surface remaining work to the user.",
2306
+ inputSchema: {
2307
+ type: "object",
2308
+ properties: {
2309
+ jsonSchema: {
2310
+ type: "object",
2311
+ additionalProperties: true,
2312
+ description: "A standard JSON Schema. The top level must be an `object` schema with a `properties` map. Supports primitive types (string/number/integer/boolean) with formats and constraints, enums, nested objects, and arrays of objects (rendered as repeaters)."
2313
+ },
2314
+ submitAction: {
2315
+ type: "boolean",
2316
+ description: "Append a submit button. Defaults to true."
2317
+ },
2318
+ submitLabel: {
2319
+ type: "string",
2320
+ description: 'Label for the submit button when `submitAction` is true. Defaults to "Submit".'
2321
+ },
2322
+ layout: {
2323
+ type: "string",
2324
+ enum: ["vertical", "horizontal", "grid"],
2325
+ description: "Top-level layout. Defaults to vertical (one field per row)."
2326
+ }
2327
+ },
2328
+ required: ["jsonSchema"]
2329
+ }
2330
+ };
2331
+ const METHODS = ["get", "post", "put", "patch", "delete"];
2332
+ async function generateFromOpenapi(input) {
2333
+ if (!input.document && !input.documentUrl) {
2334
+ throw new Error("Provide either `document` (parsed OpenAPI object) or `documentUrl`.");
2335
+ }
2336
+ const doc = input.document ?? await fetchDoc(input.documentUrl);
2337
+ const resolved = findOperation(doc, input.operation);
2338
+ if (!resolved) {
2339
+ throw new Error(
2340
+ `Operation \`${input.operation}\` not found. Use the form "METHOD /path" (e.g. "POST /users") or an exact operationId.`
2341
+ );
2342
+ }
2343
+ const { method, path, operation } = resolved;
2344
+ let bodySchema = operation.requestBody?.content?.["application/json"]?.schema;
2345
+ if (bodySchema) bodySchema = derefSchema(bodySchema, doc);
2346
+ let assembled;
2347
+ if (bodySchema && (bodySchema.type === "object" || bodySchema.properties)) {
2348
+ assembled = bodySchema;
2349
+ } else if (operation.parameters?.length) {
2350
+ assembled = paramsToSchema(operation.parameters, doc);
2351
+ } else {
2352
+ throw new Error(
2353
+ `Operation \`${method.toUpperCase()} ${path}\` has no JSON request body and no parameters — nothing to render as a form.`
2354
+ );
2355
+ }
2356
+ const { formDefinition, unmapped } = jsonSchemaToGui(assembled, {
2357
+ submitAction: input.submitAction ?? true,
2358
+ submitLabel: input.submitLabel ?? defaultSubmitLabel(method, operation)
2359
+ });
2360
+ const validation = validateFormDefinition({ formDefinition });
2361
+ return {
2362
+ resolvedOperation: { method: method.toUpperCase(), path, operationId: operation.operationId },
2363
+ formDefinition,
2364
+ unmapped,
2365
+ validation
2366
+ };
2367
+ }
2368
+ async function fetchDoc(url) {
2369
+ const res = await fetch(url);
2370
+ if (!res.ok) {
2371
+ throw new Error(
2372
+ `Failed to fetch OpenAPI document from ${url}: ${res.status} ${res.statusText}`
2373
+ );
2374
+ }
2375
+ const text = await res.text();
2376
+ try {
2377
+ return JSON.parse(text);
2378
+ } catch {
2379
+ throw new Error(
2380
+ `Document at ${url} is not JSON. v1 only supports JSON OpenAPI docs — convert YAML before passing.`
2381
+ );
2382
+ }
2383
+ }
2384
+ function findOperation(doc, ref) {
2385
+ const trimmed = ref.trim();
2386
+ const methodPathMatch = trimmed.match(/^([A-Za-z]+)\s+(\/\S*)$/);
2387
+ if (methodPathMatch) {
2388
+ const method = methodPathMatch[1].toLowerCase();
2389
+ const path = methodPathMatch[2];
2390
+ if (!METHODS.includes(method)) {
2391
+ throw new Error(`Unsupported HTTP method \`${method.toUpperCase()}\`.`);
2392
+ }
2393
+ const op = doc.paths?.[path]?.[method];
2394
+ if (op) return { method, path, operation: op };
2395
+ return null;
2396
+ }
2397
+ for (const [path, methods] of Object.entries(doc.paths ?? {})) {
2398
+ for (const [method, op] of Object.entries(methods)) {
2399
+ if (METHODS.includes(method) && op.operationId === trimmed) {
2400
+ return { method, path, operation: op };
2401
+ }
2402
+ }
2403
+ }
2404
+ return null;
2405
+ }
2406
+ function paramsToSchema(parameters, doc) {
2407
+ const properties2 = {};
2408
+ const required2 = [];
2409
+ for (const p of parameters) {
2410
+ const s = p.schema ? derefSchema(p.schema, doc) : { type: "string" };
2411
+ properties2[p.name] = { ...s, description: p.description ?? s.description };
2412
+ if (p.required) required2.push(p.name);
2413
+ }
2414
+ return { type: "object", properties: properties2, required: required2 };
2415
+ }
2416
+ function defaultSubmitLabel(method, op) {
2417
+ if (op.summary) return op.summary;
2418
+ const verbs = {
2419
+ post: "Create",
2420
+ put: "Update",
2421
+ patch: "Update",
2422
+ delete: "Delete",
2423
+ get: "Submit"
2424
+ };
2425
+ return verbs[method.toLowerCase()] ?? "Submit";
2426
+ }
2427
+ function derefSchema(schema, doc, depth = 0) {
2428
+ if (depth > 16) return schema;
2429
+ if (typeof schema.$ref === "string") {
2430
+ const target = resolveLocalRef(schema.$ref, doc);
2431
+ if (target) return derefSchema(target, doc, depth + 1);
2432
+ return schema;
2433
+ }
2434
+ const result = { ...schema };
2435
+ if (result.properties) {
2436
+ result.properties = Object.fromEntries(
2437
+ Object.entries(result.properties).map(([k, v]) => [k, derefSchema(v, doc, depth + 1)])
2438
+ );
2439
+ }
2440
+ if (result.items) result.items = derefSchema(result.items, doc, depth + 1);
2441
+ if (result.oneOf) result.oneOf = result.oneOf.map((s) => derefSchema(s, doc, depth + 1));
2442
+ if (result.anyOf) result.anyOf = result.anyOf.map((s) => derefSchema(s, doc, depth + 1));
2443
+ return result;
2444
+ }
2445
+ function resolveLocalRef(ref, doc) {
2446
+ if (!ref.startsWith("#/")) return null;
2447
+ const parts = ref.slice(2).split("/");
2448
+ let cur = doc;
2449
+ for (const p of parts) {
2450
+ if (cur && typeof cur === "object") {
2451
+ cur = cur[p];
2452
+ } else {
2453
+ return null;
2454
+ }
2455
+ }
2456
+ return cur ?? null;
2457
+ }
2458
+ const JSON_GENERATE_FROM_OPENAPI_TOOL = {
2459
+ name: "json_generate_from_openapi",
2460
+ description: 'Generate a GolemUI form for a specific OpenAPI 3.x operation (e.g. "POST /users"). Resolves the operation\'s JSON request body, dereferences `$ref`s, then maps it to a form definition that is validated against the GolemUI JSON Schemas before being returned, so it is guaranteed syntactically correct. Falls back to operation parameters when no request body is present. Anything the mapper cannot handle is reported in `unmapped` rather than silently dropped — use that list to surface remaining work to the user. Pass either a parsed `document` or a `documentUrl` to fetch.',
2461
+ inputSchema: {
2462
+ type: "object",
2463
+ properties: {
2464
+ documentUrl: {
2465
+ type: "string",
2466
+ description: "URL of a JSON OpenAPI document. Either this or `document` is required."
2467
+ },
2468
+ document: {
2469
+ type: "object",
2470
+ additionalProperties: true,
2471
+ description: "Parsed OpenAPI document (JSON object). Either this or `documentUrl` is required."
2472
+ },
2473
+ operation: {
2474
+ type: "string",
2475
+ description: 'The operation to generate a form for. Either "METHOD /path" (e.g. "POST /users") or an exact operationId.'
2476
+ },
2477
+ submitAction: {
2478
+ type: "boolean",
2479
+ description: "Append a submit button. Defaults to true."
2480
+ },
2481
+ submitLabel: {
2482
+ type: "string",
2483
+ description: "Label for the submit button. Defaults to the operation summary or a verb derived from the HTTP method."
2484
+ }
2485
+ },
2486
+ required: ["operation"]
2487
+ }
2488
+ };
2489
+ const EXAMPLES = {
2490
+ accordion: {
2491
+ kind: "layout",
2492
+ type: "accordion",
2493
+ props: {
2494
+ sections: [
2495
+ { uid: "personal", label: "Personal" },
2496
+ { uid: "preferences", label: "Preferences" }
2497
+ ]
2498
+ },
2499
+ children: [
2500
+ { kind: "input", type: "textinput", path: "firstName", label: "First name" },
2501
+ { kind: "input", type: "checkbox", path: "newsletter", label: "Newsletter" }
2502
+ ]
2503
+ },
2504
+ textinput: {
2505
+ kind: "input",
2506
+ type: "textinput",
2507
+ path: "firstName",
2508
+ label: "First name",
2509
+ validator: { type: "string", required: true, minLength: 1 },
2510
+ props: { placeholder: "Jane" }
2511
+ },
2512
+ textarea: {
2513
+ kind: "input",
2514
+ type: "textarea",
2515
+ path: "bio",
2516
+ label: "Bio",
2517
+ props: { minimumHeight: 120, autoGrow: true }
2518
+ },
2519
+ tags: {
2520
+ kind: "input",
2521
+ type: "tags",
2522
+ path: "keywords",
2523
+ label: "Keywords",
2524
+ defaultValue: [],
2525
+ props: {
2526
+ placeholder: "Add a keyword and press Enter",
2527
+ separators: ["Enter", ","],
2528
+ trim: true,
2529
+ allowDuplicates: false,
2530
+ limit: 10
2531
+ },
2532
+ validator: {
2533
+ type: "array",
2534
+ minItems: 1,
2535
+ maxItems: 10
2536
+ }
2537
+ },
2538
+ password: {
2539
+ kind: "input",
2540
+ type: "password",
2541
+ path: "password",
2542
+ label: "Password",
2543
+ validator: { type: "string", required: true, minLength: 8 }
2544
+ },
2545
+ number: {
2546
+ kind: "input",
2547
+ type: "number",
2548
+ path: "age",
2549
+ label: "Age",
2550
+ validator: { type: "integer", required: true, minimum: 0 }
2551
+ },
2552
+ currency: {
2553
+ kind: "input",
2554
+ type: "currency",
2555
+ path: "salary",
2556
+ label: "Salary",
2557
+ props: { currency: "USD" }
2558
+ },
2559
+ checkbox: {
2560
+ kind: "input",
2561
+ type: "checkbox",
2562
+ path: "termsAccepted",
2563
+ label: "I accept the terms",
2564
+ validator: {
2565
+ type: "boolean",
2566
+ required: true,
2567
+ const: true,
2568
+ messages: {
2569
+ invalid: "You must accept the terms",
2570
+ const: "You must accept the terms"
2571
+ }
2572
+ }
2573
+ },
2574
+ toggle: {
2575
+ kind: "input",
2576
+ type: "toggle",
2577
+ path: "notifications",
2578
+ label: "Email notifications"
2579
+ },
2580
+ dropdown: {
2581
+ kind: "input",
2582
+ type: "dropdown",
2583
+ path: "country",
2584
+ label: "Country",
2585
+ props: {
2586
+ labelField: "label",
2587
+ valueField: "value",
2588
+ items: [
2589
+ { label: "United States", value: "us", flag: "🇺🇸" },
2590
+ { label: "Canada", value: "ca", flag: "🇨🇦" }
2591
+ ]
2592
+ }
2593
+ },
2594
+ select: {
2595
+ kind: "input",
2596
+ type: "select",
2597
+ path: "plan",
2598
+ label: "Plan",
2599
+ props: {
2600
+ options: [
2601
+ { label: "Free", value: "free" },
2602
+ { label: "Pro", value: "pro" }
2603
+ ]
2604
+ }
2605
+ },
2606
+ radiogroup: {
2607
+ kind: "input",
2608
+ type: "radiogroup",
2609
+ path: "shippingSpeed",
2610
+ label: "Shipping",
2611
+ props: {
2612
+ options: [
2613
+ { label: "Standard", value: "standard" },
2614
+ { label: "Express", value: "express" }
2615
+ ]
2616
+ }
2617
+ },
2618
+ dateInput: {
2619
+ kind: "input",
2620
+ type: "dateInput",
2621
+ path: "birthDate",
2622
+ label: "Birth date"
2623
+ },
2624
+ datePicker: {
2625
+ kind: "input",
2626
+ type: "datePicker",
2627
+ path: "startDate",
2628
+ label: "Start date"
2629
+ },
2630
+ calendar: {
2631
+ kind: "input",
2632
+ type: "calendar",
2633
+ path: "eventDate",
2634
+ label: "Event date"
2635
+ },
2636
+ button: {
2637
+ kind: "action",
2638
+ type: "button",
2639
+ actionType: "submit",
2640
+ label: "Submit",
2641
+ props: { variant: "filled" }
2642
+ },
2643
+ alert: {
2644
+ kind: "display",
2645
+ type: "alert",
2646
+ props: { level: "info", text: "Heads up!" }
2647
+ },
2648
+ markdownText: {
2649
+ kind: "display",
2650
+ type: "markdownText",
2651
+ props: { md: "Welcome to the form." }
2652
+ },
2653
+ flex: {
2654
+ kind: "layout",
2655
+ type: "flex",
2656
+ props: { direction: "column", gap: 12 },
2657
+ children: [
2658
+ {
2659
+ kind: "input",
2660
+ type: "textinput",
2661
+ path: "firstName",
2662
+ label: "First name"
2663
+ }
2664
+ ]
2665
+ },
2666
+ grid: {
2667
+ kind: "layout",
2668
+ type: "grid",
2669
+ props: { columnGap: 12, rowGap: 12 },
2670
+ children: [
2671
+ { kind: "input", type: "textinput", path: "firstName", label: "First name" },
2672
+ { kind: "input", type: "textinput", path: "lastName", label: "Last name" }
2673
+ ]
2674
+ },
2675
+ tabs: {
2676
+ kind: "layout",
2677
+ type: "tabs",
2678
+ props: {
2679
+ tabs: [
2680
+ { uid: "personal", label: "Personal" },
2681
+ { uid: "address", label: "Address" }
2682
+ ]
2683
+ },
2684
+ children: [
2685
+ { kind: "input", type: "textinput", path: "firstName", label: "First name" },
2686
+ { kind: "input", type: "textinput", path: "street", label: "Street" }
2687
+ ]
2688
+ },
2689
+ repeater: {
2690
+ kind: "input",
2691
+ type: "repeater",
2692
+ path: "addresses",
2693
+ label: "Addresses",
2694
+ props: {
2695
+ addLabel: "Add address",
2696
+ removeLabel: "Remove",
2697
+ template: {
2698
+ kind: "layout",
2699
+ type: "flex",
2700
+ props: { direction: "column" },
2701
+ children: [
2702
+ // Child paths inside a repeater template MUST be `<repeater.path>.items.<field>` —
2703
+ // `items` is the reserved segment that the runtime expands per array entry.
2704
+ { kind: "input", type: "textinput", path: "addresses.items.street", label: "Street" },
2705
+ { kind: "input", type: "textinput", path: "addresses.items.city", label: "City" }
2706
+ ]
2707
+ }
2708
+ }
2709
+ }
2710
+ };
2711
+ const NOTES = {
2712
+ textinput: [
2713
+ "`path` is the dot-path into form data this field writes to.",
2714
+ "`validator.format` supports: `email`, `hostname`, `ipv4`, `ipv6`, `url`, `uuid`, `date`, `time`, `date-time`, `duration`.",
2715
+ 'Add custom `validator.messages` (per-rule map) on production forms — the library defaults are developer-facing. When `required: true`, ALWAYS also set `messages.invalid` with the same text as `messages.required`: an `undefined`/`null` value (pristine or cleared) fails the base type check and shows the `invalid` message, not the `required` one. Call `get_concept({ concept: "validation" })` for the full explanation.',
2716
+ 'Root props `label`, `disabled`, `readonly`, `validator`, and `size` accept state suffixes — e.g. `"label.<stateName>": "New label"` overrides the label only when that named state is active. Props inside `props` (e.g. `hint`, `placeholder`) also accept suffixes as `"hint.<stateName>"`. Call `get_concept({ concept: "states" })` for the full pattern.',
2717
+ '`props.icon` accepts a Google Material Icons ligature name (e.g. `"search"`, `"email"`, `"lock"`) to display a decorative icon inside the input field. Supports state suffix: `"icon.<stateName>": "check"` to swap the icon when a state is active. Call `get_concept({ concept: "icons" })` for setup and the full list of icon-capable widgets.'
2718
+ ],
2719
+ markdownText: [
2720
+ "Display-only widget for rendering markdown. Can be used as a top-level form widget (inside any layout) or inside templates like `dropdown.props.items[].template`.",
2721
+ "The required prop is `md` (the markdown string), not `text`."
2722
+ ],
2723
+ tags: [
2724
+ "Use `tags` for free-form arrays of primitive values (typically `string[]`) — e.g. keywords, email lists, hashtags. Backing data is `string[]`. For arrays of structured objects, use `repeater` instead.",
2725
+ '`props.separators` controls which keys/characters commit a new tag. Defaults emit on `Enter` and `,`; you can also include `"Tab"` or `"blur"`. `props.trim` strips whitespace from each tag; `props.allowDuplicates: false` rejects repeats; `props.limit` caps the array length.',
2726
+ 'Validate with an `arrayValidator`: `{ type: "array", minItems, maxItems, uniqueItems }`. The `tags` widget complements that with UI-level enforcement (`allowDuplicates`, `limit`) but the validator is still authoritative for form-level required/min/max constraints.'
2727
+ ],
2728
+ dropdown: [
2729
+ "PREFER `select` for plain label/value lists (countries, plans, sizes). `dropdown` is for richer item shapes: when each item has extra fields (icons, flags, metadata) that an `itemRenderer` or `labelField`/`valueField` can use.",
2730
+ '`props.items` is EITHER primitives `["one", 2, ...]` OR arbitrary objects `[{ label, value, ...extras }]`. Pair the object form with `labelField`/`valueField` to tell the dropdown which fields to render as label and which to use as the value. **Widget templates inside items (the `{template, value}` shape) are NOT supported — only `repeater` accepts widget templates.**'
2731
+ ],
2732
+ select: [
2733
+ '`props.options[]` is the simple form: `[{ label: "United States", value: "us" }, ...]`. Use this for ANY plain text list — countries, plans, sizes, status enums. Only switch to `dropdown` if you need custom per-item rendering (icons, flags, rich layouts).',
2734
+ "For very large lists (>50 items) consider `dropdown` for its virtualization (`height`, `itemHeight`, `searchFields`)."
2735
+ ],
2736
+ flex: [
2737
+ "Use `flex` for page scaffolding and directional grouping: a column stack of sections, a row of side-by-side panels, a row of action buttons. For field-level layout (inputs that should sit in columns with aligned labels), prefer `grid` instead.",
2738
+ '`props.direction`: `"row"` (default) | `"column"` | `"row-reverse"` | `"column-reverse"` — controls the main axis. `"column"` stacks children vertically; `"row"` places them side by side.',
2739
+ "`props.gap`: number (pixels) — uniform spacing between all children along the main axis.",
2740
+ '`props.justify`: `"center"` | `"start"` | `"end"` | `"stretch"` — aligns children along the cross-axis (perpendicular to `direction`).',
2741
+ '`props.align`: `"center"` | `"start"` | `"end"` | `"space-between"` | `"space-around"` | `"space-evenly"` — distributes children along the main axis.',
2742
+ 'All `flex` props support state suffixes: `"direction.<stateName>": "column"` swaps the direction when a state is active. Call `get_concept({ concept: "states" })` for the full pattern.'
2743
+ ],
2744
+ grid: [
2745
+ "Use `grid` when you want multiple form fields to sit side by side with their labels and inputs aligned across columns. GolemUI's `grid` uses CSS subgrid internally: each child widget gets two implicit sub-tracks (one for its label, one for its input) that align to the parent grid columns, giving consistent label/input alignment across all rows without manual sizing.",
2746
+ "For loose page scaffolding — stacking sections, wrapping a group in a header — use `flex` instead.",
2747
+ "`props.columnGap`: number (pixels) — horizontal gap between columns.",
2748
+ "`props.rowGap`: number (pixels) — vertical gap between rows.",
2749
+ "`props.autoFit`: boolean — when `true`, the grid auto-fits as many columns as will fit in the available container width, using `columnGap` as the gutter. Useful for responsive layouts where the number of columns should adapt to the viewport.",
2750
+ '`props.direction`: `"row"` | `"column"` — controls how children flow into the grid tracks.',
2751
+ "`props.align` and `props.justify` accept the same values as `flex`.",
2752
+ 'All `grid` props support state suffixes. Call `get_concept({ concept: "states" })` for the full pattern.'
2753
+ ],
2754
+ tabs: [
2755
+ "Children are associated with tabs by **`uid` matching**, not by array order: each direct child must have a `uid` field at the widget level (alongside `kind`/`type`) whose string value equals one of the `props.tabs[].uid` entries. There is no `tag` property — that is not a real GolemUI field.",
2756
+ "Children are typically written in display order for readability, but rearranging them does not change which tab they belong to — only the `uid` string match does."
2757
+ ],
2758
+ accordion: [
2759
+ "Children are associated with sections by **`uid` matching** (same pattern as `tabs`): each direct child must have a `uid` field at the widget level whose value equals one of the `props.sections[].uid` entries. There is no `tag` property.",
2760
+ "`props.defaultOpen` is a map of `{ <sectionUid>: boolean }` controlling which sections start expanded."
2761
+ ],
2762
+ repeater: [
2763
+ "`props.template` must be a layout widget (flex/grid/tabs/accordion) whose children are the per-item fields.",
2764
+ 'Child paths inside the template MUST follow the form `<repeater.path>.items.<fieldName>`. The `items` segment is reserved — the runtime substitutes it with the current array index per row. For example, a repeater at `path: "users"` with a child `firstName` uses `path: "users.items.firstName"`. Plain `firstName` will NOT bind to the array.',
2765
+ 'Nested repeaters chain the convention: a repeater at `path: "teams"` whose template contains a repeater at `path: "teams.items.members"` whose children use `path: "teams.items.members.items.<field>"`.',
2766
+ '`addLabel` supports state suffixes: `"addLabel.<stateName>": "Limit reached"` swaps the add-button label when a named state is active — useful for capping array length. Call `get_concept({ concept: "states" })` for the full pattern.'
2767
+ ],
2768
+ button: [
2769
+ "`actionType` controls the button's role. `actionType: \"submit\"` makes the button fire the form's `formSubmit` event natively — the host listens for it via `(formSubmit)` (Angular), `@formSubmit` (Vue), `onFormSubmit` (React), or the `form-submit` event (Lit). No custom handler needed. Use this for the primary submit button on a form.",
2770
+ '`actionType: "button"` (the default, can be omitted) is a regular action button. Wire it via `on.click: "<handlerName>"` where `<handlerName>` is registered in the form config\'s event handlers.',
2771
+ 'Supports state-suffixed props: `"label.<stateName>"` and `"disabled.<stateName>"` swap the label or disabled state when a named state is active — e.g. disable the submit button until terms are accepted, then re-enable it. Call `get_concept({ concept: "states" })` for the full pattern.',
2772
+ '`props.icon` accepts a Google Material Icons ligature name (e.g. `"send"`, `"check"`, `"arrow_forward"`) to render an icon on the button. `props.iconPosition` controls placement: `"left"` (default) or `"right"`. Both support state suffixes: `"icon.<stateName>": "hourglass_empty"` swaps the icon while a state is active. Call `get_concept({ concept: "icons" })` for setup instructions and the full list of icon-capable widgets.'
2773
+ ],
2774
+ checkbox: [
2775
+ 'MANDATORY CHECKBOX (e.g. terms acceptance): `required: true` alone is a silent trap — it only rejects a MISSING value; an unchecked box holding `false` is a valid boolean and passes. `const: true` is what rejects `false` — but alone it lets the pristine `undefined` pass (non-required validators are optional). Use BOTH: `validator: { type: "boolean", required: true, const: true }`.',
2776
+ 'Set BOTH `messages.invalid` and `messages.const` to the same user-facing text: a never-touched box fails the type check (`invalid` message), a checked-then-unchecked box fails the `const` rule. Call `get_concept({ concept: "validation" })` for the full explanation.'
2777
+ ],
2778
+ alert: [
2779
+ 'Use `include: { in: ["stateName"] }` to show this alert only when a named state is active, or `exclude: { from: ["stateName"] }` to hide it when a state is active. This is cleaner than `include: { when: "..." }` when the same condition is reused across multiple widgets. Call `get_concept({ concept: "states" })` for the full states pattern.',
2780
+ 'Props inside `props` (e.g. `text`, `level`) accept state suffixes: `"text.<stateName>": "New message"` swaps the message when that state is active.'
2781
+ ]
2782
+ };
2783
+ function synthesizeExample(widgetType, schema) {
2784
+ const props = schema["properties"];
2785
+ const kindProp = props?.["kind"]?.const ?? "input";
2786
+ const ex = { kind: kindProp, type: widgetType };
2787
+ if (props?.["path"]) ex["path"] = "field";
2788
+ if (props?.["label"]) ex["label"] = "Field";
2789
+ return ex;
2790
+ }
2791
+ function getWidgetSpec(input) {
2792
+ const schema = COMPONENT_SCHEMAS[input.widgetType];
2793
+ if (!schema) {
2794
+ const known = Object.keys(COMPONENT_SCHEMAS).sort().join(", ");
2795
+ throw new Error(`Unknown widget type \`${input.widgetType}\`. Known: ${known}.`);
2796
+ }
2797
+ const props = schema["properties"];
2798
+ const kindProp = props?.["kind"]?.const ?? "unknown";
2799
+ return {
2800
+ widgetType: input.widgetType,
2801
+ schema,
2802
+ kind: kindProp,
2803
+ example: EXAMPLES[input.widgetType] ?? synthesizeExample(input.widgetType, schema),
2804
+ notes: NOTES[input.widgetType] ?? []
2805
+ };
2806
+ }
2807
+ const JSON_GET_WIDGET_SPEC_TOOL = {
2808
+ name: "json_get_widget_spec",
2809
+ description: "Look up the JSON Schema and a minimal working example for a single GolemUI widget on the **JSON form-definition** surface. Use this when you need to know which `props` a widget accepts, what `kind` value it uses, or what shape its `validator` takes. **If you are writing `gui.*` DX code (TypeScript), you do NOT need this** — use `dx_list_factories` + `dx_get_spec` instead; fetching both surfaces for the same widget is redundant. Cheaper than dumping the whole API into context.",
2810
+ inputSchema: {
2811
+ type: "object",
2812
+ properties: {
2813
+ widgetType: {
2814
+ type: "string",
2815
+ description: "The widget `type` constant. One of: " + Object.keys(COMPONENT_SCHEMAS).sort().map((t) => `\`${t}\``).join(", ") + "."
2816
+ }
2817
+ },
2818
+ required: ["widgetType"]
2819
+ }
2820
+ };
2821
+ const STATES_CONCEPT = {
2822
+ concept: "states",
2823
+ summary: "States are named boolean conditions declared at the form root. Each state name maps to a reactive expression string (using `$form`, `$meta`, `$formIsInvalid`, or `$fn`) that the runtime evaluates continuously as the user interacts with the form. Once declared, state names can gate widget visibility (include / exclude) and swap individual widget properties per-state — a capability unique to named states that has no inline `when` equivalent.",
2824
+ patterns: [
2825
+ {
2826
+ name: "Declare states at the form root",
2827
+ description: 'Add a `"states"` object to the top-level form definition. Each key is a state name; each value is a reactive expression string. Expressions are evaluated at runtime — they have access to `$form` (all current form values), `$meta` (host-supplied metadata), `$formIsInvalid`, and `$fn` (host-provided pure functions). State names can contain letters, numbers, hyphens, and underscores. Colons enable hierarchical composition — see the "Composed sub-states (colon notation)" pattern below.',
2828
+ example: {
2829
+ $schema: FORM_SCHEMA_URL,
2830
+ states: {
2831
+ termsAccepted: "$form.terms === true",
2832
+ hasDiscount: "$form.hasDiscountCode === true",
2833
+ limitReached: "$form.users?.length === 5"
2834
+ },
2835
+ form: ["/* ... widgets ... */"]
2836
+ }
2837
+ },
2838
+ {
2839
+ name: "Composed sub-states (colon notation)",
2840
+ description: 'Colons in a state name denote hierarchy: `"register"`, `"register:adult"`, `"register:minor:tall"`. At runtime the form engine rewrites every child expression by ANDing the full ancestor chain in front of it. This means you write only the *incremental* condition in a child — the parent conditions are inherited automatically. A child state is active only when ALL of its ancestors are also active.',
2841
+ example: {
2842
+ // What you write in the form definition:
2843
+ statesAsAuthored: {
2844
+ register: "$form.agreeTerms === true",
2845
+ "register:adult": "$form.user?.age >= 18",
2846
+ "register:minor": "$form.user?.age < 18",
2847
+ "register:minor:tall": "$form.user?.height > 180"
2848
+ },
2849
+ // What the runtime actually evaluates (expandStateExpressions output):
2850
+ statesAtRuntime: {
2851
+ register: "($form.agreeTerms === true)",
2852
+ "register:adult": "($form.agreeTerms === true) && ($form.user?.age >= 18)",
2853
+ "register:minor": "($form.agreeTerms === true) && ($form.user?.age < 18)",
2854
+ "register:minor:tall": "($form.agreeTerms === true) && ($form.user?.age < 18) && ($form.user?.height > 180)"
2855
+ }
2856
+ }
2857
+ },
2858
+ {
2859
+ name: "Conditional rendering with include / exclude (named-state form)",
2860
+ description: 'Use `"include": { "in": ["stateName"] }` on any widget to render it only when the named state is active. Use `"exclude": { "from": ["stateName"] }` to render it only when the state is NOT active. Both `in` and `from` are arrays — a widget can be gated on multiple states simultaneously.',
2861
+ example: {
2862
+ $schema: FORM_SCHEMA_URL,
2863
+ states: {
2864
+ hasDiscount: "$form.hasDiscountCode === true"
2865
+ },
2866
+ form: [
2867
+ {
2868
+ kind: "input",
2869
+ type: "checkbox",
2870
+ path: "hasDiscountCode",
2871
+ label: "I have a discount code"
2872
+ },
2873
+ {
2874
+ kind: "input",
2875
+ type: "textinput",
2876
+ path: "discountCode",
2877
+ label: "Discount code",
2878
+ include: { in: ["hasDiscount"] }
2879
+ },
2880
+ {
2881
+ kind: "display",
2882
+ type: "alert",
2883
+ props: { text: "No discount applied." },
2884
+ exclude: { from: ["hasDiscount"] }
2885
+ }
2886
+ ]
2887
+ }
2888
+ },
2889
+ {
2890
+ name: "Inline conditional rendering with `when`",
2891
+ description: 'For a one-off condition that applies to a single widget only, use the inline `when` form: `"include": { "when": "expression" }` or `"exclude": { "when": "expression" }`. The expression is evaluated exactly like a state expression — it has access to `$form`, `$meta`, `$formIsInvalid`, and `$fn`, uses the same safe operator subset, and must use optional chaining for nested fields. No entry in the root `states` map is required. Use this form when the condition is not shared with any other widget; use the named-state form (`in`/`from`) when the same condition gates two or more widgets.',
2892
+ example: {
2893
+ $schema: FORM_SCHEMA_URL,
2894
+ form: [
2895
+ {
2896
+ kind: "input",
2897
+ type: "checkbox",
2898
+ path: "agreeTerms",
2899
+ label: "I agree to the terms"
2900
+ },
2901
+ {
2902
+ kind: "action",
2903
+ type: "button",
2904
+ actionType: "submit",
2905
+ label: "Continue",
2906
+ // Show only after terms are accepted — one-off condition, no state needed.
2907
+ include: { when: "$form.agreeTerms === true" }
2908
+ },
2909
+ {
2910
+ kind: "input",
2911
+ type: "textinput",
2912
+ path: "companyName",
2913
+ label: "Company name",
2914
+ // Hide when the user selects "individual" account type — one-off condition.
2915
+ exclude: { when: "$form.accountType === 'individual'" }
2916
+ }
2917
+ ]
2918
+ }
2919
+ },
2920
+ {
2921
+ name: "State-suffixed props",
2922
+ description: 'Override individual widget properties when a named state is active by appending `".<stateName>"` to the property key. The unsuffixed key holds the default value; each suffixed key supplies the override for that state. This works on root-level widget properties (`label`, `disabled`, `readonly`, `validator`, `size`) AND on any key inside the `props` object (`hint`, `placeholder`, `items`, `addLabel`, etc.). There is NO inline `when` equivalent for this — state-suffixed props REQUIRE a named state. Multiple suffixes can coexist on the same property; when more than one state is active, the last matching suffix in document order wins.',
2923
+ example: {
2924
+ $schema: FORM_SCHEMA_URL,
2925
+ states: {
2926
+ termsAccepted: "$form.terms === true",
2927
+ busy: "$meta.submitting === true"
2928
+ },
2929
+ form: [
2930
+ {
2931
+ kind: "input",
2932
+ type: "checkbox",
2933
+ path: "terms",
2934
+ label: "I accept the terms"
2935
+ },
2936
+ {
2937
+ kind: "action",
2938
+ type: "button",
2939
+ label: "Submit",
2940
+ "label.termsAccepted": "Submit ✓",
2941
+ "label.busy": "Submitting…",
2942
+ disabled: true,
2943
+ "disabled.termsAccepted": false,
2944
+ "disabled.busy": true
2945
+ },
2946
+ {
2947
+ kind: "display",
2948
+ type: "alert",
2949
+ props: {
2950
+ level: "warning",
2951
+ text: "Please accept the terms to continue.",
2952
+ "text.termsAccepted": "Ready to submit!"
2953
+ },
2954
+ exclude: { from: ["busy"] }
2955
+ },
2956
+ {
2957
+ kind: "input",
2958
+ type: "repeater",
2959
+ path: "users",
2960
+ label: "Users",
2961
+ addLabel: "Add user",
2962
+ "addLabel.limitReached": "Limit reached — can't add more",
2963
+ props: {
2964
+ removeLabel: "Remove",
2965
+ template: {
2966
+ kind: "layout",
2967
+ type: "flex",
2968
+ props: { direction: "column" },
2969
+ children: [
2970
+ { kind: "input", type: "textinput", path: "users.items.name", label: "Name" }
2971
+ ]
2972
+ }
2973
+ }
2974
+ }
2975
+ ]
2976
+ }
2977
+ }
2978
+ ],
2979
+ rules: [
2980
+ 'Every state name used in `include.in`, `exclude.from`, or as a property suffix MUST be declared in the root `"states"` map.',
2981
+ "Child state expressions must contain only the *additional* (incremental) condition — ancestor conditions are ANDed in automatically by the runtime. Duplicating a parent condition in a child expression is wrong and redundant.",
2982
+ 'A sub-state is only ever active when all of its ancestor states are also active. When using `include.in: ["register:adult"]` you do NOT need to also add `"register"` to the array.',
2983
+ "State-suffixed root props — only these support suffixes at the widget root level: `label`, `disabled`, `readonly`, `validator`, `size`. All other overridable properties live inside `props`.",
2984
+ 'State-suffixed props inside `props` — any key inside the `props` object can be suffixed: `"hint.<state>"`, `"placeholder.<state>"`, `"items.<state>"`, `"addLabel.<state>"`, etc.',
2985
+ 'Suffix names must not contain dots (the dot is the separator between property and state name): `"label.myState"` ✅, `"label.register:adult"` ✅ — `"label.my.state"` ❌.',
2986
+ "Reactive expressions must reference `$form`, `$meta`, `$formIsInvalid`, or `$fn`. A bare identifier like `termsAccepted` without a root reference is invalid.",
2987
+ "Use `===` / `!==` for equality, `&&` / `||` for logic. Avoid `=` (assignment), `==`/`!=` (loose equality), or bitwise `&`/`|`.",
2988
+ 'When multiple states are active at the same time and a property has more than one matching suffix, the longest state name wins (most specific takes priority). Example: if both `register` and `register:adult` are active, `"label.register:adult"` overrides `"label.register"`.',
2989
+ '`include.in` and `exclude.from` each accept an Array of state names. A widget included `in: ["a", "b"]` renders when state `a` OR state `b` is active.',
2990
+ "Use optional chaining (`?.`) when accessing nested fields that may not yet exist in the form data: `$form.user?.age >= 18` not `$form.user.age >= 18`."
2991
+ ]
2992
+ };
2993
+ const STRING_INTERPOLATION_CONCEPT = {
2994
+ concept: "string-interpolation",
2995
+ summary: "GolemUI supports live data binding in text props via `{{expression}}` template slots. Any string-valued property (e.g. `props.text`, `props.hint`, `label`) can embed one or more `{{...}}` slots. Each slot is a JavaScript-like expression evaluated against the live form state using a safe subset of JavaScript (no side effects; method calls on scope values and host-provided `$fn` functions are the only calls allowed). i18n translation `params` objects accept a matching bare-expression format — the same expressions but without the `{{}}` delimiters.",
2996
+ patterns: [
2997
+ {
2998
+ name: "Template slots in display text",
2999
+ description: "Embed `{{expression}}` in any string prop to inject live values. Available scopes: `$form` (all current field values), `$meta` (host-supplied metadata), `$errors` (current validation error messages keyed by field uid), `$formIsInvalid` (boolean — `true` when any field currently fails validation), and `$fn` (host-provided pure functions, called as `$fn.name(...)`). Use optional chaining (`?.`) when accessing nested fields that may not yet exist. Multiple slots can appear in a single string.",
3000
+ example: {
3001
+ $schema: FORM_SCHEMA_URL,
3002
+ form: [
3003
+ {
3004
+ uid: "userName",
3005
+ kind: "input",
3006
+ type: "textinput",
3007
+ path: "userName",
3008
+ validator: { type: "string", required: true }
3009
+ },
3010
+ {
3011
+ uid: "submitBtn",
3012
+ kind: "action",
3013
+ type: "button",
3014
+ label: "Submit",
3015
+ actionType: "submit"
3016
+ },
3017
+ {
3018
+ uid: "greeting",
3019
+ kind: "display",
3020
+ type: "alert",
3021
+ props: { text: "Hello {{$form.userName}}" }
3022
+ },
3023
+ {
3024
+ uid: "status",
3025
+ kind: "display",
3026
+ type: "alert",
3027
+ props: {
3028
+ text: "Error: {{$errors.userName}} | Form invalid: {{$formIsInvalid}}"
3029
+ }
3030
+ },
3031
+ {
3032
+ uid: "meta-info",
3033
+ kind: "display",
3034
+ type: "alert",
3035
+ props: { text: "Connected as {{$meta.role}} on {{$meta.server}}" }
3036
+ }
3037
+ ]
3038
+ }
3039
+ },
3040
+ {
3041
+ name: "Expressions in slots",
3042
+ description: "Slots support full JavaScript-like expressions: arithmetic, string concatenation, ternary conditionals, and optional chaining. The expression is evaluated against the same scope object (`$form`, `$meta`, `$errors`, `$formIsInvalid`, `$fn`). If the expression evaluates to `null` or `undefined`, the slot renders as an empty string.",
3043
+ example: {
3044
+ $schema: FORM_SCHEMA_URL,
3045
+ data: { firstName: "Jane", lastName: "Doe", count: 4, role: "admin" },
3046
+ form: [
3047
+ {
3048
+ uid: "full-name",
3049
+ kind: "display",
3050
+ type: "alert",
3051
+ props: { text: "Full name: {{$form.firstName + ' ' + $form.lastName}}" }
3052
+ },
3053
+ {
3054
+ uid: "next-count",
3055
+ kind: "display",
3056
+ type: "alert",
3057
+ props: { text: "Next item: {{$form.count + 1}}" }
3058
+ },
3059
+ {
3060
+ uid: "role-label",
3061
+ kind: "display",
3062
+ type: "alert",
3063
+ props: { text: "Role: {{$form.role === 'admin' ? 'Administrator' : 'User'}}" }
3064
+ },
3065
+ {
3066
+ uid: "nested",
3067
+ kind: "display",
3068
+ type: "alert",
3069
+ props: { text: "City: {{$form.address?.city}}" }
3070
+ }
3071
+ ]
3072
+ }
3073
+ },
3074
+ {
3075
+ name: "i18n param expressions",
3076
+ description: "When using i18n translations, `params` values support the same expression language as `{{}}` slots, but as **bare expressions** without the `{{}}` delimiters. Params that start with a `$` scope prefix are evaluated; others are passed as static strings. The expression has access to `$form`, `$meta`, `$errors`, `$formIsInvalid`, and `$fn`.",
3077
+ example: {
3078
+ $schema: FORM_SCHEMA_URL,
3079
+ data: { firstName: "Jane", lastName: "Doe", count: 4 },
3080
+ meta: { connectionStatus: "online" },
3081
+ form: [
3082
+ {
3083
+ uid: "greeting",
3084
+ kind: "display",
3085
+ type: "alert",
3086
+ props: {
3087
+ text: {
3088
+ key: "user.greeting",
3089
+ params: {
3090
+ hello: "Hola",
3091
+ fullName: "$form.firstName + ' ' + $form.lastName",
3092
+ n: "$form.count + 1",
3093
+ status: "$meta.connectionStatus"
3094
+ }
3095
+ }
3096
+ }
3097
+ }
3098
+ ]
3099
+ }
3100
+ }
3101
+ ],
3102
+ rules: [
3103
+ "Slots must reference at least one of `$form`, `$meta`, `$errors`, `$formIsInvalid`, or `$fn`. A bare identifier without a scope prefix is invalid inside `{{}}`: use `{{$form.name}}` not `{{name}}`. `$formIsInvalid` is a bare boolean — do not chain properties onto it.",
3104
+ "Inside a repeater `props.template`, slots can additionally reference `$item` (the current repeater item object) and `$index` (its zero-based position): `{{($item.quantity ?? 0) * ($item.unitPrice ?? 0)}}`. Outside a template, `$item`/`$index` are undefined and invalid.",
3105
+ "If an expression evaluates to `null` or `undefined`, the slot renders as an empty string in display text.",
3106
+ "Use optional chaining (`?.`) when accessing nested fields that may not yet exist: `{{$form.address?.city}}` not `{{$form.address.city}}`.",
3107
+ "Do not use assignment `=` inside a slot — slots are read-only. Use `===` for equality checks.",
3108
+ "Slots cannot be nested: `{{$form.a {{$form.b}}}}` is invalid.",
3109
+ "Every `{{` must have a matching `}}`. Unbalanced delimiters cause a lint warning.",
3110
+ 'i18n `params` values are bare expressions — do NOT wrap them in `{{}}`. Write `"$form.name"` not `"{{$form.name}}"`.',
3111
+ 'Static string params (not starting with `$`) are passed through as-is — use them for constant values like `"Hola"` or `"px"`.',
3112
+ 'The expression language is the same as reactive expressions — see `get_concept({ concept: "reactive-scope" })` for the operator reference and safe-expression constraints.'
3113
+ ]
3114
+ };
3115
+ const REACTIVE_SCOPE_CONCEPT = {
3116
+ concept: "reactive-scope",
3117
+ summary: "GolemUI reactive expressions (used in `states`, `include.when`, `exclude.when`, and `{{}}` template slots) share a common read-only scope object. The scope exposes five global variables: `$form` (live form data), `$meta` (host-supplied metadata), `$errors` (validation error messages), `$formIsInvalid` (built-in boolean), and `$fn` (host-provided pure functions). Inside a repeater `props.template` two more variables are available: `$item` (the current repeater item object) and `$index` (its zero-based position). All variables are read-only — expressions can only read from them, never write to them.",
3118
+ patterns: [
3119
+ {
3120
+ name: "$form — live form data",
3121
+ description: '`$form` is a plain object whose keys are the field paths currently registered in the form. Each key equals the `path` property of an input widget. A simple field `path: "firstName"` is accessed as `$form.firstName`. A nested field `path: "address.city"` is accessed as `$form.address?.city` — the dot segments in the path become dot-property accesses, and optional chaining (`?.`) is required at each intermediate segment because the parent object may not yet exist while the user is filling in the form. `$form` itself is always a defined object; only leaf values may be `undefined` before the user fills them in.',
3122
+ example: {
3123
+ states: {
3124
+ // path: "firstName" -> $form.firstName
3125
+ hasName: '$form.firstName !== undefined && $form.firstName !== ""',
3126
+ // path: "address.city" -> $form.address?.city (optional chaining at "address" segment)
3127
+ hasCity: '$form.address?.city !== undefined && $form.address?.city !== ""',
3128
+ // path: "user.profile.age" -> $form.user?.profile?.age
3129
+ isAdult: "$form.user?.profile?.age >= 18"
3130
+ }
3131
+ }
3132
+ },
3133
+ {
3134
+ name: "$meta — host-supplied metadata",
3135
+ description: "`$meta` is a free-form key/value object supplied by the host application at mount time. It is useful for passing server-side flags, the current user's role, locale, or any context that is not part of the form data itself. The host sets the `meta` prop on the GolemUI form component; the MCP tool has no knowledge of which keys the host will supply. Access values with `$meta.keyName`. Use optional chaining if a key may not always be present.",
3136
+ example: {
3137
+ states: {
3138
+ isAdmin: "$meta.role === 'admin'",
3139
+ isOnline: '$meta.connectionStatus === "online"'
3140
+ },
3141
+ form: [
3142
+ {
3143
+ kind: "input",
3144
+ type: "textinput",
3145
+ path: "apiKey",
3146
+ label: "API key",
3147
+ // Show only for admin users — the role comes from $meta, not from $form.
3148
+ include: { when: "$meta.role === 'admin'" }
3149
+ }
3150
+ ]
3151
+ }
3152
+ },
3153
+ {
3154
+ name: "$errors — validation error messages",
3155
+ description: '`$errors` is a plain object keyed by widget `uid`. `$errors.myField` is the current validation error message string for the widget with `uid: "myField"`, or `undefined` if that field is currently valid. Use it to display a field\'s error message inside another widget (e.g. an `alert`). Note: a widget must have an explicit `uid` value set for its errors to appear in `$errors`; auto-generated uids are not predictable.',
3156
+ example: {
3157
+ $schema: FORM_SCHEMA_URL,
3158
+ form: [
3159
+ {
3160
+ uid: "emailField",
3161
+ kind: "input",
3162
+ type: "textinput",
3163
+ path: "email",
3164
+ label: "Email",
3165
+ validator: { type: "string", required: true, format: "email" }
3166
+ },
3167
+ {
3168
+ kind: "display",
3169
+ type: "alert",
3170
+ props: {
3171
+ level: "error",
3172
+ // Render the live validation error message for the emailField widget.
3173
+ text: "{{$errors.emailField}}"
3174
+ },
3175
+ // Only show this alert when the field actually has an error.
3176
+ include: { when: "$errors.emailField !== undefined" }
3177
+ }
3178
+ ]
3179
+ }
3180
+ },
3181
+ {
3182
+ name: "$formIsInvalid — whole-form validity flag",
3183
+ description: '`$formIsInvalid` is a built-in boolean that the runtime maintains automatically. It is `true` when ANY field currently has a RECORDED validation failure; `false` otherwise. CAVEAT: validation never runs at mount, so on a pristine form the flag is `false` even when required fields are empty — it flips only after the first validated interaction. To disable a submit button from the start, combine it with a data check (see `get_concept({ concept: "validation" })` for the full explanation). It is NOT a property of `$form` — use it as a bare identifier. Do NOT chain properties onto it: `$formIsInvalid.something` is invalid.',
3184
+ example: {
3185
+ $schema: FORM_SCHEMA_URL,
3186
+ form: [
3187
+ {
3188
+ kind: "input",
3189
+ type: "textinput",
3190
+ path: "email",
3191
+ label: "Email",
3192
+ validator: { type: "string", required: true, format: "email" }
3193
+ },
3194
+ {
3195
+ kind: "action",
3196
+ type: "button",
3197
+ actionType: "submit",
3198
+ label: "Submit",
3199
+ // '$formIsInvalid' alone starts ENABLED on the pristine form (no validation has run
3200
+ // yet) — the extra data check covers the not-yet-validated empty state.
3201
+ disabled: { when: "$formIsInvalid || $form.email === undefined" }
3202
+ },
3203
+ {
3204
+ kind: "display",
3205
+ type: "alert",
3206
+ props: { level: "warning", text: "Please fix the errors above before submitting." },
3207
+ include: { when: "$formIsInvalid" }
3208
+ }
3209
+ ]
3210
+ }
3211
+ },
3212
+ {
3213
+ name: "$fn — host-provided pure functions",
3214
+ description: "`$fn` is a namespace of pure functions that the host application passes to the form component via the `functions` entry of the init config (a sibling of `dependencies`). Call them as `$fn.functionName(arg1, arg2)`; arguments can be any scope value, including `$form` paths and `$item`/`$index` inside a repeater template, and the returned value is substituted like any other expression result. Use `$fn` to keep complex derivations (totals, currency conversion, formatting) out of the expression string and inside typed, testable host code. The MCP tool has no knowledge of which function names the host supplies. Calling a name the host did not provide throws at evaluation time: template slots surface a form-health error, `when` conditions in flags propagate the error, and `states` treat the expression as `false`. Host functions MUST be pure: derive the result only from the arguments, no side effects.",
3215
+ example: {
3216
+ $schema: FORM_SCHEMA_URL,
3217
+ form: [
3218
+ {
3219
+ kind: "display",
3220
+ type: "markdownText",
3221
+ props: {
3222
+ // grandTotal comes from the host: config.functions = { grandTotal: (items) => ... }
3223
+ md: "**Grand Total:** {{$fn.grandTotal($form.lineItems)}}"
3224
+ },
3225
+ include: { when: "$fn.grandTotal($form.lineItems) > 0" }
3226
+ }
3227
+ ]
3228
+ }
3229
+ },
3230
+ {
3231
+ name: "$item / $index — current repeater item (template scope only)",
3232
+ description: "`$item` is the data object of the repeater item a widget belongs to, and `$index` is that item's zero-based position in the array. They are available ONLY to widgets inside a repeater `props.template` — in `include`/`exclude`/`disabled`/`readonly` `when` conditions, `{{}}` template slots, and i18n params. Outside a template they are `undefined` and the linter flags them. For nested repeaters, `$item`/`$index` refer to the INNERMOST enclosing item; to address an outer level, use the `items` path token through `$form` instead (e.g. `$form.teams.items.name` resolves against each item of the `teams` repeater). `$item` leaf values may be `undefined` while the user fills in the row, so guard them; `$index` is always a defined number.",
3233
+ example: {
3234
+ $schema: FORM_SCHEMA_URL,
3235
+ form: [
3236
+ {
3237
+ kind: "input",
3238
+ type: "repeater",
3239
+ path: "lineItems",
3240
+ label: "Line Items",
3241
+ props: {
3242
+ template: {
3243
+ kind: "layout",
3244
+ type: "flex",
3245
+ props: { direction: "column" },
3246
+ children: [
3247
+ {
3248
+ kind: "input",
3249
+ type: "number",
3250
+ path: "lineItems.items.quantity",
3251
+ label: "Quantity {{$index + 1}}"
3252
+ },
3253
+ {
3254
+ kind: "display",
3255
+ type: "markdownText",
3256
+ props: {
3257
+ md: "**Total:** {{(($item.quantity ?? 0) * ($item.unitPrice ?? 0)).toFixed(2)}}"
3258
+ },
3259
+ include: { when: "$item.quantity !== undefined" }
3260
+ }
3261
+ ]
3262
+ }
3263
+ }
3264
+ }
3265
+ ]
3266
+ }
3267
+ }
3268
+ ],
3269
+ rules: [
3270
+ "All scope variables are read-only. Expressions may only read values, never assign them.",
3271
+ "`$item` and `$index` exist only for widgets inside a repeater `props.template`. In `states` and in widgets outside a template they are undefined and invalid.",
3272
+ "For nested repeaters `$item`/`$index` bind to the innermost enclosing item. Use the `items` path token through `$form` to address outer levels.",
3273
+ "`$item` leaf values (`$item.someField`) may be `undefined` until the user fills them in — guard with `??` or explicit comparisons. `$index` is always a defined number.",
3274
+ "`$form` is always a defined object. Its leaf values (`$form.someField`) may be `undefined` until the user fills them in.",
3275
+ "Use optional chaining (`?.`) at every intermediate segment of a nested path. `$form.address?.city` is safe; `$form.address.city` throws if `address` is undefined.",
3276
+ 'A widget\'s `path` value maps directly to a `$form` key path using the same dot segments. `path: "shipping.address.zip"` -> `$form.shipping?.address?.zip`.',
3277
+ '`$formIsInvalid` is a built-in bare boolean — use it directly: `disabled: { when: "$formIsInvalid" }` or `states: { formValid: "!$formIsInvalid" }`. Never chain: `$formIsInvalid.value` is invalid.',
3278
+ "`$errors` keys are widget `uid` values, not field path values. A widget must have an explicit `uid` for its errors to be addressable.",
3279
+ "`$meta` keys are arbitrary — they depend entirely on what the host application passes to the form component. Use optional chaining if a key may be absent.",
3280
+ "Supported operators across all expressions: arithmetic (`+`, `-`, `*`, `/`, `%`), comparison (`===`, `!==`, `<`, `>`, `<=`, `>=`), logical (`&&`, `||`, `!`), ternary (`? :`), optional chaining (`?.`), nullish coalescing (`??`).",
3281
+ "Use `===` / `!==` for equality. Avoid `==` / `!=` (loose equality causes unexpected coercions with `undefined`).",
3282
+ "Expressions may call methods on scope values (e.g. `.includes()`, `.toFixed()`) and host functions via `$fn.name(...)`. Everything must stay a pure read: no `eval`, no assignments, no side effects.",
3283
+ "`$fn` names are defined by the host through the `functions` init config. Calling a name the host did not provide errors the expression at evaluation time — coordinate names with the host."
3284
+ ]
3285
+ };
3286
+ const VALIDATION_CONCEPT = {
3287
+ concept: "validation",
3288
+ summary: 'Input widgets validate through their declarative `validator` object. Three behaviors are non-obvious and cause real bugs when missed: (1) validation NEVER runs at mount — a pristine form has zero recorded errors, so `$formIsInvalid` starts `false` in every `validateOn` mode; (2) on boolean fields `required: true` does NOT force a checkbox to be checked — `false` is a valid boolean; a mandatory checkbox needs `const: true` AND `required: true` together; (3) when a required field is `undefined` or `null` the failure comes from the base type check, not the `required` rule, so the user sees the `invalid` message (a raw "Invalid input: expected string, received undefined" unless you customize it). Always set custom `messages`.',
3289
+ patterns: [
3290
+ {
3291
+ name: "Custom error messages per rule (`messages`)",
3292
+ description: 'Every validator accepts a `messages` object mapping rule names to custom error text. The allowed keys depend on the validator type — string: `invalid`, `required`, `minLength`, `maxLength`, `pattern`, `format`, `enum`, `const`; number/integer: `invalid`, `minimum`, `maximum`, `exclusiveMinimum`, `exclusiveMaximum`, `multipleOf`, `enum`, `const`; boolean: `invalid`, `const`; array: `invalid`, `required`, `minItems`, `maxItems`. The special key `invalid` customizes the base type check (wrong type, or `undefined`/`null` on a required field). Note that only string and array validators have a `required` message key — they are the only types with a present-but-empty state (`""` / `[]`); for number/integer/boolean a missing value can only ever show the `invalid` message. Values are plain strings or i18n descriptors `{ key, params?, default? }`. Without `messages`, failures surface library-default text (e.g. "Invalid input: expected string, received undefined") that is not written for end users — production forms should set custom messages for every rule they use, and ALWAYS set `invalid` whenever `required: true` is set (see the next patterns for why).',
3293
+ example: {
3294
+ $schema: FORM_SCHEMA_URL,
3295
+ form: [
3296
+ {
3297
+ kind: "input",
3298
+ type: "textinput",
3299
+ path: "email",
3300
+ label: "Email",
3301
+ validator: {
3302
+ type: "string",
3303
+ required: true,
3304
+ format: "email",
3305
+ messages: {
3306
+ // `invalid` fires when the value is undefined/null (pristine or cleared) —
3307
+ // for the user that IS the required case, so give it the same text.
3308
+ invalid: "Email is required",
3309
+ required: "Email is required",
3310
+ format: "Enter a valid email address"
3311
+ }
3312
+ }
3313
+ }
3314
+ ]
3315
+ }
3316
+ },
3317
+ {
3318
+ name: "Mandatory checkbox — `const: true` AND `required: true`, never `required` alone",
3319
+ description: "On a boolean validator `required: true` is a silent trap: it only rejects a MISSING value (`undefined`/`null`); an unchecked checkbox holding `false` is a perfectly valid boolean and PASSES. To force the box to be checked you need `const: true` — but `const: true` alone is also not enough: a validator without `required: true` is optional, so a pristine checkbox whose value is still `undefined` skips validation entirely and passes too. The full recipe is BOTH rules together, plus messages for BOTH failure modes: a pristine/never-touched checkbox fails the base type check (`invalid` message) while a checked-then-unchecked checkbox fails the `const` rule (`const` message) — set both keys to the same user-facing text.",
3320
+ example: {
3321
+ $schema: FORM_SCHEMA_URL,
3322
+ form: [
3323
+ {
3324
+ kind: "input",
3325
+ type: "checkbox",
3326
+ path: "termsAccepted",
3327
+ label: "I accept the terms",
3328
+ validator: {
3329
+ type: "boolean",
3330
+ required: true,
3331
+ // rejects undefined/null (never touched)
3332
+ const: true,
3333
+ // rejects false (unchecked)
3334
+ messages: {
3335
+ invalid: "You must accept the terms",
3336
+ const: "You must accept the terms"
3337
+ }
3338
+ }
3339
+ }
3340
+ ]
3341
+ }
3342
+ },
3343
+ {
3344
+ name: "The `invalid` message — what empty required fields actually show",
3345
+ description: 'When a required field holds `undefined` or `null` (pristine, or the widget cleared it), the failure is raised by the BASE TYPE check ("expected string, received undefined"), NOT by the `required` rule — the `required` rule only fires on present-but-empty values such as `""` for strings or `[]` for arrays. Consequence: `messages.required` alone does not cover the most common empty state, and the user sees the raw library default instead. Whenever you set `required: true` on a string or array validator, set BOTH `messages.required` AND `messages.invalid`, normally to the same text — from the user\'s perspective both mean "this field is required". On number/integer/boolean validators there is no `required` message key at all — `messages.invalid` is the ONLY way to word the missing-value error, so setting it is not optional there. Note `null` is never valid: even on a non-required field, `null` fails the type check and shows the `invalid` message (only `undefined` is treated as "not filled in yet").',
3346
+ example: {
3347
+ $schema: FORM_SCHEMA_URL,
3348
+ form: [
3349
+ {
3350
+ kind: "input",
3351
+ type: "number",
3352
+ path: "age",
3353
+ label: "Age",
3354
+ validator: {
3355
+ type: "integer",
3356
+ required: true,
3357
+ minimum: 18,
3358
+ messages: {
3359
+ // Number validators have no `required` message key — `invalid` covers the
3360
+ // undefined/null case (pristine or cleared input), which IS the required case.
3361
+ invalid: "Age is required",
3362
+ minimum: "You must be at least 18"
3363
+ }
3364
+ }
3365
+ }
3366
+ ]
3367
+ }
3368
+ },
3369
+ {
3370
+ name: "When validation runs — `validateOn` and the pristine-form gap",
3371
+ description: 'Validation runs only in response to user interaction, filtered by the form-level `validateOn` config: `"eager"` (the default — the first change OR blur on any field validates the WHOLE form), `"change"`, `"blur"`, `"submit"`, or an array of those. NOTHING validates at mount in ANY mode, so on a pristine form the error map is empty and `$formIsInvalid` is `false` — a submit button with `disabled: { when: "$formIsInvalid" }` starts out ENABLED even when required fields are empty. Clicking a submit button always validates the whole form and the runtime refuses to emit the submit event while invalid — data integrity is safe — but the disabled-until-valid UX needs a compound expression that also checks the data directly, because `$formIsInvalid` only reflects validations that have already run.',
3372
+ example: {
3373
+ $schema: FORM_SCHEMA_URL,
3374
+ form: [
3375
+ {
3376
+ kind: "input",
3377
+ type: "textinput",
3378
+ path: "email",
3379
+ label: "Email",
3380
+ validator: {
3381
+ type: "string",
3382
+ required: true,
3383
+ format: "email",
3384
+ messages: { invalid: "Email is required", required: "Email is required" }
3385
+ }
3386
+ },
3387
+ {
3388
+ kind: "action",
3389
+ type: "button",
3390
+ actionType: "submit",
3391
+ label: "Submit",
3392
+ // '$formIsInvalid' alone leaves this ENABLED on the pristine form (no validation has
3393
+ // run yet). The compound expression also disables it while the field is still empty.
3394
+ disabled: { when: "$formIsInvalid || $form.email === undefined" }
3395
+ }
3396
+ ]
3397
+ }
3398
+ }
3399
+ ],
3400
+ rules: [
3401
+ 'Validation NEVER runs at mount. A pristine form has an empty error map and `$formIsInvalid === false` in every `validateOn` mode, including the default `"eager"`.',
3402
+ '`disabled: { when: "$formIsInvalid" }` on a submit button leaves it ENABLED on the pristine form. For disabled-until-valid UX, use a compound expression that also checks the data: `"$formIsInvalid || $form.email === undefined"`.',
3403
+ "The runtime always re-validates everything on submit click and blocks the submit event while invalid — the pristine gap is a UX issue, not a data-integrity issue.",
3404
+ '`validateOn` values: `"eager"` (default; first change or blur anywhere validates the whole form), `"change"`, `"blur"`, `"submit"`, or an array of `"change"`/`"blur"`/`"submit"`.',
3405
+ "Boolean `required: true` does NOT force a checkbox to be checked — `false` is a valid boolean. Only `const: true` rejects `false`.",
3406
+ "`const: true` alone does NOT cover the pristine case — without `required: true` the validator is optional and `undefined` passes. A mandatory checkbox needs BOTH.",
3407
+ 'A required field holding `undefined`/`null` fails the base TYPE check, not the `required` rule — the user sees the `invalid` message. The `required` rule only fires on present-but-empty values (`""`, `[]`).',
3408
+ "Only string and array validators accept a `required` message key. Number/integer and boolean validators do NOT — `messages.invalid` is the only way to word their missing-value error.",
3409
+ "ALWAYS pair `messages.required` with `messages.invalid` (same text) on string/array validators. For a mandatory checkbox, pair `messages.const` with `messages.invalid`.",
3410
+ '`null` is never a valid value, even for non-required fields — it fails the type check and shows the `invalid` message. Only `undefined` means "not filled in yet".',
3411
+ "Message values are strings or i18n descriptors `{ key, params?, default? }` — the same `Localizable` shape as labels.",
3412
+ 'Production forms should define custom `messages` for every rule they use — the library defaults (e.g. "Invalid input: expected string, received undefined") are developer-facing, not user-facing.'
3413
+ ]
3414
+ };
3415
+ const ICONS_CONCEPT = {
3416
+ concept: "icons",
3417
+ summary: 'GolemUI uses Google Material Icons for all icon props. An icon value is a Material Icons ligature name — a lowercase string with underscores, such as `"search"`, `"home"`, `"arrow_forward"`, or `"check_circle"`. The icon font must be loaded by the host page; without it, the icon value renders as raw text. Several widgets accept a `props.icon` property; `button` additionally has `props.iconPosition`. All icon props support state suffixes for reactive icon swapping.',
3418
+ patterns: [
3419
+ {
3420
+ name: "Widget icon props",
3421
+ description: "The following widgets accept `props.icon` (a Material Icons ligature name string): `button`, `textinput`, `password`, `select`, `currency`, `tags`, `dateInput`, `datePicker`, `rangeCalendar`, `rangedateinput`, `rangedatepicker`. The `button` widget additionally accepts `props.iconPosition` to control where the icon appears relative to the label. All other icon-capable widgets render the icon at a default position determined by the component.",
3422
+ example: {
3423
+ $schema: FORM_SCHEMA_URL,
3424
+ form: [
3425
+ {
3426
+ kind: "action",
3427
+ type: "button",
3428
+ actionType: "submit",
3429
+ label: "Send",
3430
+ props: {
3431
+ // "send" is the Google Material Icons ligature name for the send icon.
3432
+ icon: "send",
3433
+ iconPosition: "right"
3434
+ }
3435
+ },
3436
+ {
3437
+ kind: "input",
3438
+ type: "textinput",
3439
+ path: "email",
3440
+ label: "Email",
3441
+ props: {
3442
+ icon: "email",
3443
+ placeholder: "you@example.com"
3444
+ }
3445
+ },
3446
+ {
3447
+ kind: "input",
3448
+ type: "select",
3449
+ path: "country",
3450
+ label: "Country",
3451
+ props: {
3452
+ icon: "public",
3453
+ options: [
3454
+ { label: "United States", value: "us" },
3455
+ { label: "Canada", value: "ca" }
3456
+ ]
3457
+ }
3458
+ }
3459
+ ]
3460
+ }
3461
+ },
3462
+ {
3463
+ name: "Reactive icon swapping with state suffixes",
3464
+ description: 'Like other widget props, `icon` supports state suffixes: `"icon.<stateName>": "checkName"` swaps the icon when the named state is active. This is useful for toggling between a default and a confirmation icon, or for indicating a loading state on a button.',
3465
+ example: {
3466
+ $schema: FORM_SCHEMA_URL,
3467
+ states: {
3468
+ submitted: "$meta.submitting === true"
3469
+ },
3470
+ form: [
3471
+ {
3472
+ kind: "action",
3473
+ type: "button",
3474
+ actionType: "submit",
3475
+ label: "Submit",
3476
+ "label.submitted": "Submitting...",
3477
+ props: {
3478
+ icon: "send",
3479
+ // Swap to a spinner/hourglass icon while the form is being submitted.
3480
+ "icon.submitted": "hourglass_empty"
3481
+ }
3482
+ }
3483
+ ]
3484
+ }
3485
+ }
3486
+ ],
3487
+ rules: [
3488
+ 'Icon values are Google Material Icons ligature names — lowercase strings, words separated by underscores: `"search"`, `"arrow_forward"`, `"check_circle"`. Wrong casing or spaces will not render correctly.',
3489
+ 'The Material Icons font MUST be loaded in the host page\'s `<head>`. Without it, `props.icon` renders as the raw string (e.g. the word "search") rather than an icon glyph.',
3490
+ "Widgets that support `props.icon`: `button`, `textinput`, `password`, `select`, `currency`, `tags`, `dateInput`, `datePicker`, `rangeCalendar`, `rangedateinput`, `rangedatepicker`.",
3491
+ '`button` is the only widget with `props.iconPosition`. Allowed values: `"left"` (default) and `"right"`.',
3492
+ 'All icon props support state suffixes: `"icon.<stateName>": "check"` swaps the icon when that state is active. Call `get_concept({ concept: "states" })` for the full state-suffix pattern.',
3493
+ "Do not set `props.icon` on widgets that do not support it — the schema will reject it and `json_validate_form_definition` will report an error."
3494
+ ]
3495
+ };
3496
+ const CONCEPTS = {
3497
+ states: STATES_CONCEPT,
3498
+ "string-interpolation": STRING_INTERPOLATION_CONCEPT,
3499
+ "reactive-scope": REACTIVE_SCOPE_CONCEPT,
3500
+ validation: VALIDATION_CONCEPT,
3501
+ icons: ICONS_CONCEPT
3502
+ };
3503
+ function getConcept(input) {
3504
+ const result = CONCEPTS[input.concept];
3505
+ if (!result) {
3506
+ const known = Object.keys(CONCEPTS).sort().map((c) => `\`${c}\``).join(", ");
3507
+ throw new Error(`Unknown concept \`${input.concept}\`. Known concepts: ${known}.`);
3508
+ }
3509
+ return result;
3510
+ }
3511
+ const GET_CONCEPT_TOOL = {
3512
+ name: "get_concept",
3513
+ description: 'Return a detailed guide for a cross-cutting GolemUI form concept — things that span multiple widgets and affect the whole form, rather than the API of a single widget. Call this when you need to: (1) conditionally show or hide widgets (`include`/`exclude`) — both the named-state form (`in`/`from`) and the inline `when` expression form are covered under the `states` concept; (2) change a widget\'s props based on form state (state-suffixed props like `"label.stateName": "…"`); (3) understand what `$form`, `$meta`, `$errors`, `$formIsInvalid`, and `$fn` are and how to reference form data in reactive expressions — use the `reactive-scope` concept; (4) write validators with custom error messages, make a checkbox mandatory, or gate a submit button on validity — use the `validation` concept (it covers three non-obvious traps: no validation at mount, boolean `required` vs `const`, and the `invalid` message); (5) add icons to widgets — use the `icons` concept. Currently supported concepts: `states`, `string-interpolation`, `reactive-scope`, `validation`, `icons`.',
3514
+ inputSchema: {
3515
+ type: "object",
3516
+ properties: {
3517
+ concept: {
3518
+ type: "string",
3519
+ description: 'The concept to explain. Currently supported: `"states"`, `"string-interpolation"`, `"reactive-scope"`, `"validation"`, `"icons"`.',
3520
+ enum: Object.keys(CONCEPTS)
3521
+ }
3522
+ },
3523
+ required: ["concept"]
3524
+ }
3525
+ };
3526
+ export {
3527
+ GET_CONCEPT_TOOL as G,
3528
+ JSON_GENERATE_FROM_OPENAPI_TOOL as J,
3529
+ JSON_GENERATE_FROM_SCHEMA_TOOL as a,
3530
+ JSON_GET_WIDGET_SPEC_TOOL as b,
3531
+ JSON_VALIDATE_FORM_DEFINITION_TOOL as c,
3532
+ generateFromOpenapi as d,
3533
+ getConcept as e,
3534
+ getWidgetSpec as f,
3535
+ generateFromJsonSchema as g,
3536
+ checkReactiveExpression as h,
3537
+ checkBooleanValidatorRules as i,
3538
+ validateFormDefinition as v
3539
+ };