@optique/core 1.0.0-dev.523 → 1.0.0-dev.552
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/dist/annotations.cjs +182 -1
- package/dist/annotations.d.cts +59 -1
- package/dist/annotations.d.ts +59 -1
- package/dist/annotations.js +176 -1
- package/dist/constructs.cjs +8 -3
- package/dist/constructs.js +8 -3
- package/dist/facade.cjs +1 -4
- package/dist/facade.js +2 -5
- package/dist/modifiers.cjs +150 -27
- package/dist/modifiers.js +150 -27
- package/dist/parser.cjs +15 -32
- package/dist/parser.js +16 -33
- package/dist/primitives.cjs +20 -7
- package/dist/primitives.js +20 -7
- package/package.json +1 -1
package/dist/annotations.cjs
CHANGED
|
@@ -16,6 +16,29 @@
|
|
|
16
16
|
*/
|
|
17
17
|
const annotationKey = Symbol.for("@optique/core/parser/annotation");
|
|
18
18
|
/**
|
|
19
|
+
* Internal key for preserving primitive parser state values when annotations
|
|
20
|
+
* are injected into non-object states.
|
|
21
|
+
* @internal
|
|
22
|
+
*/
|
|
23
|
+
const annotationStateValueKey = Symbol.for("@optique/core/parser/annotationStateValue");
|
|
24
|
+
/**
|
|
25
|
+
* Internal marker key that indicates annotation wrapping was injected by
|
|
26
|
+
* Optique internals for non-object states.
|
|
27
|
+
* @internal
|
|
28
|
+
*/
|
|
29
|
+
const annotationWrapperKey = Symbol.for("@optique/core/parser/annotationWrapper");
|
|
30
|
+
/**
|
|
31
|
+
* Internal symbol keys that define Optique's primitive-state annotation
|
|
32
|
+
* wrapper shape.
|
|
33
|
+
* @internal
|
|
34
|
+
*/
|
|
35
|
+
const annotationWrapperKeys = new Set([
|
|
36
|
+
annotationKey,
|
|
37
|
+
annotationStateValueKey,
|
|
38
|
+
annotationWrapperKey
|
|
39
|
+
]);
|
|
40
|
+
const injectedAnnotationWrappers = /* @__PURE__ */ new WeakSet();
|
|
41
|
+
/**
|
|
19
42
|
* Extracts annotations from parser state.
|
|
20
43
|
*
|
|
21
44
|
* @param state Parser state that may contain annotations
|
|
@@ -35,7 +58,165 @@ function getAnnotations(state) {
|
|
|
35
58
|
if (annotations != null && typeof annotations === "object") return annotations;
|
|
36
59
|
return void 0;
|
|
37
60
|
}
|
|
61
|
+
/**
|
|
62
|
+
* Propagates annotations from one parser state to another.
|
|
63
|
+
*
|
|
64
|
+
* This is mainly used by parsers that rebuild array states with spread syntax.
|
|
65
|
+
* Array spread copies elements but drops custom symbol properties, so we need
|
|
66
|
+
* to reattach annotations explicitly when present.
|
|
67
|
+
*
|
|
68
|
+
* @param source The original state that may carry annotations.
|
|
69
|
+
* @param target The new state to receive annotations.
|
|
70
|
+
* @returns The target state, with annotations copied when available.
|
|
71
|
+
* @internal
|
|
72
|
+
*/
|
|
73
|
+
function inheritAnnotations(source, target) {
|
|
74
|
+
const annotations = getAnnotations(source);
|
|
75
|
+
if (annotations === void 0) return target;
|
|
76
|
+
if (target == null || typeof target !== "object") return injectAnnotations(target, annotations);
|
|
77
|
+
if (isInjectedAnnotationWrapper(target)) return injectAnnotations(target, annotations);
|
|
78
|
+
if (Array.isArray(target)) {
|
|
79
|
+
const cloned$1 = [...target];
|
|
80
|
+
cloned$1[annotationKey] = annotations;
|
|
81
|
+
return cloned$1;
|
|
82
|
+
}
|
|
83
|
+
if (target instanceof Date) {
|
|
84
|
+
const cloned$1 = new Date(target.getTime());
|
|
85
|
+
cloned$1[annotationKey] = annotations;
|
|
86
|
+
return cloned$1;
|
|
87
|
+
}
|
|
88
|
+
if (target instanceof Map) {
|
|
89
|
+
const cloned$1 = new Map(target);
|
|
90
|
+
cloned$1[annotationKey] = annotations;
|
|
91
|
+
return cloned$1;
|
|
92
|
+
}
|
|
93
|
+
if (target instanceof Set) {
|
|
94
|
+
const cloned$1 = new Set(target);
|
|
95
|
+
cloned$1[annotationKey] = annotations;
|
|
96
|
+
return cloned$1;
|
|
97
|
+
}
|
|
98
|
+
if (target instanceof RegExp) {
|
|
99
|
+
const cloned$1 = new RegExp(target);
|
|
100
|
+
cloned$1[annotationKey] = annotations;
|
|
101
|
+
return cloned$1;
|
|
102
|
+
}
|
|
103
|
+
if (Object.getPrototypeOf(target) !== Object.prototype && Object.getPrototypeOf(target) !== null) return target;
|
|
104
|
+
const cloned = Object.create(Object.getPrototypeOf(target), Object.getOwnPropertyDescriptors(target));
|
|
105
|
+
cloned[annotationKey] = annotations;
|
|
106
|
+
return cloned;
|
|
107
|
+
}
|
|
108
|
+
/**
|
|
109
|
+
* Injects annotations into parser state while preserving state shape.
|
|
110
|
+
*
|
|
111
|
+
* - Primitive, null, and undefined states are wrapped with internal metadata.
|
|
112
|
+
* - Array states are cloned and annotated without mutating the original.
|
|
113
|
+
* - Plain object states are shallow-cloned with annotations attached.
|
|
114
|
+
* - Built-in object states (Date/Map/Set/RegExp) are cloned by constructor.
|
|
115
|
+
* - Other non-plain object states are cloned via prototype/descriptors.
|
|
116
|
+
*
|
|
117
|
+
* @param state The parser state to annotate.
|
|
118
|
+
* @param annotations The annotations to inject.
|
|
119
|
+
* @returns Annotated state.
|
|
120
|
+
* @internal
|
|
121
|
+
*/
|
|
122
|
+
function injectAnnotations(state, annotations) {
|
|
123
|
+
if (state == null || typeof state !== "object") {
|
|
124
|
+
const wrapper = {};
|
|
125
|
+
Object.defineProperties(wrapper, {
|
|
126
|
+
[annotationKey]: {
|
|
127
|
+
value: annotations,
|
|
128
|
+
enumerable: true,
|
|
129
|
+
writable: true,
|
|
130
|
+
configurable: true
|
|
131
|
+
},
|
|
132
|
+
[annotationStateValueKey]: {
|
|
133
|
+
value: state,
|
|
134
|
+
enumerable: false,
|
|
135
|
+
writable: true,
|
|
136
|
+
configurable: true
|
|
137
|
+
},
|
|
138
|
+
[annotationWrapperKey]: {
|
|
139
|
+
value: true,
|
|
140
|
+
enumerable: false,
|
|
141
|
+
writable: true,
|
|
142
|
+
configurable: true
|
|
143
|
+
}
|
|
144
|
+
});
|
|
145
|
+
injectedAnnotationWrappers.add(wrapper);
|
|
146
|
+
return wrapper;
|
|
147
|
+
}
|
|
148
|
+
if (Array.isArray(state)) {
|
|
149
|
+
const cloned$1 = [...state];
|
|
150
|
+
cloned$1[annotationKey] = annotations;
|
|
151
|
+
return cloned$1;
|
|
152
|
+
}
|
|
153
|
+
if (isInjectedAnnotationWrapper(state)) {
|
|
154
|
+
state[annotationKey] = annotations;
|
|
155
|
+
return state;
|
|
156
|
+
}
|
|
157
|
+
if (state instanceof Date) {
|
|
158
|
+
const cloned$1 = new Date(state.getTime());
|
|
159
|
+
cloned$1[annotationKey] = annotations;
|
|
160
|
+
return cloned$1;
|
|
161
|
+
}
|
|
162
|
+
if (state instanceof Map) {
|
|
163
|
+
const cloned$1 = new Map(state);
|
|
164
|
+
cloned$1[annotationKey] = annotations;
|
|
165
|
+
return cloned$1;
|
|
166
|
+
}
|
|
167
|
+
if (state instanceof Set) {
|
|
168
|
+
const cloned$1 = new Set(state);
|
|
169
|
+
cloned$1[annotationKey] = annotations;
|
|
170
|
+
return cloned$1;
|
|
171
|
+
}
|
|
172
|
+
if (state instanceof RegExp) {
|
|
173
|
+
const cloned$1 = new RegExp(state);
|
|
174
|
+
cloned$1[annotationKey] = annotations;
|
|
175
|
+
return cloned$1;
|
|
176
|
+
}
|
|
177
|
+
const proto = Object.getPrototypeOf(state);
|
|
178
|
+
if (proto === Object.prototype || proto === null) return {
|
|
179
|
+
...state,
|
|
180
|
+
[annotationKey]: annotations
|
|
181
|
+
};
|
|
182
|
+
const cloned = Object.create(proto, Object.getOwnPropertyDescriptors(state));
|
|
183
|
+
cloned[annotationKey] = annotations;
|
|
184
|
+
return cloned;
|
|
185
|
+
}
|
|
186
|
+
/**
|
|
187
|
+
* Unwraps a primitive-state annotation wrapper injected by Optique internals.
|
|
188
|
+
*
|
|
189
|
+
* @param value Value to potentially unwrap.
|
|
190
|
+
* @returns The unwrapped primitive value when the input is an injected wrapper;
|
|
191
|
+
* otherwise the original value.
|
|
192
|
+
* @internal
|
|
193
|
+
*/
|
|
194
|
+
function unwrapInjectedAnnotationWrapper(value) {
|
|
195
|
+
if (value == null || typeof value !== "object") return value;
|
|
196
|
+
const valueRecord = value;
|
|
197
|
+
if (valueRecord[annotationWrapperKey] !== true) return value;
|
|
198
|
+
const ownKeys = Reflect.ownKeys(valueRecord);
|
|
199
|
+
if (ownKeys.length === 3 && ownKeys.every((key) => annotationWrapperKeys.has(key)) && isInjectedAnnotationWrapper(value)) return valueRecord[annotationStateValueKey];
|
|
200
|
+
return value;
|
|
201
|
+
}
|
|
202
|
+
/**
|
|
203
|
+
* Returns whether the given value is an internal primitive-state annotation
|
|
204
|
+
* wrapper that was injected by Optique.
|
|
205
|
+
*
|
|
206
|
+
* @param value Value to check.
|
|
207
|
+
* @returns `true` if the value is an injected internal wrapper.
|
|
208
|
+
* @internal
|
|
209
|
+
*/
|
|
210
|
+
function isInjectedAnnotationWrapper(value) {
|
|
211
|
+
return value != null && typeof value === "object" && injectedAnnotationWrappers.has(value);
|
|
212
|
+
}
|
|
38
213
|
|
|
39
214
|
//#endregion
|
|
40
215
|
exports.annotationKey = annotationKey;
|
|
41
|
-
exports.
|
|
216
|
+
exports.annotationStateValueKey = annotationStateValueKey;
|
|
217
|
+
exports.annotationWrapperKey = annotationWrapperKey;
|
|
218
|
+
exports.getAnnotations = getAnnotations;
|
|
219
|
+
exports.inheritAnnotations = inheritAnnotations;
|
|
220
|
+
exports.injectAnnotations = injectAnnotations;
|
|
221
|
+
exports.isInjectedAnnotationWrapper = isInjectedAnnotationWrapper;
|
|
222
|
+
exports.unwrapInjectedAnnotationWrapper = unwrapInjectedAnnotationWrapper;
|
package/dist/annotations.d.cts
CHANGED
|
@@ -14,6 +14,18 @@
|
|
|
14
14
|
* @since 0.10.0
|
|
15
15
|
*/
|
|
16
16
|
declare const annotationKey: unique symbol;
|
|
17
|
+
/**
|
|
18
|
+
* Internal key for preserving primitive parser state values when annotations
|
|
19
|
+
* are injected into non-object states.
|
|
20
|
+
* @internal
|
|
21
|
+
*/
|
|
22
|
+
declare const annotationStateValueKey: unique symbol;
|
|
23
|
+
/**
|
|
24
|
+
* Internal marker key that indicates annotation wrapping was injected by
|
|
25
|
+
* Optique internals for non-object states.
|
|
26
|
+
* @internal
|
|
27
|
+
*/
|
|
28
|
+
declare const annotationWrapperKey: unique symbol;
|
|
17
29
|
/**
|
|
18
30
|
* Annotations that can be passed to parsers during execution.
|
|
19
31
|
* Allows external packages to provide additional data that parsers can access
|
|
@@ -56,5 +68,51 @@ interface ParseOptions {
|
|
|
56
68
|
* ```
|
|
57
69
|
*/
|
|
58
70
|
declare function getAnnotations(state: unknown): Annotations | undefined;
|
|
71
|
+
/**
|
|
72
|
+
* Propagates annotations from one parser state to another.
|
|
73
|
+
*
|
|
74
|
+
* This is mainly used by parsers that rebuild array states with spread syntax.
|
|
75
|
+
* Array spread copies elements but drops custom symbol properties, so we need
|
|
76
|
+
* to reattach annotations explicitly when present.
|
|
77
|
+
*
|
|
78
|
+
* @param source The original state that may carry annotations.
|
|
79
|
+
* @param target The new state to receive annotations.
|
|
80
|
+
* @returns The target state, with annotations copied when available.
|
|
81
|
+
* @internal
|
|
82
|
+
*/
|
|
83
|
+
declare function inheritAnnotations<T>(source: unknown, target: T): T;
|
|
84
|
+
/**
|
|
85
|
+
* Injects annotations into parser state while preserving state shape.
|
|
86
|
+
*
|
|
87
|
+
* - Primitive, null, and undefined states are wrapped with internal metadata.
|
|
88
|
+
* - Array states are cloned and annotated without mutating the original.
|
|
89
|
+
* - Plain object states are shallow-cloned with annotations attached.
|
|
90
|
+
* - Built-in object states (Date/Map/Set/RegExp) are cloned by constructor.
|
|
91
|
+
* - Other non-plain object states are cloned via prototype/descriptors.
|
|
92
|
+
*
|
|
93
|
+
* @param state The parser state to annotate.
|
|
94
|
+
* @param annotations The annotations to inject.
|
|
95
|
+
* @returns Annotated state.
|
|
96
|
+
* @internal
|
|
97
|
+
*/
|
|
98
|
+
declare function injectAnnotations<TState>(state: TState, annotations: Annotations): TState;
|
|
99
|
+
/**
|
|
100
|
+
* Unwraps a primitive-state annotation wrapper injected by Optique internals.
|
|
101
|
+
*
|
|
102
|
+
* @param value Value to potentially unwrap.
|
|
103
|
+
* @returns The unwrapped primitive value when the input is an injected wrapper;
|
|
104
|
+
* otherwise the original value.
|
|
105
|
+
* @internal
|
|
106
|
+
*/
|
|
107
|
+
declare function unwrapInjectedAnnotationWrapper<T>(value: T): T;
|
|
108
|
+
/**
|
|
109
|
+
* Returns whether the given value is an internal primitive-state annotation
|
|
110
|
+
* wrapper that was injected by Optique.
|
|
111
|
+
*
|
|
112
|
+
* @param value Value to check.
|
|
113
|
+
* @returns `true` if the value is an injected internal wrapper.
|
|
114
|
+
* @internal
|
|
115
|
+
*/
|
|
116
|
+
declare function isInjectedAnnotationWrapper(value: unknown): boolean;
|
|
59
117
|
//#endregion
|
|
60
|
-
export { Annotations, ParseOptions, annotationKey, getAnnotations };
|
|
118
|
+
export { Annotations, ParseOptions, annotationKey, annotationStateValueKey, annotationWrapperKey, getAnnotations, inheritAnnotations, injectAnnotations, isInjectedAnnotationWrapper, unwrapInjectedAnnotationWrapper };
|
package/dist/annotations.d.ts
CHANGED
|
@@ -14,6 +14,18 @@
|
|
|
14
14
|
* @since 0.10.0
|
|
15
15
|
*/
|
|
16
16
|
declare const annotationKey: unique symbol;
|
|
17
|
+
/**
|
|
18
|
+
* Internal key for preserving primitive parser state values when annotations
|
|
19
|
+
* are injected into non-object states.
|
|
20
|
+
* @internal
|
|
21
|
+
*/
|
|
22
|
+
declare const annotationStateValueKey: unique symbol;
|
|
23
|
+
/**
|
|
24
|
+
* Internal marker key that indicates annotation wrapping was injected by
|
|
25
|
+
* Optique internals for non-object states.
|
|
26
|
+
* @internal
|
|
27
|
+
*/
|
|
28
|
+
declare const annotationWrapperKey: unique symbol;
|
|
17
29
|
/**
|
|
18
30
|
* Annotations that can be passed to parsers during execution.
|
|
19
31
|
* Allows external packages to provide additional data that parsers can access
|
|
@@ -56,5 +68,51 @@ interface ParseOptions {
|
|
|
56
68
|
* ```
|
|
57
69
|
*/
|
|
58
70
|
declare function getAnnotations(state: unknown): Annotations | undefined;
|
|
71
|
+
/**
|
|
72
|
+
* Propagates annotations from one parser state to another.
|
|
73
|
+
*
|
|
74
|
+
* This is mainly used by parsers that rebuild array states with spread syntax.
|
|
75
|
+
* Array spread copies elements but drops custom symbol properties, so we need
|
|
76
|
+
* to reattach annotations explicitly when present.
|
|
77
|
+
*
|
|
78
|
+
* @param source The original state that may carry annotations.
|
|
79
|
+
* @param target The new state to receive annotations.
|
|
80
|
+
* @returns The target state, with annotations copied when available.
|
|
81
|
+
* @internal
|
|
82
|
+
*/
|
|
83
|
+
declare function inheritAnnotations<T>(source: unknown, target: T): T;
|
|
84
|
+
/**
|
|
85
|
+
* Injects annotations into parser state while preserving state shape.
|
|
86
|
+
*
|
|
87
|
+
* - Primitive, null, and undefined states are wrapped with internal metadata.
|
|
88
|
+
* - Array states are cloned and annotated without mutating the original.
|
|
89
|
+
* - Plain object states are shallow-cloned with annotations attached.
|
|
90
|
+
* - Built-in object states (Date/Map/Set/RegExp) are cloned by constructor.
|
|
91
|
+
* - Other non-plain object states are cloned via prototype/descriptors.
|
|
92
|
+
*
|
|
93
|
+
* @param state The parser state to annotate.
|
|
94
|
+
* @param annotations The annotations to inject.
|
|
95
|
+
* @returns Annotated state.
|
|
96
|
+
* @internal
|
|
97
|
+
*/
|
|
98
|
+
declare function injectAnnotations<TState>(state: TState, annotations: Annotations): TState;
|
|
99
|
+
/**
|
|
100
|
+
* Unwraps a primitive-state annotation wrapper injected by Optique internals.
|
|
101
|
+
*
|
|
102
|
+
* @param value Value to potentially unwrap.
|
|
103
|
+
* @returns The unwrapped primitive value when the input is an injected wrapper;
|
|
104
|
+
* otherwise the original value.
|
|
105
|
+
* @internal
|
|
106
|
+
*/
|
|
107
|
+
declare function unwrapInjectedAnnotationWrapper<T>(value: T): T;
|
|
108
|
+
/**
|
|
109
|
+
* Returns whether the given value is an internal primitive-state annotation
|
|
110
|
+
* wrapper that was injected by Optique.
|
|
111
|
+
*
|
|
112
|
+
* @param value Value to check.
|
|
113
|
+
* @returns `true` if the value is an injected internal wrapper.
|
|
114
|
+
* @internal
|
|
115
|
+
*/
|
|
116
|
+
declare function isInjectedAnnotationWrapper(value: unknown): boolean;
|
|
59
117
|
//#endregion
|
|
60
|
-
export { Annotations, ParseOptions, annotationKey, getAnnotations };
|
|
118
|
+
export { Annotations, ParseOptions, annotationKey, annotationStateValueKey, annotationWrapperKey, getAnnotations, inheritAnnotations, injectAnnotations, isInjectedAnnotationWrapper, unwrapInjectedAnnotationWrapper };
|
package/dist/annotations.js
CHANGED
|
@@ -15,6 +15,29 @@
|
|
|
15
15
|
*/
|
|
16
16
|
const annotationKey = Symbol.for("@optique/core/parser/annotation");
|
|
17
17
|
/**
|
|
18
|
+
* Internal key for preserving primitive parser state values when annotations
|
|
19
|
+
* are injected into non-object states.
|
|
20
|
+
* @internal
|
|
21
|
+
*/
|
|
22
|
+
const annotationStateValueKey = Symbol.for("@optique/core/parser/annotationStateValue");
|
|
23
|
+
/**
|
|
24
|
+
* Internal marker key that indicates annotation wrapping was injected by
|
|
25
|
+
* Optique internals for non-object states.
|
|
26
|
+
* @internal
|
|
27
|
+
*/
|
|
28
|
+
const annotationWrapperKey = Symbol.for("@optique/core/parser/annotationWrapper");
|
|
29
|
+
/**
|
|
30
|
+
* Internal symbol keys that define Optique's primitive-state annotation
|
|
31
|
+
* wrapper shape.
|
|
32
|
+
* @internal
|
|
33
|
+
*/
|
|
34
|
+
const annotationWrapperKeys = new Set([
|
|
35
|
+
annotationKey,
|
|
36
|
+
annotationStateValueKey,
|
|
37
|
+
annotationWrapperKey
|
|
38
|
+
]);
|
|
39
|
+
const injectedAnnotationWrappers = /* @__PURE__ */ new WeakSet();
|
|
40
|
+
/**
|
|
18
41
|
* Extracts annotations from parser state.
|
|
19
42
|
*
|
|
20
43
|
* @param state Parser state that may contain annotations
|
|
@@ -34,6 +57,158 @@ function getAnnotations(state) {
|
|
|
34
57
|
if (annotations != null && typeof annotations === "object") return annotations;
|
|
35
58
|
return void 0;
|
|
36
59
|
}
|
|
60
|
+
/**
|
|
61
|
+
* Propagates annotations from one parser state to another.
|
|
62
|
+
*
|
|
63
|
+
* This is mainly used by parsers that rebuild array states with spread syntax.
|
|
64
|
+
* Array spread copies elements but drops custom symbol properties, so we need
|
|
65
|
+
* to reattach annotations explicitly when present.
|
|
66
|
+
*
|
|
67
|
+
* @param source The original state that may carry annotations.
|
|
68
|
+
* @param target The new state to receive annotations.
|
|
69
|
+
* @returns The target state, with annotations copied when available.
|
|
70
|
+
* @internal
|
|
71
|
+
*/
|
|
72
|
+
function inheritAnnotations(source, target) {
|
|
73
|
+
const annotations = getAnnotations(source);
|
|
74
|
+
if (annotations === void 0) return target;
|
|
75
|
+
if (target == null || typeof target !== "object") return injectAnnotations(target, annotations);
|
|
76
|
+
if (isInjectedAnnotationWrapper(target)) return injectAnnotations(target, annotations);
|
|
77
|
+
if (Array.isArray(target)) {
|
|
78
|
+
const cloned$1 = [...target];
|
|
79
|
+
cloned$1[annotationKey] = annotations;
|
|
80
|
+
return cloned$1;
|
|
81
|
+
}
|
|
82
|
+
if (target instanceof Date) {
|
|
83
|
+
const cloned$1 = new Date(target.getTime());
|
|
84
|
+
cloned$1[annotationKey] = annotations;
|
|
85
|
+
return cloned$1;
|
|
86
|
+
}
|
|
87
|
+
if (target instanceof Map) {
|
|
88
|
+
const cloned$1 = new Map(target);
|
|
89
|
+
cloned$1[annotationKey] = annotations;
|
|
90
|
+
return cloned$1;
|
|
91
|
+
}
|
|
92
|
+
if (target instanceof Set) {
|
|
93
|
+
const cloned$1 = new Set(target);
|
|
94
|
+
cloned$1[annotationKey] = annotations;
|
|
95
|
+
return cloned$1;
|
|
96
|
+
}
|
|
97
|
+
if (target instanceof RegExp) {
|
|
98
|
+
const cloned$1 = new RegExp(target);
|
|
99
|
+
cloned$1[annotationKey] = annotations;
|
|
100
|
+
return cloned$1;
|
|
101
|
+
}
|
|
102
|
+
if (Object.getPrototypeOf(target) !== Object.prototype && Object.getPrototypeOf(target) !== null) return target;
|
|
103
|
+
const cloned = Object.create(Object.getPrototypeOf(target), Object.getOwnPropertyDescriptors(target));
|
|
104
|
+
cloned[annotationKey] = annotations;
|
|
105
|
+
return cloned;
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* Injects annotations into parser state while preserving state shape.
|
|
109
|
+
*
|
|
110
|
+
* - Primitive, null, and undefined states are wrapped with internal metadata.
|
|
111
|
+
* - Array states are cloned and annotated without mutating the original.
|
|
112
|
+
* - Plain object states are shallow-cloned with annotations attached.
|
|
113
|
+
* - Built-in object states (Date/Map/Set/RegExp) are cloned by constructor.
|
|
114
|
+
* - Other non-plain object states are cloned via prototype/descriptors.
|
|
115
|
+
*
|
|
116
|
+
* @param state The parser state to annotate.
|
|
117
|
+
* @param annotations The annotations to inject.
|
|
118
|
+
* @returns Annotated state.
|
|
119
|
+
* @internal
|
|
120
|
+
*/
|
|
121
|
+
function injectAnnotations(state, annotations) {
|
|
122
|
+
if (state == null || typeof state !== "object") {
|
|
123
|
+
const wrapper = {};
|
|
124
|
+
Object.defineProperties(wrapper, {
|
|
125
|
+
[annotationKey]: {
|
|
126
|
+
value: annotations,
|
|
127
|
+
enumerable: true,
|
|
128
|
+
writable: true,
|
|
129
|
+
configurable: true
|
|
130
|
+
},
|
|
131
|
+
[annotationStateValueKey]: {
|
|
132
|
+
value: state,
|
|
133
|
+
enumerable: false,
|
|
134
|
+
writable: true,
|
|
135
|
+
configurable: true
|
|
136
|
+
},
|
|
137
|
+
[annotationWrapperKey]: {
|
|
138
|
+
value: true,
|
|
139
|
+
enumerable: false,
|
|
140
|
+
writable: true,
|
|
141
|
+
configurable: true
|
|
142
|
+
}
|
|
143
|
+
});
|
|
144
|
+
injectedAnnotationWrappers.add(wrapper);
|
|
145
|
+
return wrapper;
|
|
146
|
+
}
|
|
147
|
+
if (Array.isArray(state)) {
|
|
148
|
+
const cloned$1 = [...state];
|
|
149
|
+
cloned$1[annotationKey] = annotations;
|
|
150
|
+
return cloned$1;
|
|
151
|
+
}
|
|
152
|
+
if (isInjectedAnnotationWrapper(state)) {
|
|
153
|
+
state[annotationKey] = annotations;
|
|
154
|
+
return state;
|
|
155
|
+
}
|
|
156
|
+
if (state instanceof Date) {
|
|
157
|
+
const cloned$1 = new Date(state.getTime());
|
|
158
|
+
cloned$1[annotationKey] = annotations;
|
|
159
|
+
return cloned$1;
|
|
160
|
+
}
|
|
161
|
+
if (state instanceof Map) {
|
|
162
|
+
const cloned$1 = new Map(state);
|
|
163
|
+
cloned$1[annotationKey] = annotations;
|
|
164
|
+
return cloned$1;
|
|
165
|
+
}
|
|
166
|
+
if (state instanceof Set) {
|
|
167
|
+
const cloned$1 = new Set(state);
|
|
168
|
+
cloned$1[annotationKey] = annotations;
|
|
169
|
+
return cloned$1;
|
|
170
|
+
}
|
|
171
|
+
if (state instanceof RegExp) {
|
|
172
|
+
const cloned$1 = new RegExp(state);
|
|
173
|
+
cloned$1[annotationKey] = annotations;
|
|
174
|
+
return cloned$1;
|
|
175
|
+
}
|
|
176
|
+
const proto = Object.getPrototypeOf(state);
|
|
177
|
+
if (proto === Object.prototype || proto === null) return {
|
|
178
|
+
...state,
|
|
179
|
+
[annotationKey]: annotations
|
|
180
|
+
};
|
|
181
|
+
const cloned = Object.create(proto, Object.getOwnPropertyDescriptors(state));
|
|
182
|
+
cloned[annotationKey] = annotations;
|
|
183
|
+
return cloned;
|
|
184
|
+
}
|
|
185
|
+
/**
|
|
186
|
+
* Unwraps a primitive-state annotation wrapper injected by Optique internals.
|
|
187
|
+
*
|
|
188
|
+
* @param value Value to potentially unwrap.
|
|
189
|
+
* @returns The unwrapped primitive value when the input is an injected wrapper;
|
|
190
|
+
* otherwise the original value.
|
|
191
|
+
* @internal
|
|
192
|
+
*/
|
|
193
|
+
function unwrapInjectedAnnotationWrapper(value) {
|
|
194
|
+
if (value == null || typeof value !== "object") return value;
|
|
195
|
+
const valueRecord = value;
|
|
196
|
+
if (valueRecord[annotationWrapperKey] !== true) return value;
|
|
197
|
+
const ownKeys = Reflect.ownKeys(valueRecord);
|
|
198
|
+
if (ownKeys.length === 3 && ownKeys.every((key) => annotationWrapperKeys.has(key)) && isInjectedAnnotationWrapper(value)) return valueRecord[annotationStateValueKey];
|
|
199
|
+
return value;
|
|
200
|
+
}
|
|
201
|
+
/**
|
|
202
|
+
* Returns whether the given value is an internal primitive-state annotation
|
|
203
|
+
* wrapper that was injected by Optique.
|
|
204
|
+
*
|
|
205
|
+
* @param value Value to check.
|
|
206
|
+
* @returns `true` if the value is an injected internal wrapper.
|
|
207
|
+
* @internal
|
|
208
|
+
*/
|
|
209
|
+
function isInjectedAnnotationWrapper(value) {
|
|
210
|
+
return value != null && typeof value === "object" && injectedAnnotationWrappers.has(value);
|
|
211
|
+
}
|
|
37
212
|
|
|
38
213
|
//#endregion
|
|
39
|
-
export { annotationKey, getAnnotations };
|
|
214
|
+
export { annotationKey, annotationStateValueKey, annotationWrapperKey, getAnnotations, inheritAnnotations, injectAnnotations, isInjectedAnnotationWrapper, unwrapInjectedAnnotationWrapper };
|
package/dist/constructs.cjs
CHANGED
|
@@ -837,8 +837,11 @@ function object(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
837
837
|
const parserKeys = Reflect.ownKeys(parsers);
|
|
838
838
|
const parserPairs = parserKeys.map((k) => [k, parsers[k]]);
|
|
839
839
|
parserPairs.sort(([_, parserA], [__, parserB]) => parserB.priority - parserA.priority);
|
|
840
|
-
const
|
|
841
|
-
|
|
840
|
+
const createInitialState = () => {
|
|
841
|
+
const state = {};
|
|
842
|
+
for (const key of parserKeys) state[key] = parsers[key].initialState;
|
|
843
|
+
return state;
|
|
844
|
+
};
|
|
842
845
|
if (!options.allowDuplicates) checkDuplicateOptionNames(parserPairs.map(([field, parser]) => [field, parser.usage]));
|
|
843
846
|
const noMatchContext = analyzeNoMatchContext(parserKeys.map((k) => parsers[k]));
|
|
844
847
|
const combinedMode = parserKeys.some((k) => parsers[k].$mode === "async") ? "async" : "sync";
|
|
@@ -974,7 +977,9 @@ function object(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
974
977
|
$stateType: [],
|
|
975
978
|
priority: Math.max(...parserKeys.map((k) => parsers[k].priority)),
|
|
976
979
|
usage: applyHiddenToUsage(parserPairs.flatMap(([_, p]) => p.usage), options.hidden),
|
|
977
|
-
initialState
|
|
980
|
+
get initialState() {
|
|
981
|
+
return createInitialState();
|
|
982
|
+
},
|
|
978
983
|
parse(context) {
|
|
979
984
|
return require_mode_dispatch.dispatchByMode(combinedMode, () => parseSync(context), () => parseAsync(context));
|
|
980
985
|
},
|
package/dist/constructs.js
CHANGED
|
@@ -837,8 +837,11 @@ function object(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
837
837
|
const parserKeys = Reflect.ownKeys(parsers);
|
|
838
838
|
const parserPairs = parserKeys.map((k) => [k, parsers[k]]);
|
|
839
839
|
parserPairs.sort(([_, parserA], [__, parserB]) => parserB.priority - parserA.priority);
|
|
840
|
-
const
|
|
841
|
-
|
|
840
|
+
const createInitialState = () => {
|
|
841
|
+
const state = {};
|
|
842
|
+
for (const key of parserKeys) state[key] = parsers[key].initialState;
|
|
843
|
+
return state;
|
|
844
|
+
};
|
|
842
845
|
if (!options.allowDuplicates) checkDuplicateOptionNames(parserPairs.map(([field, parser]) => [field, parser.usage]));
|
|
843
846
|
const noMatchContext = analyzeNoMatchContext(parserKeys.map((k) => parsers[k]));
|
|
844
847
|
const combinedMode = parserKeys.some((k) => parsers[k].$mode === "async") ? "async" : "sync";
|
|
@@ -974,7 +977,9 @@ function object(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
974
977
|
$stateType: [],
|
|
975
978
|
priority: Math.max(...parserKeys.map((k) => parsers[k].priority)),
|
|
976
979
|
usage: applyHiddenToUsage(parserPairs.flatMap(([_, p]) => p.usage), options.hidden),
|
|
977
|
-
initialState
|
|
980
|
+
get initialState() {
|
|
981
|
+
return createInitialState();
|
|
982
|
+
},
|
|
978
983
|
parse(context) {
|
|
979
984
|
return dispatchByMode(combinedMode, () => parseSync(context), () => parseAsync(context));
|
|
980
985
|
},
|
package/dist/facade.cjs
CHANGED
|
@@ -1122,10 +1122,7 @@ function runWithAsync(parser, programName, contexts, options) {
|
|
|
1122
1122
|
* @returns A new parser with annotations in its initial state.
|
|
1123
1123
|
*/
|
|
1124
1124
|
function injectAnnotationsIntoParser(parser, annotations) {
|
|
1125
|
-
const newInitialState =
|
|
1126
|
-
...typeof parser.initialState === "object" && parser.initialState !== null ? parser.initialState : {},
|
|
1127
|
-
[require_annotations.annotationKey]: annotations
|
|
1128
|
-
};
|
|
1125
|
+
const newInitialState = require_annotations.injectAnnotations(parser.initialState, annotations);
|
|
1129
1126
|
return {
|
|
1130
1127
|
...parser,
|
|
1131
1128
|
initialState: newInitialState
|
package/dist/facade.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { injectAnnotations } from "./annotations.js";
|
|
2
2
|
import { commandLine, formatMessage, lineBreak, message, optionName, text, value } from "./message.js";
|
|
3
3
|
import { bash, fish, nu, pwsh, zsh } from "./completion.js";
|
|
4
4
|
import { dispatchByMode } from "./mode-dispatch.js";
|
|
@@ -1122,10 +1122,7 @@ function runWithAsync(parser, programName, contexts, options) {
|
|
|
1122
1122
|
* @returns A new parser with annotations in its initial state.
|
|
1123
1123
|
*/
|
|
1124
1124
|
function injectAnnotationsIntoParser(parser, annotations) {
|
|
1125
|
-
const newInitialState =
|
|
1126
|
-
...typeof parser.initialState === "object" && parser.initialState !== null ? parser.initialState : {},
|
|
1127
|
-
[annotationKey]: annotations
|
|
1128
|
-
};
|
|
1125
|
+
const newInitialState = injectAnnotations(parser.initialState, annotations);
|
|
1129
1126
|
return {
|
|
1130
1127
|
...parser,
|
|
1131
1128
|
initialState: newInitialState
|