@maroonedog/luq 2.2.0 → 2.3.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/README.md +47 -602
- package/dist/builder/compile-declarations.d.ts +7 -1
- package/dist/builder/compile-declarations.js +18 -8
- package/dist/builder/compile-declarations.mjs +18 -8
- package/dist/builder/create-builder.js +2 -3
- package/dist/builder/create-builder.mjs +2 -3
- package/dist/builder/create-field-builder.js +13 -1
- package/dist/builder/create-field-builder.mjs +13 -1
- package/dist/builder/declared-calls-store.d.ts +9 -0
- package/dist/builder/declared-calls-store.js +19 -0
- package/dist/builder/declared-calls-store.mjs +15 -0
- package/dist/builder/field-declared-calls.types.d.ts +6 -0
- package/dist/builder/field-declared-calls.types.js +2 -0
- package/dist/builder/field-declared-calls.types.mjs +1 -0
- package/dist/builder/field-entry.types.d.ts +9 -3
- package/dist/builder/field-options.types.d.ts +26 -0
- package/dist/chain/bundle-paths.types.d.ts +9 -12
- package/dist/chain/chain-node-store.d.ts +5 -0
- package/dist/chain/chain-node-store.js +15 -0
- package/dist/chain/chain-node-store.mjs +11 -0
- package/dist/chain/collect-field-rules.d.ts +13 -2
- package/dist/chain/collect-field-rules.js +10 -3
- package/dist/chain/collect-field-rules.mjs +10 -3
- package/dist/chain/create-chain-node.js +19 -9
- package/dist/chain/create-chain-node.mjs +19 -9
- package/dist/chain/declaration-recorder.port.d.ts +31 -0
- package/dist/chain/declaration-recorder.port.js +17 -0
- package/dist/chain/declaration-recorder.port.mjs +13 -0
- package/dist/chain/declared-call.types.d.ts +15 -0
- package/dist/chain/declared-call.types.js +2 -0
- package/dist/chain/declared-call.types.mjs +1 -0
- package/dist/chain/index.d.ts +3 -1
- package/dist/compile/compile-array-node.js +1 -0
- package/dist/compile/compile-array-node.mjs +1 -0
- package/dist/compile/compile-field.d.ts +1 -0
- package/dist/compile/compile-field.js +8 -6
- package/dist/compile/compile-field.mjs +8 -6
- package/dist/compile/compile-schema.js +4 -0
- package/dist/compile/compile-schema.mjs +4 -0
- package/dist/compile/group-array-fields.d.ts +1 -0
- package/dist/compile/split-rules-by-kind.js +10 -14
- package/dist/compile/split-rules-by-kind.mjs +10 -14
- package/dist/compile/validation-plan.types.d.ts +19 -6
- package/dist/core/type-erasure.d.ts +36 -30
- package/dist/core/type-erasure.js +36 -30
- package/dist/core/type-erasure.mjs +36 -30
- package/dist/json-schema/build-from-schema.js +8 -1
- package/dist/json-schema/build-from-schema.mjs +8 -1
- package/dist/json-schema/declare-additional-properties.d.ts +7 -7
- package/dist/json-schema/declare-additional-properties.js +7 -7
- package/dist/json-schema/declare-additional-properties.mjs +7 -7
- package/dist/json-schema/declare-object-keywords.js +4 -4
- package/dist/json-schema/declare-object-keywords.mjs +4 -4
- package/dist/json-schema/follow-json-pointer.d.ts +7 -6
- package/dist/json-schema/follow-json-pointer.js +24 -24
- package/dist/json-schema/follow-json-pointer.mjs +24 -24
- package/dist/json-schema/ref-resolution-error.js +3 -3
- package/dist/json-schema/ref-resolution-error.mjs +3 -3
- package/dist/json-schema/schema-registry.js +12 -11
- package/dist/json-schema/schema-registry.mjs +12 -11
- package/dist/json-schema/uri-reference.js +12 -12
- package/dist/json-schema/uri-reference.mjs +12 -12
- package/dist/path/create-value-writer.js +12 -12
- package/dist/path/create-value-writer.mjs +12 -12
- package/dist/path/reserved-segment.d.ts +16 -16
- package/dist/path/reserved-segment.js +17 -21
- package/dist/path/reserved-segment.mjs +17 -21
- package/dist/plugins/index.generated.js +2 -2
- package/dist/plugins/index.generated.mjs +2 -2
- package/dist/plugins/manifest.generated.js +2 -2
- package/dist/plugins/manifest.generated.mjs +2 -2
- package/dist/plugins/object-additional-properties/select-additional-keys.d.ts +8 -8
- package/dist/plugins/object-additional-properties/select-additional-keys.js +16 -16
- package/dist/plugins/object-additional-properties/select-additional-keys.mjs +16 -16
- package/dist/plugins/stitch/stitch.d.ts +10 -14
- package/dist/plugins/stitch-with/stitch-with.d.ts +1 -1
- package/dist/plugins/stitch-with/stitch-with.js +22 -24
- package/dist/plugins/stitch-with/stitch-with.mjs +22 -24
- package/dist/plugins/string-min/string-min.js +6 -8
- package/dist/plugins/string-min/string-min.mjs +6 -8
- package/dist/presets/presets.d.ts +10 -11
- package/dist/presets/presets.js +22 -23
- package/dist/presets/presets.mjs +22 -23
- package/dist/runtime/create-field-validator.js +4 -6
- package/dist/runtime/create-field-validator.mjs +4 -6
- package/dist/runtime/create-validator.js +11 -11
- package/dist/runtime/create-validator.mjs +11 -11
- package/dist/runtime/output-writer.js +5 -1
- package/dist/runtime/output-writer.mjs +5 -1
- package/dist/runtime/run-array-node.js +6 -6
- package/dist/runtime/run-array-node.mjs +6 -6
- package/dist/runtime/run-field.js +18 -19
- package/dist/runtime/run-field.mjs +18 -19
- package/dist/standard-schema/assemble-json-schema.d.ts +4 -0
- package/dist/standard-schema/assemble-json-schema.js +95 -0
- package/dist/standard-schema/assemble-json-schema.mjs +92 -0
- package/dist/standard-schema/declaration-recorder.d.ts +6 -0
- package/dist/standard-schema/declaration-recorder.js +30 -0
- package/dist/standard-schema/declaration-recorder.mjs +27 -0
- package/dist/standard-schema/declarations-unavailable-error.d.ts +4 -0
- package/dist/standard-schema/declarations-unavailable-error.js +32 -0
- package/dist/standard-schema/declarations-unavailable-error.mjs +28 -0
- package/dist/standard-schema/emit-field-schema.d.ts +9 -0
- package/dist/standard-schema/emit-field-schema.js +68 -0
- package/dist/standard-schema/emit-field-schema.mjs +65 -0
- package/dist/standard-schema/index.d.ts +5 -0
- package/dist/standard-schema/index.js +9 -1
- package/dist/standard-schema/index.mjs +4 -0
- package/dist/standard-schema/json-schema-target.d.ts +6 -0
- package/dist/standard-schema/json-schema-target.js +44 -0
- package/dist/standard-schema/json-schema-target.mjs +39 -0
- package/dist/standard-schema/plugin-keyword-map.d.ts +3 -0
- package/dist/standard-schema/plugin-keyword-map.js +93 -0
- package/dist/standard-schema/plugin-keyword-map.mjs +90 -0
- package/dist/standard-schema/split-issue-path.d.ts +6 -4
- package/dist/standard-schema/split-issue-path.js +15 -13
- package/dist/standard-schema/split-issue-path.mjs +15 -13
- package/dist/standard-schema/standard-schema.types.d.ts +8 -7
- package/dist/standard-schema/standard-schema.types.js +6 -6
- package/dist/standard-schema/standard-schema.types.mjs +6 -6
- package/dist/standard-schema/to-standard-json-schema.d.ts +19 -0
- package/dist/standard-schema/to-standard-json-schema.js +36 -0
- package/dist/standard-schema/to-standard-json-schema.mjs +33 -0
- package/dist/standard-schema/to-standard-schema.d.ts +16 -15
- package/dist/standard-schema/to-standard-schema.js +15 -22
- package/dist/standard-schema/to-standard-schema.mjs +15 -22
- package/dist/standard-schema/unrepresentable-rule-error.d.ts +15 -0
- package/dist/standard-schema/unrepresentable-rule-error.js +43 -0
- package/dist/standard-schema/unrepresentable-rule-error.mjs +38 -0
- package/dist/types/index.d.ts +12 -12
- package/dist/types/index.js +7 -7
- package/dist/types/index.mjs +7 -7
- package/package.json +1 -1
|
@@ -1,24 +1,24 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* `Object.prototype
|
|
2
|
+
* Keys that share a name with something on `Object.prototype`.
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
4
|
+
* **This is no longer a deny list.** Refusing these in a declared path was
|
|
5
|
+
* over-broad: only writing is dangerous, and of the three only "__proto__"
|
|
6
|
+
* really is.
|
|
7
7
|
*
|
|
8
|
-
*
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
*
|
|
8
|
+
* reading own properties only, checked with hasOwnProperty.call, so the
|
|
9
|
+
* prototype chain is never walked to begin with
|
|
10
|
+
* writing `target[key] = value` on "__proto__" invokes the ACCESSOR on
|
|
11
|
+
* Object.prototype: it creates no own property and swaps the
|
|
12
|
+
* prototype instead. "constructor" and "prototype" are data
|
|
13
|
+
* properties, so assigning them only makes an own property and
|
|
14
|
+
* pollutes nothing
|
|
14
15
|
*
|
|
15
|
-
*
|
|
16
|
-
*
|
|
17
|
-
* `{ "properties": { "__proto__": ... } }`
|
|
18
|
-
* ようになった (JSON-Schema-Test-Suite の properties.json が要求している)。
|
|
16
|
+
* Writing through defineProperty instead of assignment closes that route.
|
|
17
|
+
* Refusing by name became unnecessary, which is what allows a schema like
|
|
18
|
+
* `{ "properties": { "__proto__": ... } }` to be validated at all.
|
|
19
19
|
*
|
|
20
|
-
*
|
|
21
|
-
*
|
|
20
|
+
* The list stays. Tests use it to name the keys they check Object.prototype
|
|
21
|
+
* against.
|
|
22
22
|
*/
|
|
23
23
|
export declare const RESERVED_SEGMENTS: readonly string[];
|
|
24
24
|
/** Thrown at BUILD time for every malformed or unsafe path. A declared rule
|
|
@@ -14,26 +14,26 @@ exports.PathSyntaxError = exports.RESERVED_SEGMENTS = void 0;
|
|
|
14
14
|
exports.isReservedSegment = isReservedSegment;
|
|
15
15
|
exports.assertDeclarableKey = assertDeclarableKey;
|
|
16
16
|
/**
|
|
17
|
-
* `Object.prototype
|
|
17
|
+
* Keys that share a name with something on `Object.prototype`.
|
|
18
18
|
*
|
|
19
|
-
*
|
|
20
|
-
*
|
|
21
|
-
*
|
|
19
|
+
* **This is no longer a deny list.** Refusing these in a declared path was
|
|
20
|
+
* over-broad: only writing is dangerous, and of the three only "__proto__"
|
|
21
|
+
* really is.
|
|
22
22
|
*
|
|
23
|
-
*
|
|
24
|
-
*
|
|
25
|
-
*
|
|
26
|
-
*
|
|
27
|
-
*
|
|
28
|
-
*
|
|
23
|
+
* reading own properties only, checked with hasOwnProperty.call, so the
|
|
24
|
+
* prototype chain is never walked to begin with
|
|
25
|
+
* writing `target[key] = value` on "__proto__" invokes the ACCESSOR on
|
|
26
|
+
* Object.prototype: it creates no own property and swaps the
|
|
27
|
+
* prototype instead. "constructor" and "prototype" are data
|
|
28
|
+
* properties, so assigning them only makes an own property and
|
|
29
|
+
* pollutes nothing
|
|
29
30
|
*
|
|
30
|
-
*
|
|
31
|
-
*
|
|
32
|
-
* `{ "properties": { "__proto__": ... } }`
|
|
33
|
-
* ようになった (JSON-Schema-Test-Suite の properties.json が要求している)。
|
|
31
|
+
* Writing through defineProperty instead of assignment closes that route.
|
|
32
|
+
* Refusing by name became unnecessary, which is what allows a schema like
|
|
33
|
+
* `{ "properties": { "__proto__": ... } }` to be validated at all.
|
|
34
34
|
*
|
|
35
|
-
*
|
|
36
|
-
*
|
|
35
|
+
* The list stays. Tests use it to name the keys they check Object.prototype
|
|
36
|
+
* against.
|
|
37
37
|
*/
|
|
38
38
|
exports.RESERVED_SEGMENTS = Object.freeze([
|
|
39
39
|
"__proto__",
|
|
@@ -80,9 +80,5 @@ function assertDeclarableKey(key, source) {
|
|
|
80
80
|
throw new PathSyntaxError(source, `the key ${JSON.stringify(key)} contains a bracket; "[*]" is the only ` +
|
|
81
81
|
"bracket form and it must trail a key");
|
|
82
82
|
}
|
|
83
|
-
//
|
|
84
|
-
// コメントに書いてある。要約すると、危険なのは書き込みだけで、その書き込みは
|
|
85
|
-
// create-value-writer.ts が defineProperty に移したので安全になった。
|
|
86
|
-
// 名前で拒否する必要が無くなり、JSON Schema が "__proto__" というキーを
|
|
87
|
-
// 持つオブジェクトを検証できるようになった。
|
|
83
|
+
// Reserved segments are deliberately NOT refused here. See RESERVED_SEGMENTS.
|
|
88
84
|
}
|
|
@@ -9,26 +9,26 @@
|
|
|
9
9
|
// dependent for no gain.
|
|
10
10
|
// ===========================================================================
|
|
11
11
|
/**
|
|
12
|
-
* `Object.prototype
|
|
12
|
+
* Keys that share a name with something on `Object.prototype`.
|
|
13
13
|
*
|
|
14
|
-
*
|
|
15
|
-
*
|
|
16
|
-
*
|
|
14
|
+
* **This is no longer a deny list.** Refusing these in a declared path was
|
|
15
|
+
* over-broad: only writing is dangerous, and of the three only "__proto__"
|
|
16
|
+
* really is.
|
|
17
17
|
*
|
|
18
|
-
*
|
|
19
|
-
*
|
|
20
|
-
*
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
*
|
|
18
|
+
* reading own properties only, checked with hasOwnProperty.call, so the
|
|
19
|
+
* prototype chain is never walked to begin with
|
|
20
|
+
* writing `target[key] = value` on "__proto__" invokes the ACCESSOR on
|
|
21
|
+
* Object.prototype: it creates no own property and swaps the
|
|
22
|
+
* prototype instead. "constructor" and "prototype" are data
|
|
23
|
+
* properties, so assigning them only makes an own property and
|
|
24
|
+
* pollutes nothing
|
|
24
25
|
*
|
|
25
|
-
*
|
|
26
|
-
*
|
|
27
|
-
* `{ "properties": { "__proto__": ... } }`
|
|
28
|
-
* ようになった (JSON-Schema-Test-Suite の properties.json が要求している)。
|
|
26
|
+
* Writing through defineProperty instead of assignment closes that route.
|
|
27
|
+
* Refusing by name became unnecessary, which is what allows a schema like
|
|
28
|
+
* `{ "properties": { "__proto__": ... } }` to be validated at all.
|
|
29
29
|
*
|
|
30
|
-
*
|
|
31
|
-
*
|
|
30
|
+
* The list stays. Tests use it to name the keys they check Object.prototype
|
|
31
|
+
* against.
|
|
32
32
|
*/
|
|
33
33
|
export const RESERVED_SEGMENTS = Object.freeze([
|
|
34
34
|
"__proto__",
|
|
@@ -74,9 +74,5 @@ export function assertDeclarableKey(key, source) {
|
|
|
74
74
|
throw new PathSyntaxError(source, `the key ${JSON.stringify(key)} contains a bracket; "[*]" is the only ` +
|
|
75
75
|
"bracket form and it must trail a key");
|
|
76
76
|
}
|
|
77
|
-
//
|
|
78
|
-
// コメントに書いてある。要約すると、危険なのは書き込みだけで、その書き込みは
|
|
79
|
-
// create-value-writer.ts が defineProperty に移したので安全になった。
|
|
80
|
-
// 名前で拒否する必要が無くなり、JSON Schema が "__proto__" というキーを
|
|
81
|
-
// 持つオブジェクトを検証できるようになった。
|
|
77
|
+
// Reserved segments are deliberately NOT refused here. See RESERVED_SEGMENTS.
|
|
82
78
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
// GENERATED FILE -
|
|
3
|
-
//
|
|
2
|
+
// GENERATED FILE - do not edit by hand.
|
|
3
|
+
// Generated by scripts/catalog/build-plugin-catalog.ts out of the plugin directory structure.
|
|
4
4
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
5
5
|
exports.stringDatetimePlugin = exports.stringDatePlugin = exports.stringContentMediaTypePlugin = exports.stringContentEncodingPlugin = exports.stringBase64Plugin = exports.stringAlphanumericPlugin = exports.stitchWithPlugin = exports.stitchPlugin = exports.skipPlugin = exports.requiredIfPlugin = exports.requiredPlugin = exports.readOnlyPlugin = exports.orFailPlugin = exports.optionalIfPlugin = exports.optionalPlugin = exports.oneOfPlugin = exports.objectRecursivelyPlugin = exports.objectPropertyNamesPlugin = exports.objectPatternPropertiesPlugin = exports.objectMinPropertiesPlugin = exports.objectMaxPropertiesPlugin = exports.objectDependentSchemasPlugin = exports.objectDependentRequiredPlugin = exports.objectAdditionalPropertiesSchemaPlugin = exports.objectAdditionalPropertiesPlugin = exports.objectPlugin = exports.numberRangePlugin = exports.numberPositivePlugin = exports.numberNegativePlugin = exports.numberMultipleOfPlugin = exports.numberMinPlugin = exports.numberMaxPlugin = exports.numberIntegerPlugin = exports.numberFinitePlugin = exports.nullablePlugin = exports.literalPlugin = exports.jsonSchemaFullFeaturePlugin = exports.jsonSchemaPlugin = exports.fromContextPlugin = exports.customPlugin = exports.conditionalSchemaPlugin = exports.compareFieldPlugin = exports.booleanTruthyPlugin = exports.booleanFalsyPlugin = exports.arrayUniquePlugin = exports.arrayMinLengthPlugin = exports.arrayMaxLengthPlugin = exports.arrayIncludesPlugin = exports.arrayEachPlugin = exports.arrayContainsPlugin = void 0;
|
|
6
6
|
exports.writeOnlyPlugin = exports.validateIfPlugin = exports.uuidPlugin = exports.unionGuardPlugin = exports.tupleBuilderPlugin = exports.transformPlugin = exports.stringUrlPlugin = exports.stringUriTemplatePlugin = exports.stringUriReferencePlugin = exports.stringTimePlugin = exports.stringStartsWithPlugin = exports.stringRelativeJsonPointerPlugin = exports.stringRegexPlugin = exports.stringPatternPlugin = exports.stringMinPlugin = exports.stringMaxPlugin = exports.stringJsonPointerPlugin = exports.stringIriReferencePlugin = exports.stringIriPlugin = exports.stringIpv6Plugin = exports.stringIpv4Plugin = exports.stringIdnHostnamePlugin = exports.stringIdnEmailPlugin = exports.stringHostnamePlugin = exports.stringExactLengthPlugin = exports.stringEndsWithPlugin = exports.stringEmailPlugin = exports.stringDurationPlugin = void 0;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
// GENERATED FILE -
|
|
2
|
-
//
|
|
1
|
+
// GENERATED FILE - do not edit by hand.
|
|
2
|
+
// Generated by scripts/catalog/build-plugin-catalog.ts out of the plugin directory structure.
|
|
3
3
|
export { arrayContainsPlugin } from "./array-contains/index.mjs";
|
|
4
4
|
export { arrayEachPlugin } from "./array-each/index.mjs";
|
|
5
5
|
export { arrayIncludesPlugin } from "./array-includes/index.mjs";
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
// GENERATED FILE -
|
|
3
|
-
//
|
|
2
|
+
// GENERATED FILE - do not edit by hand.
|
|
3
|
+
// Generated by scripts/catalog/build-plugin-catalog.ts out of the plugin directory structure.
|
|
4
4
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
5
5
|
exports.PLUGIN_MANIFEST = void 0;
|
|
6
6
|
exports.PLUGIN_MANIFEST = [
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
// GENERATED FILE -
|
|
2
|
-
//
|
|
1
|
+
// GENERATED FILE - do not edit by hand.
|
|
2
|
+
// Generated by scripts/catalog/build-plugin-catalog.ts out of the plugin directory structure.
|
|
3
3
|
export const PLUGIN_MANIFEST = [
|
|
4
4
|
{ directoryName: "array-contains", subpathName: "arrayContains", tier: "isolated", entryFile: "src/plugins/array-contains/index.ts", exportedSymbols: ["arrayContainsPlugin"] },
|
|
5
5
|
{ directoryName: "array-each", subpathName: "arrayEach", tier: "isolated", entryFile: "src/plugins/array-each/index.ts", exportedSymbols: ["arrayEachPlugin"] },
|
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
3
|
-
*
|
|
4
|
-
*
|
|
2
|
+
* Patterns are compiled once, at build time, matching the design where
|
|
3
|
+
* validation only runs what was already assembled. Compiling per key would
|
|
4
|
+
* cost O(keys × patterns) compilations on every call.
|
|
5
5
|
*
|
|
6
|
-
*
|
|
7
|
-
*
|
|
8
|
-
*
|
|
6
|
+
* A broken pattern is ignored rather than fatal. Draft-07 asks for ECMA-262
|
|
7
|
+
* regular expressions and real documents arrive with dialect differences;
|
|
8
|
+
* having that one pattern match nothing beats refusing the whole build.
|
|
9
9
|
*/
|
|
10
10
|
export declare function compilePatterns(patterns: readonly string[] | undefined): readonly RegExp[];
|
|
11
11
|
/**
|
|
12
|
-
*
|
|
13
|
-
*
|
|
12
|
+
* Returns the keys matched by neither a declared name nor any pattern,
|
|
13
|
+
* preserving the input's enumeration order so issue output stays stable.
|
|
14
14
|
*/
|
|
15
15
|
export declare function selectAdditionalKeys(value: Readonly<Record<string, unknown>>, known: ReadonlySet<string>, patterns: readonly RegExp[]): readonly string[];
|
|
@@ -2,25 +2,25 @@
|
|
|
2
2
|
// ===========================================================================
|
|
3
3
|
// L7 src/plugins/object-additional-properties/select-additional-keys.ts
|
|
4
4
|
//
|
|
5
|
-
//
|
|
5
|
+
// Which keys count as "additional". Used by both the boolean form and the
|
|
6
|
+
// schema form.
|
|
6
7
|
//
|
|
7
|
-
// Draft-07 §6.5.4
|
|
8
|
-
// patternProperties
|
|
9
|
-
// `{"patternProperties":{"^v":{}},"additionalProperties":false}`
|
|
10
|
-
// {"vroom":2}
|
|
11
|
-
// "patternProperties are not additional properties" がそれを突く)。
|
|
8
|
+
// Draft-07 §6.5.4 defines them as the keys matched by neither `properties`
|
|
9
|
+
// nor `patternProperties`. Miss the patterns and
|
|
10
|
+
// `{"patternProperties":{"^v":{}},"additionalProperties":false}` wrongly
|
|
11
|
+
// rejects {"vroom":2}.
|
|
12
12
|
// ===========================================================================
|
|
13
13
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
14
14
|
exports.compilePatterns = compilePatterns;
|
|
15
15
|
exports.selectAdditionalKeys = selectAdditionalKeys;
|
|
16
16
|
/**
|
|
17
|
-
*
|
|
18
|
-
*
|
|
19
|
-
*
|
|
17
|
+
* Patterns are compiled once, at build time, matching the design where
|
|
18
|
+
* validation only runs what was already assembled. Compiling per key would
|
|
19
|
+
* cost O(keys × patterns) compilations on every call.
|
|
20
20
|
*
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
*
|
|
21
|
+
* A broken pattern is ignored rather than fatal. Draft-07 asks for ECMA-262
|
|
22
|
+
* regular expressions and real documents arrive with dialect differences;
|
|
23
|
+
* having that one pattern match nothing beats refusing the whole build.
|
|
24
24
|
*/
|
|
25
25
|
function compilePatterns(patterns) {
|
|
26
26
|
if (patterns === undefined || patterns.length === 0)
|
|
@@ -32,19 +32,19 @@ function compilePatterns(patterns) {
|
|
|
32
32
|
}
|
|
33
33
|
catch {
|
|
34
34
|
try {
|
|
35
|
-
// "u"
|
|
35
|
+
// Some real patterns fail only under "u". Try again without it.
|
|
36
36
|
compiled.push(new RegExp(pattern));
|
|
37
37
|
}
|
|
38
38
|
catch {
|
|
39
|
-
//
|
|
39
|
+
// Failing both ways, treat this pattern as matching nothing.
|
|
40
40
|
}
|
|
41
41
|
}
|
|
42
42
|
}
|
|
43
43
|
return Object.freeze(compiled);
|
|
44
44
|
}
|
|
45
45
|
/**
|
|
46
|
-
*
|
|
47
|
-
*
|
|
46
|
+
* Returns the keys matched by neither a declared name nor any pattern,
|
|
47
|
+
* preserving the input's enumeration order so issue output stays stable.
|
|
48
48
|
*/
|
|
49
49
|
function selectAdditionalKeys(value, known, patterns) {
|
|
50
50
|
return Object.keys(value).filter((key) => !known.has(key) && !patterns.some((pattern) => pattern.test(key)));
|
|
@@ -1,22 +1,22 @@
|
|
|
1
1
|
// ===========================================================================
|
|
2
2
|
// L7 src/plugins/object-additional-properties/select-additional-keys.ts
|
|
3
3
|
//
|
|
4
|
-
//
|
|
4
|
+
// Which keys count as "additional". Used by both the boolean form and the
|
|
5
|
+
// schema form.
|
|
5
6
|
//
|
|
6
|
-
// Draft-07 §6.5.4
|
|
7
|
-
// patternProperties
|
|
8
|
-
// `{"patternProperties":{"^v":{}},"additionalProperties":false}`
|
|
9
|
-
// {"vroom":2}
|
|
10
|
-
// "patternProperties are not additional properties" がそれを突く)。
|
|
7
|
+
// Draft-07 §6.5.4 defines them as the keys matched by neither `properties`
|
|
8
|
+
// nor `patternProperties`. Miss the patterns and
|
|
9
|
+
// `{"patternProperties":{"^v":{}},"additionalProperties":false}` wrongly
|
|
10
|
+
// rejects {"vroom":2}.
|
|
11
11
|
// ===========================================================================
|
|
12
12
|
/**
|
|
13
|
-
*
|
|
14
|
-
*
|
|
15
|
-
*
|
|
13
|
+
* Patterns are compiled once, at build time, matching the design where
|
|
14
|
+
* validation only runs what was already assembled. Compiling per key would
|
|
15
|
+
* cost O(keys × patterns) compilations on every call.
|
|
16
16
|
*
|
|
17
|
-
*
|
|
18
|
-
*
|
|
19
|
-
*
|
|
17
|
+
* A broken pattern is ignored rather than fatal. Draft-07 asks for ECMA-262
|
|
18
|
+
* regular expressions and real documents arrive with dialect differences;
|
|
19
|
+
* having that one pattern match nothing beats refusing the whole build.
|
|
20
20
|
*/
|
|
21
21
|
export function compilePatterns(patterns) {
|
|
22
22
|
if (patterns === undefined || patterns.length === 0)
|
|
@@ -28,19 +28,19 @@ export function compilePatterns(patterns) {
|
|
|
28
28
|
}
|
|
29
29
|
catch {
|
|
30
30
|
try {
|
|
31
|
-
// "u"
|
|
31
|
+
// Some real patterns fail only under "u". Try again without it.
|
|
32
32
|
compiled.push(new RegExp(pattern));
|
|
33
33
|
}
|
|
34
34
|
catch {
|
|
35
|
-
//
|
|
35
|
+
// Failing both ways, treat this pattern as matching nothing.
|
|
36
36
|
}
|
|
37
37
|
}
|
|
38
38
|
}
|
|
39
39
|
return Object.freeze(compiled);
|
|
40
40
|
}
|
|
41
41
|
/**
|
|
42
|
-
*
|
|
43
|
-
*
|
|
42
|
+
* Returns the keys matched by neither a declared name nor any pattern,
|
|
43
|
+
* preserving the input's enumeration order so issue output stays stable.
|
|
44
44
|
*/
|
|
45
45
|
export function selectAdditionalKeys(value, known, patterns) {
|
|
46
46
|
return Object.keys(value).filter((key) => !known.has(key) && !patterns.some((pattern) => pattern.test(key)));
|
|
@@ -5,11 +5,10 @@ import type { FieldRefs, StitchOut } from "../../plugin-kit/marker.types";
|
|
|
5
5
|
* The bundle handed to the check at RUN TIME, keyed by the path exactly as
|
|
6
6
|
* declared.
|
|
7
7
|
*
|
|
8
|
-
*
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
* パス文字列」という事実を書き留めておく場所だからである。
|
|
8
|
+
* Callers no longer see this type. Writing `.stitch(["price"], ...)` already
|
|
9
|
+
* fixes the set of paths, so the bundle the predicate receives is typed per
|
|
10
|
+
* key from those paths. What survives here is the run-time side's record of
|
|
11
|
+
* one fact: the keys are the path strings.
|
|
13
12
|
*/
|
|
14
13
|
export type StitchFieldValues = Readonly<Record<string, unknown>>;
|
|
15
14
|
/**
|
|
@@ -22,19 +21,16 @@ export type StitchFieldValues = Readonly<Record<string, unknown>>;
|
|
|
22
21
|
*/
|
|
23
22
|
export type StitchFieldsOf<TRoot, TFields extends readonly string[]> = PickPaths<TRoot, TFields>;
|
|
24
23
|
/**
|
|
25
|
-
*
|
|
26
|
-
*
|
|
27
|
-
*
|
|
24
|
+
* The legacy `{ valid, message? }`, name and shape unchanged. It is declared
|
|
25
|
+
* where the chain layer can reach it, so that layer never has to import a
|
|
26
|
+
* plugin to build a caller-facing type.
|
|
28
27
|
*/
|
|
29
28
|
export type StitchOutcome = CrossFieldOutcome;
|
|
30
29
|
/**
|
|
31
|
-
*
|
|
30
|
+
* The shape build() receives at run time. **Not the type a caller sees.**
|
|
32
31
|
*
|
|
33
|
-
* `.stitch(["price", "quantity"], ...)`
|
|
34
|
-
*
|
|
35
|
-
* 値の型が付く (src/chain/chain-method.types.ts の StitchOut の腕)。
|
|
36
|
-
* ここが `Record<string, unknown>` のままだったのが、その腕を足すまでの
|
|
37
|
-
* stitch である。
|
|
32
|
+
* Writing `.stitch(["price", "quantity"], ...)` already fixes the set of
|
|
33
|
+
* paths, so the bundle the predicate receives is typed per key.
|
|
38
34
|
*/
|
|
39
35
|
export type StitchCheck = (fieldValues: StitchFieldValues, value: unknown, root: unknown) => StitchOutcome;
|
|
40
36
|
/** 1.x's messageFactory context for this plugin, minus the re-run. */
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import type { MessageContextExtra } from "../../types";
|
|
2
2
|
import type { BundleOut, NarrowedChain } from "../../plugin-kit/marker.types";
|
|
3
|
-
/**
|
|
3
|
+
/** Alias to a path from the root. At run time, a table of strings. */
|
|
4
4
|
export type BundleAliasMap = Readonly<Record<string, string>>;
|
|
5
5
|
export interface StitchWithExtra extends MessageContextExtra {
|
|
6
6
|
readonly aliases: readonly string[];
|
|
@@ -3,38 +3,36 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.stitchWithPlugin = void 0;
|
|
4
4
|
// ===========================================================================
|
|
5
5
|
// L7 src/plugins/stitch-with/stitch-with.ts — EXPERIMENTAL.
|
|
6
|
-
// `stitch
|
|
6
|
+
// The typed successor to `stitch`, for cross-field validation.
|
|
7
7
|
//
|
|
8
|
-
//
|
|
9
|
-
//
|
|
10
|
-
//
|
|
11
|
-
//
|
|
8
|
+
// The point of stitching is to bring SEVERAL FIELDS INTO ONE JUDGEMENT, so
|
|
9
|
+
// the subject is the bundle itself and not each alias. Listing rules per alias
|
|
10
|
+
// is writable but cannot express `total === price * quantity`, at which point
|
|
11
|
+
// it is no longer stitching.
|
|
12
12
|
//
|
|
13
|
-
//
|
|
14
|
-
// `Readonly<Record<string, unknown
|
|
15
|
-
//
|
|
13
|
+
// One difference from `stitch`. There the bundle reaches the predicate as
|
|
14
|
+
// `Readonly<Record<string, unknown>>`, so the type says nothing about its
|
|
15
|
+
// contents. Here the bundle is assembled from a mapping and IS TYPED:
|
|
16
16
|
//
|
|
17
17
|
// .v("total", (b) => b.number.stitchWith(
|
|
18
18
|
// { cost: "price", count: "quantity" },
|
|
19
19
|
// (f) => f.object.custom((bundle) => bundle.cost * bundle.count === 100)
|
|
20
20
|
// ))
|
|
21
21
|
//
|
|
22
|
-
// `bundle`
|
|
23
|
-
//
|
|
22
|
+
// `bundle` is `{ cost: number; count: number }`, not a Record. Misspell a
|
|
23
|
+
// member or mistake its type and it fails to compile.
|
|
24
24
|
//
|
|
25
|
-
//
|
|
26
|
-
//
|
|
27
|
-
//
|
|
28
|
-
//
|
|
25
|
+
// Why aliases rather than paths as keys. A path string used as a bundle key is
|
|
26
|
+
// interpreted AS A PATH where it is declared, so `"user.name"` goes looking
|
|
27
|
+
// for `user.name` inside the bundle and never finds it, the bundle being
|
|
28
|
+
// flat. An alias is a bare identifier, so that collision cannot happen and the
|
|
29
|
+
// only things referable are the aliases actually declared.
|
|
29
30
|
//
|
|
30
|
-
//
|
|
31
|
-
// `readonly Rule[]`
|
|
32
|
-
//
|
|
33
|
-
//
|
|
34
|
-
//
|
|
35
|
-
//
|
|
36
|
-
// 1.x が同じ責務の実装を3つ持っていたのは、ここで「もう1つ書く」を選んだ
|
|
37
|
-
// からである。
|
|
31
|
+
// No judgement happens in this file. The sub-chain resolves to
|
|
32
|
+
// `readonly Rule[]` through the same route a narrowed chain takes, and the
|
|
33
|
+
// engine runs it. A bundle-specific collector in the core was built and
|
|
34
|
+
// measured; it added bytes to everyone who never stitches, so this rides the
|
|
35
|
+
// existing route instead and adds none.
|
|
38
36
|
// ===========================================================================
|
|
39
37
|
const types_1 = require("../../types");
|
|
40
38
|
const create_rule_1 = require("../../plugin-kit/create-rule");
|
|
@@ -57,7 +55,7 @@ function readMembers(aliasMap) {
|
|
|
57
55
|
read: (0, index_1.createValueReader)((0, index_1.parseFieldPath)(path)),
|
|
58
56
|
})));
|
|
59
57
|
}
|
|
60
|
-
/**
|
|
58
|
+
/** Assembles the bundle from the root; this object is the branch's subject. */
|
|
61
59
|
function collectBundle(members, root) {
|
|
62
60
|
const bundle = {};
|
|
63
61
|
for (const member of members)
|
|
@@ -76,7 +74,7 @@ exports.stitchWithPlugin = (0, plugin_definition_1.definePlugin)()({
|
|
|
76
74
|
messageFactory: ctx.messageFactory,
|
|
77
75
|
severity: ctx.severity,
|
|
78
76
|
branches: [(0, create_rule_1.branch)(BUNDLE_BRANCH_LABEL, rules)],
|
|
79
|
-
//
|
|
77
|
+
// The field's own value is not read. Only the assembled bundle is.
|
|
80
78
|
combine: (runners) => {
|
|
81
79
|
const runner = runners[0];
|
|
82
80
|
if (runner === undefined)
|
|
@@ -1,37 +1,35 @@
|
|
|
1
1
|
// ===========================================================================
|
|
2
2
|
// L7 src/plugins/stitch-with/stitch-with.ts — EXPERIMENTAL.
|
|
3
|
-
// `stitch
|
|
3
|
+
// The typed successor to `stitch`, for cross-field validation.
|
|
4
4
|
//
|
|
5
|
-
//
|
|
6
|
-
//
|
|
7
|
-
//
|
|
8
|
-
//
|
|
5
|
+
// The point of stitching is to bring SEVERAL FIELDS INTO ONE JUDGEMENT, so
|
|
6
|
+
// the subject is the bundle itself and not each alias. Listing rules per alias
|
|
7
|
+
// is writable but cannot express `total === price * quantity`, at which point
|
|
8
|
+
// it is no longer stitching.
|
|
9
9
|
//
|
|
10
|
-
//
|
|
11
|
-
// `Readonly<Record<string, unknown
|
|
12
|
-
//
|
|
10
|
+
// One difference from `stitch`. There the bundle reaches the predicate as
|
|
11
|
+
// `Readonly<Record<string, unknown>>`, so the type says nothing about its
|
|
12
|
+
// contents. Here the bundle is assembled from a mapping and IS TYPED:
|
|
13
13
|
//
|
|
14
14
|
// .v("total", (b) => b.number.stitchWith(
|
|
15
15
|
// { cost: "price", count: "quantity" },
|
|
16
16
|
// (f) => f.object.custom((bundle) => bundle.cost * bundle.count === 100)
|
|
17
17
|
// ))
|
|
18
18
|
//
|
|
19
|
-
// `bundle`
|
|
20
|
-
//
|
|
19
|
+
// `bundle` is `{ cost: number; count: number }`, not a Record. Misspell a
|
|
20
|
+
// member or mistake its type and it fails to compile.
|
|
21
21
|
//
|
|
22
|
-
//
|
|
23
|
-
//
|
|
24
|
-
//
|
|
25
|
-
//
|
|
22
|
+
// Why aliases rather than paths as keys. A path string used as a bundle key is
|
|
23
|
+
// interpreted AS A PATH where it is declared, so `"user.name"` goes looking
|
|
24
|
+
// for `user.name` inside the bundle and never finds it, the bundle being
|
|
25
|
+
// flat. An alias is a bare identifier, so that collision cannot happen and the
|
|
26
|
+
// only things referable are the aliases actually declared.
|
|
26
27
|
//
|
|
27
|
-
//
|
|
28
|
-
// `readonly Rule[]`
|
|
29
|
-
//
|
|
30
|
-
//
|
|
31
|
-
//
|
|
32
|
-
//
|
|
33
|
-
// 1.x が同じ責務の実装を3つ持っていたのは、ここで「もう1つ書く」を選んだ
|
|
34
|
-
// からである。
|
|
28
|
+
// No judgement happens in this file. The sub-chain resolves to
|
|
29
|
+
// `readonly Rule[]` through the same route a narrowed chain takes, and the
|
|
30
|
+
// engine runs it. A bundle-specific collector in the core was built and
|
|
31
|
+
// measured; it added bytes to everyone who never stitches, so this rides the
|
|
32
|
+
// existing route instead and adds none.
|
|
35
33
|
// ===========================================================================
|
|
36
34
|
import { PASS, fail, isPlainObject } from "../../types/index.mjs";
|
|
37
35
|
import { branch, composite } from "../../plugin-kit/create-rule.mjs";
|
|
@@ -54,7 +52,7 @@ function readMembers(aliasMap) {
|
|
|
54
52
|
read: createValueReader(parseFieldPath(path)),
|
|
55
53
|
})));
|
|
56
54
|
}
|
|
57
|
-
/**
|
|
55
|
+
/** Assembles the bundle from the root; this object is the branch's subject. */
|
|
58
56
|
function collectBundle(members, root) {
|
|
59
57
|
const bundle = {};
|
|
60
58
|
for (const member of members)
|
|
@@ -73,7 +71,7 @@ export const stitchWithPlugin = /*#__PURE__*/ definePlugin()({
|
|
|
73
71
|
messageFactory: ctx.messageFactory,
|
|
74
72
|
severity: ctx.severity,
|
|
75
73
|
branches: [branch(BUNDLE_BRANCH_LABEL, rules)],
|
|
76
|
-
//
|
|
74
|
+
// The field's own value is not read. Only the assembled bundle is.
|
|
77
75
|
combine: (runners) => {
|
|
78
76
|
const runner = runners[0];
|
|
79
77
|
if (runner === undefined)
|
|
@@ -23,17 +23,15 @@ exports.stringMinPlugin = (0, plugin_definition_1.definePlugin)()({
|
|
|
23
23
|
code: ctx.code,
|
|
24
24
|
messageFactory: ctx.messageFactory,
|
|
25
25
|
severity: ctx.severity,
|
|
26
|
-
// min
|
|
27
|
-
//
|
|
28
|
-
//
|
|
29
|
-
//
|
|
30
|
-
// 変えているのは、いつ止めるかだけである。受理パスで 12.7%。
|
|
26
|
+
// Stops as soon as min is reached. The full length is only needed to
|
|
27
|
+
// REPORT a failure, and a failing value is shorter than min, so that
|
|
28
|
+
// walk is short too. Counting is still by code point, not UTF-16 unit;
|
|
29
|
+
// the only thing that changed is when it stops.
|
|
31
30
|
run: (value) => {
|
|
32
31
|
if (!(0, types_1.isString)(value))
|
|
33
32
|
return types_1.PASS;
|
|
34
|
-
// min
|
|
35
|
-
//
|
|
36
|
-
// ときに実際に開いた穴で、既存のテストは一件も気づかなかった。
|
|
33
|
+
// min of 0 admits the empty string. The loop body never runs on an
|
|
34
|
+
// empty string, so without this line the empty string fails with 0.
|
|
37
35
|
if (min === 0)
|
|
38
36
|
return types_1.PASS;
|
|
39
37
|
let count = 0;
|
|
@@ -20,17 +20,15 @@ export const stringMinPlugin = /*#__PURE__*/ definePlugin()({
|
|
|
20
20
|
code: ctx.code,
|
|
21
21
|
messageFactory: ctx.messageFactory,
|
|
22
22
|
severity: ctx.severity,
|
|
23
|
-
// min
|
|
24
|
-
//
|
|
25
|
-
//
|
|
26
|
-
//
|
|
27
|
-
// 変えているのは、いつ止めるかだけである。受理パスで 12.7%。
|
|
23
|
+
// Stops as soon as min is reached. The full length is only needed to
|
|
24
|
+
// REPORT a failure, and a failing value is shorter than min, so that
|
|
25
|
+
// walk is short too. Counting is still by code point, not UTF-16 unit;
|
|
26
|
+
// the only thing that changed is when it stops.
|
|
28
27
|
run: (value) => {
|
|
29
28
|
if (!isString(value))
|
|
30
29
|
return PASS;
|
|
31
|
-
// min
|
|
32
|
-
//
|
|
33
|
-
// ときに実際に開いた穴で、既存のテストは一件も気づかなかった。
|
|
30
|
+
// min of 0 admits the empty string. The loop body never runs on an
|
|
31
|
+
// empty string, so without this line the empty string fails with 0.
|
|
34
32
|
if (min === 0)
|
|
35
33
|
return PASS;
|
|
36
34
|
let count = 0;
|