stimeo-ui 0.12.0 → 0.14.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.
- package/CHANGELOG.md +71 -0
- package/dist/cable/index.d.ts +68 -14
- package/dist/cable/index.js +438 -152
- package/dist/cable/index.js.map +1 -1
- package/dist/controllers/accordion_controller.d.ts +1 -1
- package/dist/controllers/accordion_controller.js.map +1 -1
- package/dist/controllers/alert_dialog_controller.d.ts +1 -1
- package/dist/controllers/alert_dialog_controller.js.map +1 -1
- package/dist/controllers/announcer_controller.d.ts +1 -1
- package/dist/controllers/announcer_controller.js.map +1 -1
- package/dist/controllers/auto_submit_controller.js.map +1 -1
- package/dist/controllers/breadcrumb_controller.d.ts +1 -1
- package/dist/controllers/breadcrumb_controller.js.map +1 -1
- package/dist/controllers/calendar_controller.d.ts +4 -3
- package/dist/controllers/calendar_controller.js +34 -2
- package/dist/controllers/calendar_controller.js.map +1 -1
- package/dist/controllers/carousel_controller.js +9 -7
- package/dist/controllers/carousel_controller.js.map +1 -1
- package/dist/controllers/character_counter_controller.js.map +1 -1
- package/dist/controllers/clipboard_controller.d.ts +2 -2
- package/dist/controllers/clipboard_controller.js.map +1 -1
- package/dist/controllers/collapsible_controller.d.ts +1 -1
- package/dist/controllers/collapsible_controller.js.map +1 -1
- package/dist/controllers/color_picker_controller.d.ts +1 -1
- package/dist/controllers/color_picker_controller.js.map +1 -1
- package/dist/controllers/command_palette_controller.d.ts +3 -3
- package/dist/controllers/command_palette_controller.js +2 -2
- package/dist/controllers/command_palette_controller.js.map +1 -1
- package/dist/controllers/conditional_fields_controller.js +7 -1
- package/dist/controllers/conditional_fields_controller.js.map +1 -1
- package/dist/controllers/confirm_controller.d.ts +2 -2
- package/dist/controllers/confirm_controller.js.map +1 -1
- package/dist/controllers/context_menu_controller.d.ts +1 -1
- package/dist/controllers/context_menu_controller.js.map +1 -1
- package/dist/controllers/countdown_controller.d.ts +1 -1
- package/dist/controllers/countdown_controller.js.map +1 -1
- package/dist/controllers/currency_input_controller.js +68 -23
- package/dist/controllers/currency_input_controller.js.map +1 -1
- package/dist/controllers/data_grid_controller.d.ts +1 -1
- package/dist/controllers/data_grid_controller.js.map +1 -1
- package/dist/controllers/date_range_picker_controller.d.ts +3 -3
- package/dist/controllers/date_range_picker_controller.js +34 -10
- package/dist/controllers/date_range_picker_controller.js.map +1 -1
- package/dist/controllers/dialog_controller.d.ts +3 -3
- package/dist/controllers/dialog_controller.js.map +1 -1
- package/dist/controllers/direct_upload_controller.js +21 -10
- package/dist/controllers/direct_upload_controller.js.map +1 -1
- package/dist/controllers/dirty_form_controller.js.map +1 -1
- package/dist/controllers/dismissible_controller.d.ts +1 -1
- package/dist/controllers/dismissible_controller.js.map +1 -1
- package/dist/controllers/drawer_controller.d.ts +2 -2
- package/dist/controllers/drawer_controller.js +2 -2
- package/dist/controllers/drawer_controller.js.map +1 -1
- package/dist/controllers/dropdown_controller.d.ts +2 -2
- package/dist/controllers/dropdown_controller.js.map +1 -1
- package/dist/controllers/file_dropzone_controller.js.map +1 -1
- package/dist/controllers/flash_controller.js.map +1 -1
- package/dist/controllers/focus_controller.d.ts +2 -2
- package/dist/controllers/focus_controller.js.map +1 -1
- package/dist/controllers/form_field_controller.js +7 -1
- package/dist/controllers/form_field_controller.js.map +1 -1
- package/dist/controllers/form_validation_controller.js.map +1 -1
- package/dist/controllers/frame_loading_controller.d.ts +3 -3
- package/dist/controllers/frame_loading_controller.js.map +1 -1
- package/dist/controllers/highlight_controller.js.map +1 -1
- package/dist/controllers/hover_card_controller.d.ts +1 -1
- package/dist/controllers/hover_card_controller.js.map +1 -1
- package/dist/controllers/idle_controller.d.ts +1 -1
- package/dist/controllers/idle_controller.js.map +1 -1
- package/dist/controllers/input_mask_controller.d.ts +3 -2
- package/dist/controllers/input_mask_controller.js +33 -12
- package/dist/controllers/input_mask_controller.js.map +1 -1
- package/dist/controllers/intersection_controller.js +10 -5
- package/dist/controllers/intersection_controller.js.map +1 -1
- package/dist/controllers/lazy_frame_controller.js +10 -5
- package/dist/controllers/lazy_frame_controller.js.map +1 -1
- package/dist/controllers/listbox_controller.js.map +1 -1
- package/dist/controllers/local_time_controller.d.ts +4 -3
- package/dist/controllers/local_time_controller.js +34 -7
- package/dist/controllers/local_time_controller.js.map +1 -1
- package/dist/controllers/masonry_controller.d.ts +2 -2
- package/dist/controllers/masonry_controller.js +1 -1
- package/dist/controllers/masonry_controller.js.map +1 -1
- package/dist/controllers/menu_controller.d.ts +1 -1
- package/dist/controllers/menu_controller.js +10 -2
- package/dist/controllers/menu_controller.js.map +1 -1
- package/dist/controllers/menubar_controller.d.ts +2 -2
- package/dist/controllers/menubar_controller.js +10 -2
- package/dist/controllers/menubar_controller.js.map +1 -1
- package/dist/controllers/navigation_menu_controller.d.ts +1 -1
- package/dist/controllers/navigation_menu_controller.js +8 -2
- package/dist/controllers/navigation_menu_controller.js.map +1 -1
- package/dist/controllers/nested_form_controller.js.map +1 -1
- package/dist/controllers/network_status_controller.js.map +1 -1
- package/dist/controllers/number_input_controller.js.map +1 -1
- package/dist/controllers/optimistic_controller.d.ts +23 -10
- package/dist/controllers/optimistic_controller.js +141 -20
- package/dist/controllers/optimistic_controller.js.map +1 -1
- package/dist/controllers/otp_controller.js +23 -10
- package/dist/controllers/otp_controller.js.map +1 -1
- package/dist/controllers/overflow_indicator_controller.d.ts +1 -1
- package/dist/controllers/overflow_indicator_controller.js.map +1 -1
- package/dist/controllers/overflow_menu_controller.js +10 -1
- package/dist/controllers/overflow_menu_controller.js.map +1 -1
- package/dist/controllers/pagination_controller.js.map +1 -1
- package/dist/controllers/password_reveal_controller.d.ts +1 -1
- package/dist/controllers/password_reveal_controller.js.map +1 -1
- package/dist/controllers/password_strength_controller.d.ts +2 -1
- package/dist/controllers/password_strength_controller.js.map +1 -1
- package/dist/controllers/persist_controller.js.map +1 -1
- package/dist/controllers/pointer_drag_controller.js +10 -3
- package/dist/controllers/pointer_drag_controller.js.map +1 -1
- package/dist/controllers/popover_controller.d.ts +1 -1
- package/dist/controllers/popover_controller.js.map +1 -1
- package/dist/controllers/portal_controller.d.ts +2 -2
- package/dist/controllers/portal_controller.js +21 -10
- package/dist/controllers/portal_controller.js.map +1 -1
- package/dist/controllers/radio_group_controller.d.ts +1 -1
- package/dist/controllers/radio_group_controller.js +11 -3
- package/dist/controllers/radio_group_controller.js.map +1 -1
- package/dist/controllers/read_more_controller.d.ts +1 -1
- package/dist/controllers/read_more_controller.js.map +1 -1
- package/dist/controllers/relative_time_controller.d.ts +3 -3
- package/dist/controllers/relative_time_controller.js +31 -5
- package/dist/controllers/relative_time_controller.js.map +1 -1
- package/dist/controllers/reset_before_cache_controller.js +23 -10
- package/dist/controllers/reset_before_cache_controller.js.map +1 -1
- package/dist/controllers/resizable_controller.js +7 -2
- package/dist/controllers/resizable_controller.js.map +1 -1
- package/dist/controllers/roving_controller.d.ts +1 -1
- package/dist/controllers/roving_controller.js +7 -3
- package/dist/controllers/roving_controller.js.map +1 -1
- package/dist/controllers/scroll_area_controller.js.map +1 -1
- package/dist/controllers/scroll_visibility_controller.d.ts +1 -1
- package/dist/controllers/scroll_visibility_controller.js +22 -13
- package/dist/controllers/scroll_visibility_controller.js.map +1 -1
- package/dist/controllers/scrollspy_controller.d.ts +1 -1
- package/dist/controllers/scrollspy_controller.js +11 -6
- package/dist/controllers/scrollspy_controller.js.map +1 -1
- package/dist/controllers/sidebar_controller.d.ts +1 -1
- package/dist/controllers/sidebar_controller.js.map +1 -1
- package/dist/controllers/skeleton_controller.d.ts +2 -2
- package/dist/controllers/skeleton_controller.js.map +1 -1
- package/dist/controllers/smart_sticky_header_controller.js +23 -12
- package/dist/controllers/smart_sticky_header_controller.js.map +1 -1
- package/dist/controllers/spinner_controller.d.ts +3 -3
- package/dist/controllers/spinner_controller.js.map +1 -1
- package/dist/controllers/sticky_observer_controller.js +10 -5
- package/dist/controllers/sticky_observer_controller.js.map +1 -1
- package/dist/controllers/submit_once_controller.d.ts +3 -3
- package/dist/controllers/submit_once_controller.js.map +1 -1
- package/dist/controllers/switch_controller.d.ts +1 -1
- package/dist/controllers/switch_controller.js.map +1 -1
- package/dist/controllers/tabs_controller.d.ts +1 -1
- package/dist/controllers/tabs_controller.js.map +1 -1
- package/dist/controllers/textarea_autosize_controller.d.ts +1 -1
- package/dist/controllers/textarea_autosize_controller.js.map +1 -1
- package/dist/controllers/theme_controller.d.ts +5 -5
- package/dist/controllers/theme_controller.js +23 -13
- package/dist/controllers/theme_controller.js.map +1 -1
- package/dist/controllers/toast_controller.js +1 -1
- package/dist/controllers/toast_controller.js.map +1 -1
- package/dist/controllers/toggle_group_controller.js +11 -3
- package/dist/controllers/toggle_group_controller.js.map +1 -1
- package/dist/controllers/toolbar_controller.d.ts +1 -1
- package/dist/controllers/toolbar_controller.js +7 -3
- package/dist/controllers/toolbar_controller.js.map +1 -1
- package/dist/controllers/tooltip_controller.d.ts +1 -1
- package/dist/controllers/tooltip_controller.js.map +1 -1
- package/dist/controllers/transition_controller.d.ts +1 -1
- package/dist/controllers/transition_controller.js.map +1 -1
- package/dist/controllers/tree_view_controller.d.ts +4 -3
- package/dist/controllers/tree_view_controller.js.map +1 -1
- package/dist/index.js +259 -202
- package/dist/index.js.map +1 -1
- package/dist/inspector/cli.d.ts +39 -2
- package/dist/inspector/cli.js +81 -8
- package/dist/inspector/cli.js.map +1 -1
- package/dist/inspector/cli_bin.js +104 -8
- package/dist/inspector/cli_bin.js.map +1 -1
- package/dist/inspector/examples.json +5 -5
- package/dist/inspector/manifest.json +132 -3
- package/package.json +9 -11
package/dist/inspector/cli.d.ts
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* Shared types for the Stimeo Inspector CLI (`stimeo check`).
|
|
3
3
|
*
|
|
4
4
|
* The Inspector statically checks HTML/ERB against a *manifest* describing the
|
|
5
|
-
*
|
|
5
|
+
* `stimeo--` controllers this package ships. The same engine powers both the library's
|
|
6
6
|
* own contract checks (e.g. `stimeo check app/views`) and the user-facing CLI;
|
|
7
7
|
* it is therefore intentionally input-path agnostic.
|
|
8
8
|
*/
|
|
@@ -29,6 +29,13 @@ interface ControllerManifest {
|
|
|
29
29
|
* strictly positive step, so those contracts stay explicit and reviewable.
|
|
30
30
|
*/
|
|
31
31
|
readonly valueConstraints: readonly ValueConstraint[];
|
|
32
|
+
/**
|
|
33
|
+
* Grammar contracts on String Values whose accepted set cannot be enumerated
|
|
34
|
+
* (stage 1). Optional on the wire: a manifest written before the field existed
|
|
35
|
+
* omits it, and an engine written before it skips it, so either side pairs
|
|
36
|
+
* with the other. See {@link StringSyntaxConstraint}.
|
|
37
|
+
*/
|
|
38
|
+
readonly valueSyntaxConstraints?: readonly StringSyntaxConstraint[];
|
|
32
39
|
/** Statically decidable relationships between literal Stimulus Values. */
|
|
33
40
|
readonly valueRelations: readonly ValueRelation[];
|
|
34
41
|
/**
|
|
@@ -740,6 +747,36 @@ interface StringValueConstraint {
|
|
|
740
747
|
/** Human-readable fix suggestion shown by the CLI (stage 4). */
|
|
741
748
|
readonly suggestion: string;
|
|
742
749
|
}
|
|
750
|
+
/**
|
|
751
|
+
* A String Value whose text is only readable by handing it to a parser, so the
|
|
752
|
+
* contract is a grammar rather than a set of literals.
|
|
753
|
+
*
|
|
754
|
+
* The controller parses the same text at runtime and falls back to the Value's
|
|
755
|
+
* default when it does not read, so a violation is a silently degraded element
|
|
756
|
+
* rather than a crash — which is exactly what a static check is for. Selectors
|
|
757
|
+
* are deliberately absent: the Inspector parses HTML itself and has no DOM to
|
|
758
|
+
* ask, so it cannot tell a malformed selector from one that simply matches
|
|
759
|
+
* nothing.
|
|
760
|
+
*
|
|
761
|
+
* These live in their own manifest field rather than alongside
|
|
762
|
+
* {@link StringValueConstraint}: an engine that predates them reads every String
|
|
763
|
+
* entry of `valueConstraints` through `allowedValues`, so a grammar contract
|
|
764
|
+
* placed there would be accepted by the shape check and then fail on the first
|
|
765
|
+
* document that declares the Value. A field such an engine never looks at is
|
|
766
|
+
* skipped instead.
|
|
767
|
+
*/
|
|
768
|
+
interface StringSyntaxConstraint {
|
|
769
|
+
/** Value name (camelCase, as declared in `static values`). */
|
|
770
|
+
readonly value: string;
|
|
771
|
+
/** Decoder family. */
|
|
772
|
+
readonly type: "string";
|
|
773
|
+
/** Grammar the whole literal has to satisfy. */
|
|
774
|
+
readonly syntax: "regexp" | "json-object";
|
|
775
|
+
/** For `json-object`, the grammar every property value has to satisfy. */
|
|
776
|
+
readonly entries?: "regexp";
|
|
777
|
+
/** Human-readable fix suggestion shown by the CLI (stage 4). */
|
|
778
|
+
readonly suggestion: string;
|
|
779
|
+
}
|
|
743
780
|
/** A statically checkable semantic contract on one declared Stimulus Value. */
|
|
744
781
|
type ValueConstraint = NumericValueConstraint | StringValueConstraint;
|
|
745
782
|
/**
|
|
@@ -769,7 +806,7 @@ type DiagnosticSeverity = "error" | "warning";
|
|
|
769
806
|
* for testing, machine-readable output, and `data-stimeo-ignore` suppression
|
|
770
807
|
* lists (which is why the set also exists as a runtime array).
|
|
771
808
|
*/
|
|
772
|
-
declare const DIAGNOSTIC_CODES: readonly ["unknown-controller", "unknown-target", "unknown-value", "invalid-value", "unknown-action-controller", "unknown-action-method", "orphan-target", "missing-required-target", "missing-conditional-target", "missing-required-action", "missing-action-completion", "missing-aria", "invalid-aria-value", "keyboard-inaccessible", "invalid-host", "unresolved-idref", "managed-aria", "composition-mismatch", "missing-companion", "undeclared-target", "cardinality-violation", "forbidden-aria", "missing-announcer", "unknown-ignore-code"];
|
|
809
|
+
declare const DIAGNOSTIC_CODES: readonly ["unknown-controller", "unknown-target", "unknown-value", "invalid-value", "unknown-action-controller", "unknown-action-method", "orphan-target", "missing-required-target", "missing-conditional-target", "missing-required-action", "missing-action-completion", "missing-action-event", "missing-aria", "invalid-aria-value", "keyboard-inaccessible", "invalid-host", "unresolved-idref", "managed-aria", "composition-mismatch", "missing-companion", "undeclared-target", "cardinality-violation", "forbidden-aria", "missing-announcer", "unknown-ignore-code"];
|
|
773
810
|
/** See {@link DIAGNOSTIC_CODES}. */
|
|
774
811
|
type DiagnosticCode = (typeof DIAGNOSTIC_CODES)[number];
|
|
775
812
|
/**
|
package/dist/inspector/cli.js
CHANGED
|
@@ -69,6 +69,30 @@ function announcerSeatingDiagnostic(sources) {
|
|
|
69
69
|
};
|
|
70
70
|
}
|
|
71
71
|
|
|
72
|
+
// src/utils/declared_value.ts
|
|
73
|
+
function parseDeclared(raw, parse, fallback) {
|
|
74
|
+
try {
|
|
75
|
+
return parse(raw);
|
|
76
|
+
} catch {
|
|
77
|
+
return fallback;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
function compileRegExp(source, anchor = "none") {
|
|
81
|
+
return parseDeclared(
|
|
82
|
+
source,
|
|
83
|
+
(text) => {
|
|
84
|
+
const bare = new RegExp(text);
|
|
85
|
+
return anchor === "exact" ? new RegExp(`^(?:${text})$`) : bare;
|
|
86
|
+
},
|
|
87
|
+
null
|
|
88
|
+
);
|
|
89
|
+
}
|
|
90
|
+
function parseJsonObject(raw) {
|
|
91
|
+
const parsed = parseDeclared(raw, (text) => JSON.parse(text), null);
|
|
92
|
+
if (parsed === null || typeof parsed !== "object" || Array.isArray(parsed)) return null;
|
|
93
|
+
return parsed;
|
|
94
|
+
}
|
|
95
|
+
|
|
72
96
|
// src/inspector/html_parser.ts
|
|
73
97
|
var ERB_ELEMENT_TAG = "#erb";
|
|
74
98
|
var VOID_ELEMENTS = /* @__PURE__ */ new Set([
|
|
@@ -987,7 +1011,21 @@ function parseValueAttr(attrName, knownIdentifiers) {
|
|
|
987
1011
|
const valueGuess = dash === -1 ? "" : rest.slice(dash + 1);
|
|
988
1012
|
return { identifier: null, valueToken: valueGuess || identifierGuess };
|
|
989
1013
|
}
|
|
990
|
-
|
|
1014
|
+
var DEFAULT_EVENT_NAMES = {
|
|
1015
|
+
a: "click",
|
|
1016
|
+
button: "click",
|
|
1017
|
+
details: "toggle",
|
|
1018
|
+
form: "submit",
|
|
1019
|
+
input: "input",
|
|
1020
|
+
select: "change",
|
|
1021
|
+
textarea: "input"
|
|
1022
|
+
};
|
|
1023
|
+
function defaultEventFor(host) {
|
|
1024
|
+
if (!host) return "";
|
|
1025
|
+
if (host.tag === "input" && host.inputType === "submit") return "click";
|
|
1026
|
+
return DEFAULT_EVENT_NAMES[host.tag] ?? "";
|
|
1027
|
+
}
|
|
1028
|
+
function actionDescriptors(dataActionValue, host) {
|
|
991
1029
|
const descriptors = [];
|
|
992
1030
|
for (const descriptor of dataActionValue.split(/\s+/)) {
|
|
993
1031
|
const hash = descriptor.indexOf("#");
|
|
@@ -1000,6 +1038,8 @@ function actionDescriptors(dataActionValue) {
|
|
|
1000
1038
|
lhs = lhs.slice(arrow + 2);
|
|
1001
1039
|
const at = eventType.indexOf("@");
|
|
1002
1040
|
if (at !== -1) eventType = eventType.slice(0, at);
|
|
1041
|
+
} else {
|
|
1042
|
+
eventType = defaultEventFor(host);
|
|
1003
1043
|
}
|
|
1004
1044
|
if (!lhs.startsWith(NAMESPACE_PREFIX)) continue;
|
|
1005
1045
|
const method = /^[a-zA-Z_$][\w$]*/.exec(descriptor.slice(hash + 1))?.[0] ?? "";
|
|
@@ -1024,6 +1064,7 @@ var DIAGNOSTIC_CODES = [
|
|
|
1024
1064
|
"missing-conditional-target",
|
|
1025
1065
|
"missing-required-action",
|
|
1026
1066
|
"missing-action-completion",
|
|
1067
|
+
"missing-action-event",
|
|
1027
1068
|
"missing-aria",
|
|
1028
1069
|
"invalid-aria-value",
|
|
1029
1070
|
"keyboard-inaccessible",
|
|
@@ -1368,9 +1409,7 @@ function checkSource(source, manifest) {
|
|
|
1368
1409
|
didYouMean(parsed.valueToken, (controller?.values ?? []).map(dasherize))
|
|
1369
1410
|
);
|
|
1370
1411
|
} else if (!isDynamicValue(attr)) {
|
|
1371
|
-
const constraint = controller
|
|
1372
|
-
(candidate) => dasherize(candidate.value) === parsed.valueToken
|
|
1373
|
-
);
|
|
1412
|
+
const constraint = declaredConstraint(controller, parsed.valueToken);
|
|
1374
1413
|
if (constraint && !valueSatisfiesConstraint(attr.value, constraint)) {
|
|
1375
1414
|
const literal = constraint.type === "string" ? attr.value : attr.value.trim();
|
|
1376
1415
|
report(
|
|
@@ -1388,12 +1427,26 @@ function checkSource(source, manifest) {
|
|
|
1388
1427
|
}
|
|
1389
1428
|
}
|
|
1390
1429
|
if (attr.name === "data-action") {
|
|
1391
|
-
|
|
1430
|
+
const host = {
|
|
1431
|
+
tag: node.tag,
|
|
1432
|
+
inputType: node.attrs.find((a) => a.name === "type")?.value
|
|
1433
|
+
};
|
|
1434
|
+
for (const { identifier, method, eventType } of actionDescriptors(attr.value, host)) {
|
|
1392
1435
|
const controller = known[identifier];
|
|
1393
1436
|
if (controller && method.length > 0) {
|
|
1394
1437
|
const owner = findOwner(node, identifier);
|
|
1395
1438
|
if (owner) recordAction(owner, identifier, node, method, eventType);
|
|
1396
1439
|
}
|
|
1440
|
+
if (controller && method.length > 0 && eventType === "" && node.origin === "markup" && !isDynamicValue(attr)) {
|
|
1441
|
+
report(
|
|
1442
|
+
node,
|
|
1443
|
+
"missing-action-event",
|
|
1444
|
+
"error",
|
|
1445
|
+
`"${identifier}#${method}" omits the event and <${node.tag}> has no default one, so Stimulus never binds it.`,
|
|
1446
|
+
attr,
|
|
1447
|
+
`Name the event: data-action="<event>->${identifier}#${method}".`
|
|
1448
|
+
);
|
|
1449
|
+
}
|
|
1397
1450
|
if (!controller) {
|
|
1398
1451
|
const best = nearestName(identifier, knownIdentifiers);
|
|
1399
1452
|
report(
|
|
@@ -1859,8 +1912,13 @@ function checkSource(source, manifest) {
|
|
|
1859
1912
|
diagnostics.sort((a, b) => a.line - b.line || a.column - b.column);
|
|
1860
1913
|
return diagnostics;
|
|
1861
1914
|
}
|
|
1915
|
+
function declaredConstraint(controller, valueToken) {
|
|
1916
|
+
const matches = (candidate) => dasherize(candidate.value) === valueToken;
|
|
1917
|
+
const syntax = controller?.valueSyntaxConstraints;
|
|
1918
|
+
return controller?.valueConstraints.find(matches) ?? (Array.isArray(syntax) ? syntax.find(matches) : void 0);
|
|
1919
|
+
}
|
|
1862
1920
|
function valueSatisfiesConstraint(raw, constraint) {
|
|
1863
|
-
if (constraint.type === "string") return
|
|
1921
|
+
if (constraint.type === "string") return stringValueSatisfies(raw, constraint);
|
|
1864
1922
|
const value = decodeNumericValue(raw);
|
|
1865
1923
|
if (Number.isNaN(value)) return false;
|
|
1866
1924
|
if (constraint.finite && !Number.isFinite(value)) return false;
|
|
@@ -1871,8 +1929,18 @@ function valueSatisfiesConstraint(raw, constraint) {
|
|
|
1871
1929
|
function decodeNumericValue(raw) {
|
|
1872
1930
|
return Number(raw.replace(/_/g, ""));
|
|
1873
1931
|
}
|
|
1932
|
+
function stringValueSatisfies(raw, constraint) {
|
|
1933
|
+
if (!("syntax" in constraint)) return constraint.allowedValues.includes(raw);
|
|
1934
|
+
if (constraint.syntax === "regexp") return compileRegExp(raw, "exact") !== null;
|
|
1935
|
+
if (raw === "") return true;
|
|
1936
|
+
const parsed = parseJsonObject(raw);
|
|
1937
|
+
if (parsed === null) return false;
|
|
1938
|
+
return Object.values(parsed).every(
|
|
1939
|
+
(source) => typeof source === "string" && (constraint.entries !== "regexp" || compileRegExp(source, "exact") !== null)
|
|
1940
|
+
);
|
|
1941
|
+
}
|
|
1874
1942
|
function describeValueConstraint(constraint) {
|
|
1875
|
-
if (constraint.type === "string") return
|
|
1943
|
+
if (constraint.type === "string") return describeStringConstraint(constraint);
|
|
1876
1944
|
const parts = [constraint.finite ? "a finite number" : "a number"];
|
|
1877
1945
|
if (constraint.greaterThan !== void 0) {
|
|
1878
1946
|
parts.push(`greater than ${constraint.greaterThan}`);
|
|
@@ -1880,6 +1948,11 @@ function describeValueConstraint(constraint) {
|
|
|
1880
1948
|
if (constraint.integer) parts.push("with no fractional part");
|
|
1881
1949
|
return parts.join(" ");
|
|
1882
1950
|
}
|
|
1951
|
+
function describeStringConstraint(constraint) {
|
|
1952
|
+
if (!("syntax" in constraint)) return `one of ${list(constraint.allowedValues)}`;
|
|
1953
|
+
if (constraint.syntax === "regexp") return "a valid regular expression";
|
|
1954
|
+
return constraint.entries === "regexp" ? "a JSON object whose values are valid regular expressions" : "a JSON object of strings";
|
|
1955
|
+
}
|
|
1883
1956
|
var UNRESOLVED_TARGET_HINT = "Part of this scope is rendered by a helper or a non-literal data: hash, so the target may exist at runtime.";
|
|
1884
1957
|
var UNRESOLVED_HOST_HINT = "An enclosing helper's data: option is not a literal hash, so the host controller may be declared at runtime.";
|
|
1885
1958
|
function hasReadableMarkup(el) {
|
|
@@ -2265,7 +2338,7 @@ Usage:
|
|
|
2265
2338
|
Check HTML/ERB files (or directories) for
|
|
2266
2339
|
unknown or misused stimeo--* controllers,
|
|
2267
2340
|
targets, values and action methods.
|
|
2268
|
-
stimeo catalog [--json] Print the
|
|
2341
|
+
stimeo catalog [--json] Print the controller catalog
|
|
2269
2342
|
(identifiers, targets, values, actions,
|
|
2270
2343
|
events).
|
|
2271
2344
|
stimeo mcp Run a Model Context Protocol server over
|