@depup/typebox 1.3.11-depup.0 → 1.3.16-depup.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 +2 -2
- package/build/format/date.d.mts +1 -1
- package/build/format/date.mjs +1 -1
- package/build/format/date_time.d.mts +2 -2
- package/build/format/date_time.mjs +3 -3
- package/build/format/email.d.mts +1 -1
- package/build/format/email.mjs +2 -2
- package/build/format/hostname.mjs +2 -10
- package/build/format/idn_email.d.mts +1 -1
- package/build/format/idn_email.mjs +3 -3
- package/build/format/idn_hostname.d.mts +1 -0
- package/build/format/idn_hostname.mjs +3 -11
- package/build/format/idna/format/bidi.d.mts +3 -0
- package/build/format/idna/format/bidi.mjs +98 -0
- package/build/format/idna/format/puny.d.mts +3 -0
- package/build/format/idna/format/puny.mjs +144 -0
- package/build/format/idna/hostname.d.mts +1 -0
- package/build/format/idna/hostname.mjs +16 -0
- package/build/format/idna/idn-hostname.d.mts +1 -0
- package/build/format/idna/idn-hostname.mjs +23 -0
- package/build/format/idna/index.d.mts +2 -0
- package/build/format/idna/index.mjs +2 -0
- package/build/format/idna/label/ascii.d.mts +1 -0
- package/build/format/idna/label/ascii.mjs +9 -0
- package/build/format/idna/label/puny.d.mts +1 -0
- package/build/format/idna/label/puny.mjs +28 -0
- package/build/format/idna/label/unicode.d.mts +1 -0
- package/build/format/idna/label/unicode.mjs +106 -0
- package/build/format/idna/pattern/pattern.d.mts +30 -0
- package/build/format/idna/pattern/pattern.mjs +70 -0
- package/build/format/ipv4.d.mts +0 -1
- package/build/format/ipv4.mjs +2 -32
- package/build/format/ipv6.mjs +2 -61
- package/build/format/iri.d.mts +2 -2
- package/build/format/iri.mjs +26 -8
- package/build/format/iri_reference.d.mts +2 -2
- package/build/format/iri_reference.mjs +9 -55
- package/build/format/regex.d.mts +1 -2
- package/build/format/regex.mjs +2 -6
- package/build/format/time.d.mts +2 -2
- package/build/format/time.mjs +19 -14
- package/build/format/uri.d.mts +1 -1
- package/build/format/uri.mjs +3 -130
- package/build/format/uri_reference.d.mts +1 -1
- package/build/format/uri_reference.mjs +2 -3
- package/build/format/uri_template.d.mts +2 -3
- package/build/format/uri_template.mjs +4 -5
- package/build/format/url.d.mts +3 -3
- package/build/format/url.mjs +4 -5
- package/build/guard/guard.mjs +2 -2
- package/build/guard/string.d.mts +2 -2
- package/build/guard/string.mjs +7 -7
- package/build/schema/engine/_regexp.d.mts +2 -0
- package/build/schema/engine/_regexp.mjs +4 -0
- package/build/schema/engine/_stack.mjs +12 -13
- package/build/schema/engine/additionalProperties.mjs +4 -3
- package/build/schema/engine/pattern.mjs +3 -2
- package/build/schema/engine/patternProperties.mjs +4 -3
- package/build/schema/engine/schema.mjs +13 -4
- package/build/schema/resolve/resolve.d.mts +4 -1
- package/build/schema/resolve/resolve.mjs +202 -1
- package/build/schema/static/propertyNames.d.mts +5 -0
- package/build/schema/static/propertyNames.mjs +3 -0
- package/build/schema/static/schema.d.mts +3 -0
- package/build/schema/types/index.d.mts +0 -2
- package/build/schema/types/index.mjs +0 -2
- package/build/system/memory/clone.mjs +1 -1
- package/build/system/memory/discard.mjs +2 -1
- package/build/type/engine/evaluate/broaden.d.mts +5 -5
- package/build/type/engine/evaluate/broaden.mjs +20 -26
- package/build/type/engine/evaluate/compare.d.mts +6 -10
- package/build/type/engine/evaluate/compare.mjs +9 -13
- package/build/type/engine/evaluate/composite.d.mts +7 -4
- package/build/type/engine/evaluate/composite.mjs +12 -19
- package/build/type/engine/evaluate/distribute.d.mts +4 -20
- package/build/type/engine/evaluate/distribute.mjs +8 -20
- package/build/type/engine/evaluate/evaluate.d.mts +4 -4
- package/build/type/engine/evaluate/evaluate.mjs +11 -8
- package/build/type/engine/evaluate/flatten.d.mts +1 -1
- package/build/type/engine/evaluate/flatten.mjs +3 -4
- package/build/type/engine/evaluate/narrow.d.mts +17 -2
- package/build/type/engine/evaluate/narrow.mjs +26 -6
- package/build/type/engine/exclude/operation.mjs +3 -4
- package/build/type/engine/extract/operation.d.mts +1 -1
- package/build/type/engine/extract/operation.mjs +3 -4
- package/build/type/engine/priority/priority.d.mts +2 -2
- package/build/type/engine/priority/priority.mjs +3 -4
- package/build/type/script/parser.mjs +8 -1
- package/changes.json +1 -1
- package/package.json +3 -3
- package/readme.md +39 -37
- package/build/format/_idna.d.mts +0 -2
- package/build/format/_idna.mjs +0 -246
- package/build/format/_puny.d.mts +0 -1
- package/build/format/_puny.mjs +0 -77
- package/build/schema/resolve/ref.d.mts +0 -3
- package/build/schema/resolve/ref.mjs +0 -146
- package/build/schema/types/contentEncoding.d.mts +0 -9
- package/build/schema/types/contentEncoding.mjs +0 -13
- package/build/schema/types/contentMediaType.d.mts +0 -9
- package/build/schema/types/contentMediaType.mjs +0 -13
package/build/guard/string.d.mts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/** Returns the number of grapheme clusters in a string */
|
|
2
2
|
export declare function GraphemeCount(value: string): number;
|
|
3
3
|
/** Fast check for minimum grapheme length, falls back to full check if needed */
|
|
4
|
-
export declare function
|
|
4
|
+
export declare function IsMinLength(value: string, minLength: number): boolean;
|
|
5
5
|
/** Fast check for maximum grapheme length, falls back to full check if needed */
|
|
6
|
-
export declare function
|
|
6
|
+
export declare function IsMaxLength(value: string, maxLength: number): boolean;
|
package/build/guard/string.mjs
CHANGED
|
@@ -67,7 +67,7 @@ function NextGraphemeClusterIndex(value, clusterStart) {
|
|
|
67
67
|
// Consume combining marks & variation selectors
|
|
68
68
|
clusterEnd = ConsumeModifiers(value, clusterEnd);
|
|
69
69
|
// Handle multi-ZWJ sequences
|
|
70
|
-
while (clusterEnd < value.length - 1 && value
|
|
70
|
+
while (clusterEnd < value.length - 1 && IsZeroWidthJoiner(value.codePointAt(clusterEnd))) {
|
|
71
71
|
const nextCP = value.codePointAt(clusterEnd + 1);
|
|
72
72
|
clusterEnd += 1 + CodePointLength(nextCP);
|
|
73
73
|
clusterEnd = ConsumeModifiers(value, clusterEnd);
|
|
@@ -106,7 +106,7 @@ export function GraphemeCount(value) {
|
|
|
106
106
|
// IsMinLength
|
|
107
107
|
// --------------------------------------------------------------------------
|
|
108
108
|
/** Checks if a string has at least a minimum number of grapheme clusters */
|
|
109
|
-
function
|
|
109
|
+
function IsMinLengthSegmented(value, minLength) {
|
|
110
110
|
// ----------------------------------------------------------------
|
|
111
111
|
// Inaccessible via public interface (review)
|
|
112
112
|
//
|
|
@@ -129,7 +129,7 @@ function IsMinLength(value, minLength) {
|
|
|
129
129
|
// IsMaxLength
|
|
130
130
|
// --------------------------------------------------------------------------
|
|
131
131
|
/** Checks if a string has at most a maximum number of grapheme clusters */
|
|
132
|
-
function
|
|
132
|
+
function IsMaxLengthSegmented(value, maxLength) {
|
|
133
133
|
let count = 0;
|
|
134
134
|
let index = 0;
|
|
135
135
|
while (index < value.length) {
|
|
@@ -144,13 +144,13 @@ function IsMaxLength(value, maxLength) {
|
|
|
144
144
|
// IsMinLengthFast
|
|
145
145
|
// --------------------------------------------------------------------------
|
|
146
146
|
/** Fast check for minimum grapheme length, falls back to full check if needed */
|
|
147
|
-
export function
|
|
147
|
+
export function IsMinLength(value, minLength) {
|
|
148
148
|
if (minLength === 0)
|
|
149
149
|
return true; // 0-length
|
|
150
150
|
let index = 0;
|
|
151
151
|
while (index < value.length) {
|
|
152
152
|
if (IsGraphemeCodePoint(value.charCodeAt(index))) {
|
|
153
|
-
return
|
|
153
|
+
return IsMinLengthSegmented(value, minLength);
|
|
154
154
|
}
|
|
155
155
|
index++;
|
|
156
156
|
if (index >= minLength)
|
|
@@ -162,11 +162,11 @@ export function IsMinLengthFast(value, minLength) {
|
|
|
162
162
|
// IsMaxLengthFast
|
|
163
163
|
// --------------------------------------------------------------------------
|
|
164
164
|
/** Fast check for maximum grapheme length, falls back to full check if needed */
|
|
165
|
-
export function
|
|
165
|
+
export function IsMaxLength(value, maxLength) {
|
|
166
166
|
let index = 0;
|
|
167
167
|
while (index < value.length) {
|
|
168
168
|
if (IsGraphemeCodePoint(value.charCodeAt(index))) {
|
|
169
|
-
return
|
|
169
|
+
return IsMaxLengthSegmented(value, maxLength);
|
|
170
170
|
}
|
|
171
171
|
index++;
|
|
172
172
|
if (index > maxLength)
|
|
@@ -4,7 +4,7 @@ var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (
|
|
|
4
4
|
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
5
5
|
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
6
6
|
};
|
|
7
|
-
var _Stack_instances, _Stack_PushResourceAnchors, _Stack_PopResourceAnchors
|
|
7
|
+
var _Stack_instances, _Stack_PushResourceAnchors, _Stack_PopResourceAnchors;
|
|
8
8
|
import * as Schema from '../types/index.mjs';
|
|
9
9
|
import { Guard as G } from '../../guard/index.mjs';
|
|
10
10
|
import { Resolve } from '../resolve/index.mjs';
|
|
@@ -22,7 +22,7 @@ export class Stack {
|
|
|
22
22
|
// Base
|
|
23
23
|
// ----------------------------------------------------------------
|
|
24
24
|
BaseURL() {
|
|
25
|
-
return this.ids.reduce((result, schema) => new URL(schema.$id, result),
|
|
25
|
+
return this.ids.reduce((result, schema) => new URL(schema.$id, result), Resolve.DefaultBase);
|
|
26
26
|
}
|
|
27
27
|
Base() {
|
|
28
28
|
return this.ids[this.ids.length - 1] ?? this.schema;
|
|
@@ -58,23 +58,29 @@ export class Stack {
|
|
|
58
58
|
if (Schema.IsDynamicAnchor(schema))
|
|
59
59
|
this.dynamicAnchors.pop();
|
|
60
60
|
}
|
|
61
|
+
// ----------------------------------------------------------------
|
|
62
|
+
// Ref
|
|
63
|
+
// ----------------------------------------------------------------
|
|
61
64
|
Ref(ref) {
|
|
62
|
-
|
|
65
|
+
const root = this.schema;
|
|
66
|
+
return !ref.$ref.startsWith('#')
|
|
67
|
+
? Resolve.Ref(this.context, root, ref.$ref)
|
|
68
|
+
: Resolve.Ref(this.context, this.Base(), ref.$ref);
|
|
63
69
|
}
|
|
64
70
|
// ----------------------------------------------------------------
|
|
65
71
|
// RecursiveRef
|
|
66
72
|
// ----------------------------------------------------------------
|
|
67
73
|
RecursiveRef(recursiveRef) {
|
|
68
74
|
return Schema.IsRecursiveAnchorTrue(this.Base())
|
|
69
|
-
? Resolve.Ref(this.recursiveAnchors[0], recursiveRef.$recursiveRef)
|
|
70
|
-
: Resolve.Ref(this.Base(), recursiveRef.$recursiveRef);
|
|
75
|
+
? Resolve.Ref(this.context, this.recursiveAnchors[0], recursiveRef.$recursiveRef)
|
|
76
|
+
: Resolve.Ref(this.context, this.Base(), recursiveRef.$recursiveRef);
|
|
71
77
|
}
|
|
72
78
|
// ----------------------------------------------------------------
|
|
73
79
|
// DynamicRef
|
|
74
80
|
// ----------------------------------------------------------------
|
|
75
81
|
DynamicRef(dynamicRef) {
|
|
76
82
|
const root = this.schema;
|
|
77
|
-
return Resolve.DynamicRef(root, this.Base(), dynamicRef, this.dynamicAnchors);
|
|
83
|
+
return Resolve.DynamicRef(this.context, root, this.Base(), dynamicRef, this.dynamicAnchors);
|
|
78
84
|
}
|
|
79
85
|
}
|
|
80
86
|
_Stack_instances = new WeakSet(), _Stack_PushResourceAnchors = function _Stack_PushResourceAnchors(schema, isRoot = true) {
|
|
@@ -97,11 +103,4 @@ _Stack_instances = new WeakSet(), _Stack_PushResourceAnchors = function _Stack_P
|
|
|
97
103
|
this.dynamicAnchors.pop();
|
|
98
104
|
for (const key of G.Keys(current))
|
|
99
105
|
__classPrivateFieldGet(this, _Stack_instances, "m", _Stack_PopResourceAnchors).call(this, current[key], false);
|
|
100
|
-
}, _Stack_FromContext = function _Stack_FromContext(ref) {
|
|
101
|
-
return G.HasPropertyKey(this.context, ref.$ref) ? this.context[ref.$ref] : undefined;
|
|
102
|
-
}, _Stack_FromRef = function _Stack_FromRef(ref) {
|
|
103
|
-
const root = this.schema;
|
|
104
|
-
return !ref.$ref.startsWith('#')
|
|
105
|
-
? Resolve.Ref(root, ref.$ref)
|
|
106
|
-
: Resolve.Ref(this.Base(), ref.$ref);
|
|
107
106
|
};
|
|
@@ -3,6 +3,7 @@ import * as S from '../types/index.mjs';
|
|
|
3
3
|
import * as V from './_externals.mjs';
|
|
4
4
|
import { Unique } from './_unique.mjs';
|
|
5
5
|
import { AccumulatedErrorContext } from './_context.mjs';
|
|
6
|
+
import { UnicodeRegExp } from './_regexp.mjs';
|
|
6
7
|
import { EmitGuard as E, Guard as G } from '../../guard/index.mjs';
|
|
7
8
|
import { BuildSchemaPushStack, CheckSchemaPushStack, ErrorSchemaPushStack } from './schema.mjs';
|
|
8
9
|
// ------------------------------------------------------------------
|
|
@@ -58,7 +59,7 @@ export function BuildAdditionalPropertiesFast(_context, schema, value) {
|
|
|
58
59
|
// ------------------------------------------------------------------
|
|
59
60
|
export function BuildAdditionalPropertiesStandard(stack, context, schema, value) {
|
|
60
61
|
const [key, _index] = [Unique(), Unique()];
|
|
61
|
-
const regexp = V.CreateVariable(
|
|
62
|
+
const regexp = V.CreateVariable(UnicodeRegExp(GetPropertiesPattern(schema)));
|
|
62
63
|
const isSchema = BuildSchemaPushStack(stack, context, schema.additionalProperties, `${value}[${key}]`);
|
|
63
64
|
const isKey = E.Call(E.Member(regexp, 'test'), [key]);
|
|
64
65
|
const addKey = context.AddKey(key);
|
|
@@ -78,7 +79,7 @@ export function BuildAdditionalProperties(stack, context, schema, value) {
|
|
|
78
79
|
// Check
|
|
79
80
|
// ------------------------------------------------------------------
|
|
80
81
|
export function CheckAdditionalProperties(stack, context, schema, value) {
|
|
81
|
-
const regexp =
|
|
82
|
+
const regexp = UnicodeRegExp(GetPropertiesPattern(schema));
|
|
82
83
|
const isAdditionalProperties = G.Every(G.Keys(value), 0, (key, _index) => {
|
|
83
84
|
return regexp.test(key) ||
|
|
84
85
|
(CheckSchemaPushStack(stack, context, schema.additionalProperties, value[key]) && context.AddKey(key));
|
|
@@ -89,7 +90,7 @@ export function CheckAdditionalProperties(stack, context, schema, value) {
|
|
|
89
90
|
// Error
|
|
90
91
|
// ------------------------------------------------------------------
|
|
91
92
|
export function ErrorAdditionalProperties(stack, context, schemaPath, instancePath, schema, value) {
|
|
92
|
-
const regexp =
|
|
93
|
+
const regexp = UnicodeRegExp(GetPropertiesPattern(schema));
|
|
93
94
|
const additionalProperties = [];
|
|
94
95
|
const isAdditionalProperties = G.EveryAll(G.Keys(value), 0, (key, _index) => {
|
|
95
96
|
const nextSchemaPath = `${schemaPath}/additionalProperties`;
|
|
@@ -1,18 +1,19 @@
|
|
|
1
1
|
// deno-fmt-ignore-file
|
|
2
2
|
import * as Externals from './_externals.mjs';
|
|
3
3
|
import { Guard as G, EmitGuard as E } from '../../guard/index.mjs';
|
|
4
|
+
import { UnicodeRegExp } from './_regexp.mjs';
|
|
4
5
|
// ------------------------------------------------------------------
|
|
5
6
|
// Build
|
|
6
7
|
// ------------------------------------------------------------------
|
|
7
8
|
export function BuildPattern(_stack, _context, schema, value) {
|
|
8
|
-
const regexp = Externals.CreateVariable(G.IsString(schema.pattern) ?
|
|
9
|
+
const regexp = Externals.CreateVariable(G.IsString(schema.pattern) ? UnicodeRegExp(schema.pattern) : schema.pattern);
|
|
9
10
|
return E.Call(E.Member(regexp, 'test'), [value]);
|
|
10
11
|
}
|
|
11
12
|
// ------------------------------------------------------------------
|
|
12
13
|
// Check
|
|
13
14
|
// ------------------------------------------------------------------
|
|
14
15
|
export function CheckPattern(_stack, _context, schema, value) {
|
|
15
|
-
const regexp = G.IsString(schema.pattern) ?
|
|
16
|
+
const regexp = G.IsString(schema.pattern) ? UnicodeRegExp(schema.pattern) : schema.pattern;
|
|
16
17
|
return regexp.test(value);
|
|
17
18
|
}
|
|
18
19
|
// ------------------------------------------------------------------
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
// deno-fmt-ignore-file
|
|
2
2
|
import * as Externals from './_externals.mjs';
|
|
3
3
|
import { Unique } from './_unique.mjs';
|
|
4
|
+
import { UnicodeRegExp } from './_regexp.mjs';
|
|
4
5
|
import { Guard as G, EmitGuard as E } from '../../guard/index.mjs';
|
|
5
6
|
import { BuildSchemaPushStack, CheckSchemaPushStack, ErrorSchemaPushStack } from './schema.mjs';
|
|
6
7
|
// ------------------------------------------------------------------
|
|
@@ -9,7 +10,7 @@ import { BuildSchemaPushStack, CheckSchemaPushStack, ErrorSchemaPushStack } from
|
|
|
9
10
|
export function BuildPatternProperties(stack, context, schema, value) {
|
|
10
11
|
return E.ReduceAnd(G.Entries(schema.patternProperties).map(([pattern, schema]) => {
|
|
11
12
|
const [key, prop] = [Unique(), Unique()];
|
|
12
|
-
const regexp = Externals.CreateVariable(
|
|
13
|
+
const regexp = Externals.CreateVariable(UnicodeRegExp(pattern));
|
|
13
14
|
const notKey = E.Not(E.Call(E.Member(regexp, 'test'), [key]));
|
|
14
15
|
const isSchema = BuildSchemaPushStack(stack, context, schema, prop);
|
|
15
16
|
const addKey = context.AddKey(key);
|
|
@@ -22,7 +23,7 @@ export function BuildPatternProperties(stack, context, schema, value) {
|
|
|
22
23
|
// ------------------------------------------------------------------
|
|
23
24
|
export function CheckPatternProperties(stack, context, schema, value) {
|
|
24
25
|
return G.Every(G.Entries(schema.patternProperties), 0, ([pattern, schema]) => {
|
|
25
|
-
const regexp =
|
|
26
|
+
const regexp = UnicodeRegExp(pattern);
|
|
26
27
|
return G.Every(G.Entries(value), 0, ([key, prop]) => {
|
|
27
28
|
return !regexp.test(key) || CheckSchemaPushStack(stack, context, schema, prop) && context.AddKey(key);
|
|
28
29
|
});
|
|
@@ -34,7 +35,7 @@ export function CheckPatternProperties(stack, context, schema, value) {
|
|
|
34
35
|
export function ErrorPatternProperties(stack, context, schemaPath, instancePath, schema, value) {
|
|
35
36
|
return G.EveryAll(G.Entries(schema.patternProperties), 0, ([pattern, schema]) => {
|
|
36
37
|
const nextSchemaPath = `${schemaPath}/patternProperties/${pattern}`;
|
|
37
|
-
const regexp =
|
|
38
|
+
const regexp = UnicodeRegExp(pattern);
|
|
38
39
|
return G.EveryAll(G.Entries(value), 0, ([key, value]) => {
|
|
39
40
|
const nextInstancePath = `${instancePath}/${key}`;
|
|
40
41
|
const notKey = !regexp.test(key);
|
|
@@ -45,12 +45,21 @@ import { BuildUnevaluatedItems, CheckUnevaluatedItems, ErrorUnevaluatedItems } f
|
|
|
45
45
|
import { BuildUnevaluatedProperties, CheckUnevaluatedProperties, ErrorUnevaluatedProperties } from './unevaluatedProperties.mjs';
|
|
46
46
|
import { BuildUniqueItems, CheckUniqueItems, ErrorUniqueItems } from './uniqueItems.mjs';
|
|
47
47
|
// ----------------------------------------------------------------
|
|
48
|
-
// HasTypeName
|
|
48
|
+
// HasTypeName (Optimization)
|
|
49
|
+
//
|
|
50
|
+
// We only consider a schema as having a type name when the schema
|
|
51
|
+
// has a single type string, or when every element in the type
|
|
52
|
+
// array is the same. For a type array, we must treat multi-variant
|
|
53
|
+
// types as unions and therefore can NOT use an optimized forward
|
|
54
|
+
// type check.
|
|
55
|
+
//
|
|
49
56
|
// ----------------------------------------------------------------
|
|
50
57
|
function HasTypeName(schema, typename) {
|
|
51
|
-
return Schema.IsType(schema) &&
|
|
52
|
-
(G.IsArray(schema.type) &&
|
|
53
|
-
G.
|
|
58
|
+
return (Schema.IsType(schema) &&
|
|
59
|
+
((G.IsArray(schema.type) &&
|
|
60
|
+
G.IsGreaterThan(schema.type.length, 0) &&
|
|
61
|
+
G.Every(schema.type, 0, type => G.IsEqual(type, typename))) ||
|
|
62
|
+
G.IsEqual(schema.type, typename)));
|
|
54
63
|
}
|
|
55
64
|
// ----------------------------------------------------------------
|
|
56
65
|
// HasObject
|
|
@@ -1 +1,4 @@
|
|
|
1
|
-
|
|
1
|
+
import * as Schema from '../types/index.mjs';
|
|
2
|
+
export declare const DefaultBase: URL;
|
|
3
|
+
export declare function Ref(context: Record<string, Schema.XSchema>, schema: Schema.XSchemaObject, ref: string): Schema.XSchema | undefined;
|
|
4
|
+
export declare function DynamicRef(context: Record<string, Schema.XSchema>, root: Schema.XSchemaObject, base: Schema.XSchemaObject, dynamicRef: Schema.XDynamicRef, dynamicAnchors: Schema.XDynamicAnchor[]): Schema.XSchema | undefined;
|
|
@@ -1 +1,202 @@
|
|
|
1
|
-
|
|
1
|
+
// deno-fmt-ignore-file
|
|
2
|
+
import { Guard } from '../../guard/index.mjs';
|
|
3
|
+
import { Pointer } from '../pointer/index.mjs';
|
|
4
|
+
import * as Schema from '../types/index.mjs';
|
|
5
|
+
// ------------------------------------------------------------------
|
|
6
|
+
// DefaultBase
|
|
7
|
+
// ------------------------------------------------------------------
|
|
8
|
+
export const DefaultBase = new URL('https://json-schema.org');
|
|
9
|
+
// ------------------------------------------------------------------
|
|
10
|
+
// Match: Id
|
|
11
|
+
// ------------------------------------------------------------------
|
|
12
|
+
function MatchId(schema, base, ref) {
|
|
13
|
+
if (schema.$id === ref.hash)
|
|
14
|
+
return schema;
|
|
15
|
+
const absoluteId = new URL(schema.$id, base.href);
|
|
16
|
+
const absoluteRef = new URL(ref.href, base.href);
|
|
17
|
+
if (Guard.IsEqual(absoluteId.pathname, absoluteRef.pathname)) {
|
|
18
|
+
return ref.hash.startsWith('#') ? MatchHash(schema, base, ref) : schema;
|
|
19
|
+
}
|
|
20
|
+
return undefined;
|
|
21
|
+
}
|
|
22
|
+
// ------------------------------------------------------------------
|
|
23
|
+
// Match: Anchor
|
|
24
|
+
// ------------------------------------------------------------------
|
|
25
|
+
function MatchAnchor(schema, base, ref) {
|
|
26
|
+
const absoluteAnchor = new URL(`#${schema.$anchor}`, base.href);
|
|
27
|
+
const absoluteRef = new URL(ref.href, base.href);
|
|
28
|
+
return Guard.IsEqual(absoluteAnchor.href, absoluteRef.href) ? schema : undefined;
|
|
29
|
+
}
|
|
30
|
+
// ------------------------------------------------------------------
|
|
31
|
+
// Match: DynamicAnchor
|
|
32
|
+
// ------------------------------------------------------------------
|
|
33
|
+
function MatchDynamicAnchor(schema, base, ref) {
|
|
34
|
+
const absoluteAnchor = new URL(`#${schema.$dynamicAnchor}`, base.href);
|
|
35
|
+
const absoluteRef = new URL(ref.href, base.href);
|
|
36
|
+
return Guard.IsEqual(absoluteAnchor.href, absoluteRef.href) ? schema : undefined;
|
|
37
|
+
}
|
|
38
|
+
// ------------------------------------------------------------------
|
|
39
|
+
// Match: Hash
|
|
40
|
+
//
|
|
41
|
+
// Resolves JSON Pointer fragments only. Plain anchor-style fragments
|
|
42
|
+
// (no leading '/') are handled exclusively by MatchAnchor and
|
|
43
|
+
// MatchDynamicAnchor to prevent accidentally resolving an anchor name
|
|
44
|
+
// as a pointer into the schema tree.
|
|
45
|
+
//
|
|
46
|
+
// ------------------------------------------------------------------
|
|
47
|
+
function MatchHash(schema, _base, ref) {
|
|
48
|
+
if (ref.href.endsWith('#'))
|
|
49
|
+
return schema;
|
|
50
|
+
if (!ref.hash.startsWith('#'))
|
|
51
|
+
return undefined;
|
|
52
|
+
const fragment = decodeURIComponent(ref.hash.slice(1));
|
|
53
|
+
if (!fragment.startsWith('/'))
|
|
54
|
+
return undefined;
|
|
55
|
+
return Pointer.Get(schema, fragment);
|
|
56
|
+
}
|
|
57
|
+
// ------------------------------------------------------------------
|
|
58
|
+
// Match
|
|
59
|
+
// ------------------------------------------------------------------
|
|
60
|
+
function Match(schema, base, ref) {
|
|
61
|
+
if (Schema.IsId(schema)) {
|
|
62
|
+
const result = MatchId(schema, base, ref);
|
|
63
|
+
if (!Guard.IsUndefined(result))
|
|
64
|
+
return result;
|
|
65
|
+
}
|
|
66
|
+
if (Schema.IsAnchor(schema)) {
|
|
67
|
+
const result = MatchAnchor(schema, base, ref);
|
|
68
|
+
if (!Guard.IsUndefined(result))
|
|
69
|
+
return result;
|
|
70
|
+
}
|
|
71
|
+
if (Schema.IsDynamicAnchor(schema)) {
|
|
72
|
+
const result = MatchDynamicAnchor(schema, base, ref);
|
|
73
|
+
if (!Guard.IsUndefined(result))
|
|
74
|
+
return result;
|
|
75
|
+
}
|
|
76
|
+
return MatchHash(schema, base, ref);
|
|
77
|
+
}
|
|
78
|
+
// ------------------------------------------------------------------
|
|
79
|
+
// FromArray
|
|
80
|
+
// ------------------------------------------------------------------
|
|
81
|
+
function FromArray(schema, base, ref) {
|
|
82
|
+
return schema.reduce((result, item) => {
|
|
83
|
+
const match = FromValue(item, base, ref);
|
|
84
|
+
return !Guard.IsUndefined(match) ? match : result;
|
|
85
|
+
}, undefined);
|
|
86
|
+
}
|
|
87
|
+
// ------------------------------------------------------------------
|
|
88
|
+
// FromObject
|
|
89
|
+
// ------------------------------------------------------------------
|
|
90
|
+
function SkipProperty(key) {
|
|
91
|
+
// these are explicit data encoded in a schema, they should not
|
|
92
|
+
// be considered valid targets used for de-referencing.
|
|
93
|
+
return Guard.IsEqual(key, 'const') || Guard.IsEqual(key, 'enum');
|
|
94
|
+
}
|
|
95
|
+
function FromObject(schema, base, ref) {
|
|
96
|
+
return Guard.Keys(schema).reduce((result, key) => {
|
|
97
|
+
if (SkipProperty(key))
|
|
98
|
+
return result;
|
|
99
|
+
const match = FromValue(schema[key], base, ref);
|
|
100
|
+
return !Guard.IsUndefined(match) ? match : result;
|
|
101
|
+
}, undefined);
|
|
102
|
+
}
|
|
103
|
+
// ------------------------------------------------------------------
|
|
104
|
+
// FromValue
|
|
105
|
+
// ------------------------------------------------------------------
|
|
106
|
+
function FromValue(schema, base, ref) {
|
|
107
|
+
const nextBase = Schema.IsSchemaObject(schema) && Schema.IsId(schema)
|
|
108
|
+
? new URL(schema.$id, base.href)
|
|
109
|
+
: base;
|
|
110
|
+
if (Schema.IsSchemaObject(schema)) {
|
|
111
|
+
const result = Match(schema, nextBase, ref);
|
|
112
|
+
if (!Guard.IsUndefined(result))
|
|
113
|
+
return result;
|
|
114
|
+
}
|
|
115
|
+
if (Guard.IsArray(schema))
|
|
116
|
+
return FromArray(schema, nextBase, ref);
|
|
117
|
+
if (Guard.IsObject(schema))
|
|
118
|
+
return FromObject(schema, nextBase, ref);
|
|
119
|
+
return undefined;
|
|
120
|
+
}
|
|
121
|
+
// ------------------------------------------------------------------
|
|
122
|
+
// CanonicalHref
|
|
123
|
+
//
|
|
124
|
+
// Returns the URL's href with its fragment removed, as a string.
|
|
125
|
+
// This is the canonical URI a document is identified and keyed by
|
|
126
|
+
// in context.
|
|
127
|
+
// ------------------------------------------------------------------
|
|
128
|
+
function CanonicalHref(url) {
|
|
129
|
+
return url.href.split('#')[0];
|
|
130
|
+
}
|
|
131
|
+
// ------------------------------------------------------------------
|
|
132
|
+
// RefContext: Phase 1
|
|
133
|
+
//
|
|
134
|
+
// A ContextRef targets a simple key name in the context and is
|
|
135
|
+
// used for fast resolution of inline referential TypeBox types.
|
|
136
|
+
// ------------------------------------------------------------------
|
|
137
|
+
function RefContext(context, ref) {
|
|
138
|
+
return Guard.HasPropertyKey(context, ref) ? context[ref] : undefined;
|
|
139
|
+
}
|
|
140
|
+
// ------------------------------------------------------------------
|
|
141
|
+
// RefLocal: Phase 2
|
|
142
|
+
//
|
|
143
|
+
// Resolves the ref's fragment within the current schema resource,
|
|
144
|
+
// either as a JSON Pointer or a plain-name fragment ($anchor,
|
|
145
|
+
// $dynamicAnchor), per the JSON Schema spec.
|
|
146
|
+
// ------------------------------------------------------------------
|
|
147
|
+
function RefLocal(schema, base, ref) {
|
|
148
|
+
return FromValue(schema, base, ref);
|
|
149
|
+
}
|
|
150
|
+
// ------------------------------------------------------------------
|
|
151
|
+
// RefRemote: Phase 3
|
|
152
|
+
//
|
|
153
|
+
// Locates the schema resource identified by the ref's base URI, then
|
|
154
|
+
// resolves the ref's fragment within that resource, either as a JSON
|
|
155
|
+
// Pointer or a plain-name fragment, per the JSON Schema spec.
|
|
156
|
+
// ------------------------------------------------------------------
|
|
157
|
+
function RefRemote(context, base, ref) {
|
|
158
|
+
const targetDocumentHref = CanonicalHref(ref);
|
|
159
|
+
if (Guard.IsEqual(targetDocumentHref, CanonicalHref(base)))
|
|
160
|
+
return undefined;
|
|
161
|
+
if (!Guard.HasPropertyKey(context, targetDocumentHref))
|
|
162
|
+
return undefined;
|
|
163
|
+
const remoteSchema = context[targetDocumentHref];
|
|
164
|
+
const remoteBase = (Schema.IsSchemaObject(remoteSchema) && Schema.IsId(remoteSchema)) ? new URL(remoteSchema.$id, DefaultBase.href) : new URL(targetDocumentHref);
|
|
165
|
+
return FromValue(remoteSchema, remoteBase, ref);
|
|
166
|
+
}
|
|
167
|
+
// ------------------------------------------------------------------
|
|
168
|
+
// Ref
|
|
169
|
+
// ------------------------------------------------------------------
|
|
170
|
+
export function Ref(context, schema, ref) {
|
|
171
|
+
const initialBase = Schema.IsId(schema) ? new URL(schema.$id, DefaultBase.href) : DefaultBase;
|
|
172
|
+
const initialRef = new URL(ref, initialBase.href);
|
|
173
|
+
return RefContext(context, ref) ?? RefLocal(schema, initialBase, initialRef) ?? RefRemote(context, initialBase, initialRef);
|
|
174
|
+
}
|
|
175
|
+
// ------------------------------------------------------------------
|
|
176
|
+
// DynamicRef
|
|
177
|
+
// ------------------------------------------------------------------
|
|
178
|
+
export function DynamicRef(context, root, base, dynamicRef, dynamicAnchors) {
|
|
179
|
+
// Resolve the static target using either the local base (for fragment‑only references)
|
|
180
|
+
// or the document root (for absolute URI references).
|
|
181
|
+
const fragmentTarget = dynamicRef.$dynamicRef.startsWith('#')
|
|
182
|
+
? Ref(context, base, dynamicRef.$dynamicRef)
|
|
183
|
+
: Ref(context, root, dynamicRef.$dynamicRef);
|
|
184
|
+
if (Guard.IsUndefined(fragmentTarget))
|
|
185
|
+
return undefined;
|
|
186
|
+
// Dynamic override only applies if the resolved target itself declares a $dynamicAnchor.
|
|
187
|
+
// If it does not, return the static target unchanged.
|
|
188
|
+
if (!Schema.IsSchemaObject(fragmentTarget) || !Schema.IsDynamicAnchor(fragmentTarget))
|
|
189
|
+
return fragmentTarget;
|
|
190
|
+
// Extract the fragment portion of the reference. According to the test suite,
|
|
191
|
+
// only plain fragment names (e.g., "#foo") trigger the dynamic scope; JSON
|
|
192
|
+
// Pointer fragments (e.g., "#/definitions/foo") bypass dynamic resolution.
|
|
193
|
+
const fragment = new URL(dynamicRef.$dynamicRef, DefaultBase).hash;
|
|
194
|
+
if (fragment.startsWith('#/'))
|
|
195
|
+
return fragmentTarget;
|
|
196
|
+
// Search the live dynamic anchor stack for a schema whose $dynamicAnchor matches the
|
|
197
|
+
// target's $dynamicAnchor. The stack reflects the current evaluation path, and
|
|
198
|
+
// find() returns the outermost (first encountered) match, which is the correct
|
|
199
|
+
// lexical scope per the specification.
|
|
200
|
+
const anchorTarget = dynamicAnchors.find(anchor => anchor.$dynamicAnchor === fragmentTarget.$dynamicAnchor);
|
|
201
|
+
return anchorTarget ?? fragmentTarget;
|
|
202
|
+
}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import type { XSchema } from '../types/schema.mjs';
|
|
2
|
+
import type { XStaticSchema } from './schema.mjs';
|
|
3
|
+
export type XStaticPropertyNames<Stack extends string[], Root extends XSchema, Schema extends XSchema, StaticKey extends unknown = XStaticSchema<Stack, Root, Schema>, Result extends Record<string, unknown> = [StaticKey] extends [PropertyKey] ? {
|
|
4
|
+
[Key in StaticKey]?: unknown;
|
|
5
|
+
} : {}> = Result;
|
|
@@ -9,6 +9,7 @@ import type { XOneOf } from '../types/oneOf.mjs';
|
|
|
9
9
|
import type { XPatternProperties } from '../types/patternProperties.mjs';
|
|
10
10
|
import type { XPrefixItems } from '../types/prefixItems.mjs';
|
|
11
11
|
import type { XProperties } from '../types/properties.mjs';
|
|
12
|
+
import type { XPropertyNames } from '../types/propertyNames.mjs';
|
|
12
13
|
import type { XRef } from '../types/ref.mjs';
|
|
13
14
|
import type { XRequired } from '../types/required.mjs';
|
|
14
15
|
import type { XSchema } from '../types/schema.mjs';
|
|
@@ -25,6 +26,7 @@ import type { XStaticOneOf } from './oneOf.mjs';
|
|
|
25
26
|
import type { XStaticPatternProperties } from './patternProperties.mjs';
|
|
26
27
|
import type { XStaticPrefixItems } from './prefixItems.mjs';
|
|
27
28
|
import type { XStaticProperties } from './properties.mjs';
|
|
29
|
+
import type { XStaticPropertyNames } from './propertyNames.mjs';
|
|
28
30
|
import type { XStaticRef } from './ref.mjs';
|
|
29
31
|
import type { XStaticRequired } from './required.mjs';
|
|
30
32
|
import type { XStaticType } from './type.mjs';
|
|
@@ -41,6 +43,7 @@ type XFromKeywords<Stack extends string[], Root extends XSchema, Schema extends
|
|
|
41
43
|
Schema extends XPatternProperties<infer Properties extends Record<PropertyKey, XSchema>> ? XStaticPatternProperties<Stack, Root, Properties> : unknown,
|
|
42
44
|
Schema extends XPrefixItems<infer Types extends XSchema[]> ? XStaticPrefixItems<Stack, Root, Schema, Types> : unknown,
|
|
43
45
|
Schema extends XProperties<infer Properties extends Record<PropertyKey, XSchema>> ? XStaticProperties<Stack, Root, Schema, Properties> : unknown,
|
|
46
|
+
Schema extends XPropertyNames<infer Type extends XSchema> ? XStaticPropertyNames<Stack, Root, Type> : unknown,
|
|
44
47
|
Schema extends XRef<infer Ref extends string> ? XStaticRef<Stack, Root, Ref> : unknown,
|
|
45
48
|
Schema extends XRequired<infer Keys extends string[]> ? XStaticRequired<Stack, Root, Schema, Keys> : unknown,
|
|
46
49
|
Schema extends XType<infer TypeName extends string[] | string> ? XStaticType<TypeName> : unknown,
|
|
@@ -6,8 +6,6 @@ export * from './anchor.mjs';
|
|
|
6
6
|
export * from './anyOf.mjs';
|
|
7
7
|
export * from './const.mjs';
|
|
8
8
|
export * from './contains.mjs';
|
|
9
|
-
export * from './contentEncoding.mjs';
|
|
10
|
-
export * from './contentMediaType.mjs';
|
|
11
9
|
export * from './default.mjs';
|
|
12
10
|
export * from './defs.mjs';
|
|
13
11
|
export * from './dependencies.mjs';
|
|
@@ -12,8 +12,6 @@ export * from './anchor.mjs';
|
|
|
12
12
|
export * from './anyOf.mjs';
|
|
13
13
|
export * from './const.mjs';
|
|
14
14
|
export * from './contains.mjs';
|
|
15
|
-
export * from './contentEncoding.mjs';
|
|
16
|
-
export * from './contentMediaType.mjs';
|
|
17
15
|
export * from './default.mjs';
|
|
18
16
|
export * from './defs.mjs';
|
|
19
17
|
export * from './dependencies.mjs';
|
|
@@ -24,7 +24,7 @@ function IsSchemaObject(value) {
|
|
|
24
24
|
}
|
|
25
25
|
function FromSchemaObject(value) {
|
|
26
26
|
const result = {};
|
|
27
|
-
for (const key of
|
|
27
|
+
for (const key of Guard.Keys(value)) {
|
|
28
28
|
if (Guard.IsUnsafePropertyKey(key))
|
|
29
29
|
continue; // (ignore: prototype-pollution)
|
|
30
30
|
const descriptor = Object.getOwnPropertyDescriptor(value, key); // safe-name!
|
|
@@ -1,12 +1,13 @@
|
|
|
1
1
|
// deno-lint-ignore-file no-explicit-any
|
|
2
2
|
// deno-fmt-ignore-file
|
|
3
|
+
import { Guard } from '../../guard/index.mjs';
|
|
3
4
|
import { Metrics } from './metrics.mjs';
|
|
4
5
|
import { Clone } from './clone.mjs';
|
|
5
6
|
/** Discards multiple property keys from the given object value */
|
|
6
7
|
export function Discard(value, propertyKeys) {
|
|
7
8
|
Metrics.discard += 1;
|
|
8
9
|
const result = {};
|
|
9
|
-
for (const key of
|
|
10
|
+
for (const key of Guard.Keys(value)) {
|
|
10
11
|
if (propertyKeys.includes(key))
|
|
11
12
|
continue;
|
|
12
13
|
const descriptor = Object.getOwnPropertyDescriptor(value, key); // safe-name!
|
|
@@ -2,13 +2,13 @@ import { type TSchema } from '../../types/schema.mjs';
|
|
|
2
2
|
import { type TAny } from '../../types/any.mjs';
|
|
3
3
|
import { type TNever } from '../../types/never.mjs';
|
|
4
4
|
import { type TObject } from '../../types/object.mjs';
|
|
5
|
-
import { type
|
|
5
|
+
import { type TUnknown } from '../../types/unknown.mjs';
|
|
6
|
+
import { type TCompare, CompareResultLeftInside, CompareResultEqual, CompareResultDisjoint } from './compare.mjs';
|
|
6
7
|
import { type TFlatten } from './flatten.mjs';
|
|
7
8
|
import { type TEvaluateType } from './evaluate.mjs';
|
|
8
|
-
type
|
|
9
|
-
type
|
|
10
|
-
type
|
|
11
|
-
type TBroadenTypes<Types extends TSchema[], Result extends TSchema[] = []> = (Types extends [infer Left extends TSchema, ...infer Right extends TSchema[]] ? (Left extends TObject ? TBroadenTypes<Right, [...Result, Left]> : Left extends TNever ? TBroadenTypes<Right, Result> : TBroadenTypes<Right, TBroadenType<Left, Result>>) : Result);
|
|
9
|
+
type TBroadenFilter<Type extends TSchema, Types extends TSchema[], Result extends TSchema[] = [], All extends TSchema[] = Types> = (Types extends [infer Left extends TSchema, ...infer Right extends TSchema[]] ? TCompare<Type, Left> extends typeof CompareResultLeftInside | typeof CompareResultEqual ? All : TCompare<Type, Left> extends typeof CompareResultDisjoint ? TBroadenFilter<Type, Right, [...Result, Left], All> : TBroadenFilter<Type, Right, Result, All> : [...Result, Type]);
|
|
10
|
+
type TBroadenType<Type extends TSchema, Types extends TSchema[], Result extends TSchema[], Evaluated extends TSchema = TEvaluateType<Type>> = (Evaluated extends TAny ? [Evaluated] : Evaluated extends TUnknown ? [Evaluated] : Evaluated extends TNever ? TBroadenTypes<Types, Result> : Evaluated extends TObject ? TBroadenTypes<Types, [...Result, Evaluated]> : TBroadenTypes<Types, TBroadenFilter<Evaluated, Result>>);
|
|
11
|
+
type TBroadenTypes<Types extends TSchema[], Result extends TSchema[] = []> = (Types extends [infer Left extends TSchema, ...infer Right extends TSchema[]] ? TBroadenType<Left, Right, Result> : Result);
|
|
12
12
|
export type TBroaden<Types extends TSchema[], Broadened extends TSchema[] = TBroadenTypes<Types>, Flattened extends TSchema[] = TFlatten<Broadened>> = Flattened;
|
|
13
13
|
/** Broadens a set of types and returns either the most broad type, or union or disjoint types. */
|
|
14
14
|
export declare function Broaden<Types extends TSchema[]>(types: [...Types]): TBroaden<Types>;
|
|
@@ -3,37 +3,31 @@ import { Guard } from '../../../guard/index.mjs';
|
|
|
3
3
|
import { IsAny } from '../../types/any.mjs';
|
|
4
4
|
import { IsNever } from '../../types/never.mjs';
|
|
5
5
|
import { IsObject } from '../../types/object.mjs';
|
|
6
|
-
import {
|
|
6
|
+
import { IsUnknown } from '../../types/unknown.mjs';
|
|
7
|
+
import { Compare, CompareResultLeftInside, CompareResultEqual, CompareResultDisjoint } from './compare.mjs';
|
|
7
8
|
import { Flatten } from './flatten.mjs';
|
|
8
9
|
import { EvaluateType } from './evaluate.mjs';
|
|
9
|
-
function
|
|
10
|
-
return
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
return Guard.IsEqual(result, ResultLeftInside) || Guard.IsEqual(result, ResultEqual);
|
|
20
|
-
});
|
|
21
|
-
return Guard.IsEqual(result, false);
|
|
10
|
+
function BroadenFilter(type, types, result = [], all = types) {
|
|
11
|
+
return Guard.ShiftLeft(types, (left, right) => {
|
|
12
|
+
const compare = Compare(type, left);
|
|
13
|
+
return ((Guard.IsEqual(compare, CompareResultLeftInside) || Guard.IsEqual(compare, CompareResultEqual))
|
|
14
|
+
? all // Left in set. Return original All set.
|
|
15
|
+
: Guard.IsEqual(compare, CompareResultDisjoint)
|
|
16
|
+
? BroadenFilter(type, right, [...result, left], all) // Left is disjoint, keep it
|
|
17
|
+
: BroadenFilter(type, right, result, all) // Left in Type, drop it
|
|
18
|
+
);
|
|
19
|
+
}, () => [...result, type]); // Type broadest in set
|
|
22
20
|
}
|
|
23
|
-
function BroadenType(type, types) {
|
|
21
|
+
function BroadenType(type, types, result) {
|
|
24
22
|
const evaluated = EvaluateType(type);
|
|
25
|
-
return (IsAny(evaluated) ? [evaluated] :
|
|
26
|
-
|
|
27
|
-
?
|
|
28
|
-
|
|
23
|
+
return (IsAny(evaluated) ? [evaluated] : // terminate (always the most broad)
|
|
24
|
+
IsUnknown(evaluated) ? [evaluated] : // terminate (always the most broad)
|
|
25
|
+
IsNever(evaluated) ? BroadenTypes(types, result) : // ignored: never is dropped
|
|
26
|
+
IsObject(evaluated) ? BroadenTypes(types, [...result, evaluated]) : // objects are always considered (too expensive to compare)
|
|
27
|
+
BroadenTypes(types, BroadenFilter(evaluated, result)));
|
|
29
28
|
}
|
|
30
|
-
function BroadenTypes(types) {
|
|
31
|
-
return
|
|
32
|
-
return (IsObject(left) ? [...result, left] : // push
|
|
33
|
-
IsNever(left) ? result : // ignore
|
|
34
|
-
BroadenType(left, result) // broaden
|
|
35
|
-
);
|
|
36
|
-
}, []);
|
|
29
|
+
function BroadenTypes(types, result = []) {
|
|
30
|
+
return Guard.ShiftLeft(types, (left, right) => (BroadenType(left, right, result)), () => result);
|
|
37
31
|
}
|
|
38
32
|
/** Broadens a set of types and returns either the most broad type, or union or disjoint types. */
|
|
39
33
|
export function Broaden(types) {
|