@optique/core 1.3.0-dev.2379 → 1.3.0-dev.2381
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/constructs.cjs +344 -38
- package/dist/constructs.js +345 -39
- package/dist/dependency-metadata.cjs +13 -1
- package/dist/dependency-metadata.d.cts +20 -1
- package/dist/dependency-metadata.d.ts +20 -1
- package/dist/dependency-metadata.js +13 -1
- package/dist/dependency-runtime.cjs +216 -0
- package/dist/dependency-runtime.d.cts +162 -1
- package/dist/dependency-runtime.d.ts +162 -1
- package/dist/dependency-runtime.js +213 -1
- package/dist/facade.cjs +54 -26
- package/dist/facade.js +55 -27
- package/dist/index.d.cts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/internal/parser.cjs +23 -3
- package/dist/internal/parser.d.cts +80 -3
- package/dist/internal/parser.d.ts +80 -3
- package/dist/internal/parser.js +23 -4
- package/dist/modifiers.cjs +43 -2
- package/dist/modifiers.js +43 -2
- package/dist/parser.d.cts +2 -2
- package/dist/parser.d.ts +2 -2
- package/dist/primitives.cjs +14 -0
- package/dist/primitives.js +15 -1
- package/package.json +2 -2
package/dist/constructs.js
CHANGED
|
@@ -5,7 +5,7 @@ import { extractArgumentMetavars, extractCommandNames, extractOptionNames, isDoc
|
|
|
5
5
|
import { deduplicateDocFragments } from "./doc.js";
|
|
6
6
|
import { dispatchByMode, dispatchIterableByMode } from "./internal/mode-dispatch.js";
|
|
7
7
|
import { createDependencySourceState, dependencyId, isDependencySourceState, isPendingDependencySourceState, isWrappedDependencySource, wrappedDependencySourceMarker } from "./internal/dependency.js";
|
|
8
|
-
import { buildRuntimeNodesFromArray, buildRuntimeNodesFromPairs, collectExplicitSourceValues, collectExplicitSourceValuesAsync, collectSourcesFromState, createDependencyRuntimeContext, fillMissingSourceDefaults, fillMissingSourceDefaultsAsync, resolveStateWithRuntime, resolveStateWithRuntimeAsync } from "./dependency-runtime.js";
|
|
8
|
+
import { buildRuntimeNodesFromArray, buildRuntimeNodesFromPairs, collectExplicitSourceValues, collectExplicitSourceValuesAsync, collectSourcesFromState, completeEffectfulSourcesAsync, createDependencyRuntimeContext, effectfulSchedulingNodesKey, fillMissingSourceDefaults, fillMissingSourceDefaultsAsync, resolveStateWithRuntime, resolveStateWithRuntimeAsync } from "./dependency-runtime.js";
|
|
9
9
|
import { defineInheritedAnnotationParser, defineParseLanes, getOwnParseLanes, getParserSuggestRuntimeNodes, unmatchedNonCliDependencySourceStateMarker } from "./internal/parser.js";
|
|
10
10
|
import { annotationViewTargets, getWrappedChildParseState, getWrappedChildState, reconcileObjectChildState, unwrapAnnotationView } from "./annotation-state.js";
|
|
11
11
|
import { allowDuplicateLeadingCommandNamesKey } from "./internal/command-alias.js";
|
|
@@ -58,6 +58,117 @@ function filterPreCompletedRuntimeNodes(nodes, preCompletedKeys) {
|
|
|
58
58
|
return segment == null || !preCompletedKeys.has(segment);
|
|
59
59
|
});
|
|
60
60
|
}
|
|
61
|
+
/**
|
|
62
|
+
* Runs the effectful source completion pass for a construct's direct
|
|
63
|
+
* children and merges the completed results into the construct's
|
|
64
|
+
* pre-completed cache so its final completion phase reuses them instead
|
|
65
|
+
* of completing the same field twice.
|
|
66
|
+
*
|
|
67
|
+
* Returns a failure when an effectful completion fails (e.g., a cancelled
|
|
68
|
+
* prompt); the construct should propagate it as its own completion
|
|
69
|
+
* failure. Returns `undefined` on success.
|
|
70
|
+
*/
|
|
71
|
+
/**
|
|
72
|
+
* Expands runtime nodes through nested constructs for effectful source
|
|
73
|
+
* scheduling and demand detection.
|
|
74
|
+
*
|
|
75
|
+
* A node without effectful-source or consumer metadata whose parser
|
|
76
|
+
* exposes child field pairs (e.g., a `tuple()` child of `concat()`, or a
|
|
77
|
+
* nested `object()` field) is replaced by nodes for its children so that
|
|
78
|
+
* an effectful source nested one or more constructs deep is still
|
|
79
|
+
* completed before any sibling consumer completes. Array states use
|
|
80
|
+
* numeric path segments and record states use their field keys, matching
|
|
81
|
+
* the paths that child completion (and parse-time tracing) uses.
|
|
82
|
+
*/
|
|
83
|
+
function expandEffectfulRuntimeNodes(nodes) {
|
|
84
|
+
const expanded = [];
|
|
85
|
+
const visit = (node) => {
|
|
86
|
+
const meta = node.parser.dependencyMetadata;
|
|
87
|
+
if (meta?.source?.completeSource != null || meta?.derived != null) {
|
|
88
|
+
expanded.push(node);
|
|
89
|
+
return;
|
|
90
|
+
}
|
|
91
|
+
const schedulingNodes = node.parser[effectfulSchedulingNodesKey];
|
|
92
|
+
if (schedulingNodes != null) {
|
|
93
|
+
for (const child of schedulingNodes(node.state, node.path)) visit(child);
|
|
94
|
+
return;
|
|
95
|
+
}
|
|
96
|
+
const pairs = node.parser[fieldParsersKey];
|
|
97
|
+
if (pairs == null || node.state == null || typeof node.state !== "object") {
|
|
98
|
+
expanded.push(node);
|
|
99
|
+
return;
|
|
100
|
+
}
|
|
101
|
+
const duplicateFieldNames = collectDuplicateFieldNames(pairs);
|
|
102
|
+
const state = node.state;
|
|
103
|
+
for (const [field, childParser] of pairs) {
|
|
104
|
+
if (duplicateFieldNames.has(field)) continue;
|
|
105
|
+
const segment = Array.isArray(state) && typeof field === "string" ? Number(field) : field;
|
|
106
|
+
const childState = Array.isArray(state) ? state[segment] : state[field];
|
|
107
|
+
visit({
|
|
108
|
+
path: [...node.path, segment],
|
|
109
|
+
parser: childParser,
|
|
110
|
+
state: getWrappedChildState(state, childState, childParser)
|
|
111
|
+
});
|
|
112
|
+
}
|
|
113
|
+
};
|
|
114
|
+
for (const node of nodes) visit(node);
|
|
115
|
+
return expanded;
|
|
116
|
+
}
|
|
117
|
+
function isDeferredCompletionResult(result) {
|
|
118
|
+
return typeof result === "object" && result !== null && "success" in result && result.success === true && "deferred" in result && result.deferred === true;
|
|
119
|
+
}
|
|
120
|
+
/**
|
|
121
|
+
* Returns the keys of pre-completed results that are settled (not
|
|
122
|
+
* deferred).
|
|
123
|
+
*
|
|
124
|
+
* A deferred pre-completion—e.g., a demand-only prompt invoked during
|
|
125
|
+
* Phase 1 through a source binding wrapper, before consumer demand was
|
|
126
|
+
* known—must remain visible to the effectful scheduling pass so it can
|
|
127
|
+
* complete once demand is discovered; the scheduler then replaces the
|
|
128
|
+
* cached placeholder result with the real one.
|
|
129
|
+
*/
|
|
130
|
+
function settledPreCompletedKeys(preCompleted) {
|
|
131
|
+
const keys = /* @__PURE__ */ new Set();
|
|
132
|
+
for (const [key, result] of preCompleted) {
|
|
133
|
+
if (isDeferredCompletionResult(result)) continue;
|
|
134
|
+
keys.add(key);
|
|
135
|
+
}
|
|
136
|
+
return keys;
|
|
137
|
+
}
|
|
138
|
+
/**
|
|
139
|
+
* Returns the first failure among pre-completed results, if any.
|
|
140
|
+
*
|
|
141
|
+
* A failed pre-completion (e.g., a prompt cancelled during Phase 1
|
|
142
|
+
* through a source binding wrapper) fails the construct in its final
|
|
143
|
+
* completion phase anyway, so the scheduling pass must not run further
|
|
144
|
+
* effectful completions after it—cancellation stops later prompts
|
|
145
|
+
* immediately.
|
|
146
|
+
*/
|
|
147
|
+
function firstPreCompletedFailure(preCompleted) {
|
|
148
|
+
for (const result of preCompleted.values()) if (typeof result === "object" && result !== null && "success" in result && result.success === false && "error" in result) return result.error;
|
|
149
|
+
return void 0;
|
|
150
|
+
}
|
|
151
|
+
async function scheduleEffectfulSourceCompletions(nodes, state, runtime, exec, preCompleted, demandNodes) {
|
|
152
|
+
const preCompletedFailure = firstPreCompletedFailure(preCompleted);
|
|
153
|
+
if (preCompletedFailure != null) return {
|
|
154
|
+
success: false,
|
|
155
|
+
error: preCompletedFailure
|
|
156
|
+
};
|
|
157
|
+
const direct = new Set(nodes);
|
|
158
|
+
const effectful = await completeEffectfulSourcesAsync(expandEffectfulRuntimeNodes(nodes), state, runtime, exec, {
|
|
159
|
+
...demandNodes != null ? { demandNodes: expandEffectfulRuntimeNodes(demandNodes) } : {},
|
|
160
|
+
isReusable: (node) => direct.has(node)
|
|
161
|
+
});
|
|
162
|
+
if (!effectful.success) return {
|
|
163
|
+
success: false,
|
|
164
|
+
error: effectful.error
|
|
165
|
+
};
|
|
166
|
+
for (const { key, result } of effectful.completed) {
|
|
167
|
+
const cacheKey = typeof key === "number" ? String(key) : key;
|
|
168
|
+
preCompleted.set(cacheKey, result);
|
|
169
|
+
}
|
|
170
|
+
return void 0;
|
|
171
|
+
}
|
|
61
172
|
function buildIndexedParserPairs(parsers) {
|
|
62
173
|
return parsers.map((parser, index) => [String(index), parser]);
|
|
63
174
|
}
|
|
@@ -792,16 +903,42 @@ function getNoMatchError(options, noMatchContext) {
|
|
|
792
903
|
const customNoMatch = options?.errors?.noMatch;
|
|
793
904
|
return customNoMatch ? typeof customNoMatch === "function" ? customNoMatch(noMatchContext) : customNoMatch : generateNoMatchError(noMatchContext);
|
|
794
905
|
}
|
|
906
|
+
/**
|
|
907
|
+
* Installs the effectful scheduling hook on an exclusive parser
|
|
908
|
+
* (`or()`/`longestMatch()`), exposing the committed branch so a parent
|
|
909
|
+
* construct's scheduling expansion can complete a source nested in the
|
|
910
|
+
* selected branch before parent-level dependency replay. The branch
|
|
911
|
+
* node's path appends the branch index, matching the execution path used
|
|
912
|
+
* when the committed branch completes.
|
|
913
|
+
*/
|
|
914
|
+
function defineExclusiveSchedulingNodes(exclusiveParser, parsers) {
|
|
915
|
+
Object.defineProperty(exclusiveParser, effectfulSchedulingNodesKey, {
|
|
916
|
+
value: ((state, parentPath) => {
|
|
917
|
+
const active = normalizeExclusiveState(state);
|
|
918
|
+
if (active == null) return [];
|
|
919
|
+
const [index, result] = active;
|
|
920
|
+
if (result?.success !== true) return [];
|
|
921
|
+
return [{
|
|
922
|
+
path: [...parentPath ?? [], index],
|
|
923
|
+
parser: parsers[index],
|
|
924
|
+
state: result.next.state
|
|
925
|
+
}];
|
|
926
|
+
}),
|
|
927
|
+
configurable: true,
|
|
928
|
+
enumerable: false
|
|
929
|
+
});
|
|
930
|
+
}
|
|
795
931
|
function composeExclusiveDependencyMetadata(parsers) {
|
|
796
932
|
const sourceBranches = parsers.filter((parser) => parser.dependencyMetadata?.source != null);
|
|
797
933
|
if (sourceBranches.length < 1) return void 0;
|
|
798
934
|
const sourceIds = new Set(sourceBranches.map((parser) => parser.dependencyMetadata.source.sourceId));
|
|
799
935
|
if (sourceIds.size !== 1) return void 0;
|
|
800
936
|
const sharedSource = sourceBranches[0].dependencyMetadata.source;
|
|
937
|
+
const everyBranchPreserves = sourceBranches.length === parsers.length && sourceBranches.every((parser) => parser.dependencyMetadata?.source?.preservesSourceValue !== false);
|
|
801
938
|
return { source: {
|
|
802
939
|
...sharedSource,
|
|
803
940
|
getMissingSourceValue: void 0,
|
|
804
|
-
preservesSourceValue:
|
|
941
|
+
preservesSourceValue: everyBranchPreserves,
|
|
805
942
|
extractSourceValue(state) {
|
|
806
943
|
if (!Array.isArray(state) || state.length !== 2 || typeof state[0] !== "number") return void 0;
|
|
807
944
|
const [index, parserResult] = state;
|
|
@@ -809,6 +946,14 @@ function composeExclusiveDependencyMetadata(parsers) {
|
|
|
809
946
|
const branchSource = parsers[index].dependencyMetadata?.source;
|
|
810
947
|
if (branchSource?.extractSourceValue == null) return void 0;
|
|
811
948
|
return branchSource.extractSourceValue(parserResult.next.state);
|
|
949
|
+
},
|
|
950
|
+
completeSource(state, exec) {
|
|
951
|
+
if (!Array.isArray(state) || state.length !== 2 || typeof state[0] !== "number") return Promise.resolve(void 0);
|
|
952
|
+
const [index, parserResult] = state;
|
|
953
|
+
if (!parserResult?.success) return Promise.resolve(void 0);
|
|
954
|
+
const branchSource = parsers[index].dependencyMetadata?.source;
|
|
955
|
+
if (branchSource?.completeSource == null) return Promise.resolve(void 0);
|
|
956
|
+
return branchSource.completeSource(parserResult.next.state, exec);
|
|
812
957
|
}
|
|
813
958
|
} };
|
|
814
959
|
}
|
|
@@ -1310,6 +1455,7 @@ function or(...args) {
|
|
|
1310
1455
|
};
|
|
1311
1456
|
const singleDependencyMetadata = composeExclusiveDependencyMetadata(parsers);
|
|
1312
1457
|
if (singleDependencyMetadata != null) singleResult.dependencyMetadata = singleDependencyMetadata;
|
|
1458
|
+
defineExclusiveSchedulingNodes(singleResult, parsers);
|
|
1313
1459
|
defineInheritedAnnotationParser(singleResult);
|
|
1314
1460
|
return fluent(singleResult);
|
|
1315
1461
|
}
|
|
@@ -1525,6 +1671,7 @@ function createLongestMatch(...args) {
|
|
|
1525
1671
|
};
|
|
1526
1672
|
const multiDependencyMetadata = composeExclusiveDependencyMetadata(parsers);
|
|
1527
1673
|
if (multiDependencyMetadata != null) multiResult.dependencyMetadata = multiDependencyMetadata;
|
|
1674
|
+
defineExclusiveSchedulingNodes(multiResult, parsers);
|
|
1528
1675
|
defineInheritedAnnotationParser(multiResult);
|
|
1529
1676
|
return fluent(multiResult);
|
|
1530
1677
|
}
|
|
@@ -1634,8 +1781,11 @@ async function* suggestObjectAsync(context, prefix, parserPairs) {
|
|
|
1634
1781
|
*
|
|
1635
1782
|
* @internal
|
|
1636
1783
|
*/
|
|
1637
|
-
function registerCompletedDependency(completed, registry) {
|
|
1638
|
-
if (isDependencySourceState(completed)
|
|
1784
|
+
function registerCompletedDependency(completed, registry, exec) {
|
|
1785
|
+
if (!isDependencySourceState(completed) || !completed.result.success) return;
|
|
1786
|
+
const sourceId = completed[dependencyId];
|
|
1787
|
+
const effectful = exec?.effectfulCompletionSession?.effectfulSources.has(sourceId) === true;
|
|
1788
|
+
if (effectful || !registry.has(sourceId)) registry.set(sourceId, completed.result.value);
|
|
1639
1789
|
}
|
|
1640
1790
|
/**
|
|
1641
1791
|
* Yields `(parser, state)` pairs for dependency source parsers whose field
|
|
@@ -1713,6 +1863,7 @@ function wrapAsDependencySourceState(completed, parser) {
|
|
|
1713
1863
|
const metadataSource = parser.dependencyMetadata?.source;
|
|
1714
1864
|
if (metadataSource?.preservesSourceValue === false) return void 0;
|
|
1715
1865
|
const hasDep = metadataSource != null || isWrappedDependencySource(parser) || isPendingDependencySourceState(parser.initialState);
|
|
1866
|
+
if (isDeferredCompletionResult(completed)) return void 0;
|
|
1716
1867
|
if (hasDep && typeof completed === "object" && completed !== null && "success" in completed && completed.success && "value" in completed && completed.value !== void 0) {
|
|
1717
1868
|
const depId = metadataSource?.sourceId ?? (isWrappedDependencySource(parser) ? parser[wrappedDependencySourceMarker][dependencyId] : parser.initialState[dependencyId]);
|
|
1718
1869
|
return createDependencySourceState(completed, depId);
|
|
@@ -1856,47 +2007,49 @@ async function preCompleteAndRegisterDependenciesAsync(state, fieldParserPairs,
|
|
|
1856
2007
|
const preCompleted = /* @__PURE__ */ new Map();
|
|
1857
2008
|
const parentResults = exec?.preCompletedByParser;
|
|
1858
2009
|
for (const [field, fieldParser] of fieldParserPairs) {
|
|
2010
|
+
if (firstPreCompletedFailure(preCompleted) != null) break;
|
|
1859
2011
|
const cached = parentResults?.get(field);
|
|
1860
2012
|
if (cached !== void 0) {
|
|
1861
2013
|
preCompleted.set(field, cached);
|
|
1862
|
-
registerCompletedDependency(cached, registry);
|
|
2014
|
+
registerCompletedDependency(cached, registry, exec);
|
|
1863
2015
|
continue;
|
|
1864
2016
|
}
|
|
2017
|
+
if (fieldParser.dependencyMetadata?.source?.completeSource != null) continue;
|
|
1865
2018
|
const fieldState = state[field];
|
|
1866
2019
|
const annotatedFieldState = getAnnotatedFieldState(state, field, fieldParser);
|
|
1867
2020
|
if (fieldParser.dependencyMetadata?.source?.getMissingSourceValue != null && isUnmatchedDependencyState(fieldState, fieldParser)) {
|
|
1868
2021
|
const completed = await fieldParser.complete(annotatedFieldState, withChildExecPath(exec, field));
|
|
1869
2022
|
preCompleted.set(field, completed);
|
|
1870
2023
|
const depState = wrapAsDependencySourceState(completed, fieldParser);
|
|
1871
|
-
if (depState) registerCompletedDependency(depState, registry);
|
|
2024
|
+
if (depState) registerCompletedDependency(depState, registry, exec);
|
|
1872
2025
|
continue;
|
|
1873
2026
|
}
|
|
1874
2027
|
if (fieldParser.dependencyMetadata?.source != null && isUnmatchedDependencyState(fieldState, fieldParser) && (annotatedFieldState !== fieldState || isNonCliBoundSourceState(fieldState, fieldParser))) {
|
|
1875
2028
|
const completed = await fieldParser.complete(annotatedFieldState, withChildExecPath(exec, field));
|
|
1876
2029
|
preCompleted.set(field, completed);
|
|
1877
2030
|
const depState = wrapAsDependencySourceState(completed, fieldParser);
|
|
1878
|
-
if (depState) registerCompletedDependency(depState, registry);
|
|
2031
|
+
if (depState) registerCompletedDependency(depState, registry, exec);
|
|
1879
2032
|
continue;
|
|
1880
2033
|
}
|
|
1881
2034
|
if (Array.isArray(fieldState) && fieldState.length === 1 && isPendingDependencySourceState(fieldState[0])) {
|
|
1882
2035
|
const completed = await fieldParser.complete(fieldState, withChildExecPath(exec, field));
|
|
1883
2036
|
preCompleted.set(field, completed);
|
|
1884
|
-
if (isDependencySourceState(completed)) registerCompletedDependency(completed, registry);
|
|
2037
|
+
if (isDependencySourceState(completed)) registerCompletedDependency(completed, registry, exec);
|
|
1885
2038
|
} else if (fieldState === void 0 && isPendingDependencySourceState(fieldParser.initialState)) {
|
|
1886
2039
|
const completed = await fieldParser.complete([fieldParser.initialState], withChildExecPath(exec, field));
|
|
1887
2040
|
preCompleted.set(field, completed);
|
|
1888
|
-
if (isDependencySourceState(completed)) registerCompletedDependency(completed, registry);
|
|
2041
|
+
if (isDependencySourceState(completed)) registerCompletedDependency(completed, registry, exec);
|
|
1889
2042
|
} else if (fieldState === void 0 && isWrappedDependencySource(fieldParser)) {
|
|
1890
2043
|
const pendingState = fieldParser[wrappedDependencySourceMarker];
|
|
1891
2044
|
const completed = await fieldParser.complete([pendingState], withChildExecPath(exec, field));
|
|
1892
2045
|
preCompleted.set(field, completed);
|
|
1893
|
-
if (isDependencySourceState(completed)) registerCompletedDependency(completed, registry);
|
|
2046
|
+
if (isDependencySourceState(completed)) registerCompletedDependency(completed, registry, exec);
|
|
1894
2047
|
} else if (fieldState != null && !Array.isArray(fieldState) && !isDependencySourceState(fieldState) && (isWrappedDependencySource(fieldParser) || isPendingDependencySourceState(fieldParser.initialState))) {
|
|
1895
2048
|
const annotatedFieldState$1 = getAnnotatedFieldState(state, field, fieldParser);
|
|
1896
2049
|
const completed = await fieldParser.complete(annotatedFieldState$1, withChildExecPath(exec, field));
|
|
1897
2050
|
preCompleted.set(field, completed);
|
|
1898
2051
|
const depState = wrapAsDependencySourceState(completed, fieldParser);
|
|
1899
|
-
if (depState) registerCompletedDependency(depState, registry);
|
|
2052
|
+
if (depState) registerCompletedDependency(depState, registry, exec);
|
|
1900
2053
|
}
|
|
1901
2054
|
}
|
|
1902
2055
|
return preCompleted;
|
|
@@ -2307,7 +2460,11 @@ function object(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
2307
2460
|
const fieldParser = parsers[field];
|
|
2308
2461
|
annotatedState[fieldKey] = getFieldState(field, fieldParser);
|
|
2309
2462
|
}
|
|
2310
|
-
|
|
2463
|
+
const allRuntimeNodes = buildRuntimeNodesFromPairs(asyncParserPairs, annotatedState, exec?.path);
|
|
2464
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
2465
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
2466
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), annotatedState, runtime, childExec, preCompleted);
|
|
2467
|
+
if (effectfulFailure != null) return effectfulFailure;
|
|
2311
2468
|
const resolvedFieldStates = await resolveStateWithRuntimeAsync(annotatedState, runtime);
|
|
2312
2469
|
const result = {};
|
|
2313
2470
|
const deferredKeys = /* @__PURE__ */ new Map();
|
|
@@ -2429,7 +2586,11 @@ function object(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
2429
2586
|
const fieldParser = parsers[field];
|
|
2430
2587
|
annotatedState[fieldKey] = getFieldState(field, fieldParser);
|
|
2431
2588
|
}
|
|
2432
|
-
|
|
2589
|
+
const allRuntimeNodes = buildRuntimeNodesFromPairs(asyncParserPairs, annotatedState, exec?.path);
|
|
2590
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
2591
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
2592
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), annotatedState, runtime, childExec, preCompleted);
|
|
2593
|
+
if (effectfulFailure != null) return null;
|
|
2433
2594
|
const resolvedFieldStates = await resolveStateWithRuntimeAsync(annotatedState, runtime);
|
|
2434
2595
|
const result = {};
|
|
2435
2596
|
const deferredKeys = /* @__PURE__ */ new Map();
|
|
@@ -2848,7 +3009,11 @@ function createSeqComplete(parsers, combinedMode) {
|
|
|
2848
3009
|
const pairs = buildIndexedParserPairs(parsers);
|
|
2849
3010
|
const stateRecord = createAnnotatedArrayStateRecord(stateArray);
|
|
2850
3011
|
const preCompleted = await preCompleteAndRegisterDependenciesAsync(stateRecord, pairs, runtime.registry, childExec);
|
|
2851
|
-
|
|
3012
|
+
const allRuntimeNodes = buildRuntimeNodesFromArray(parsers, stateArray, exec?.path);
|
|
3013
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
3014
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
3015
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), stateArray, runtime, childExec, preCompleted);
|
|
3016
|
+
if (effectfulFailure != null) return effectfulFailure;
|
|
2852
3017
|
const phase3Exec = {
|
|
2853
3018
|
...childExec,
|
|
2854
3019
|
preCompletedByParser: void 0
|
|
@@ -3339,7 +3504,11 @@ function tuple(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
3339
3504
|
const tuplePairs = buildIndexedParserPairs(parsers);
|
|
3340
3505
|
const tupleState = createAnnotatedArrayStateRecord(stateArray);
|
|
3341
3506
|
const preCompleted = await preCompleteAndRegisterDependenciesAsync(tupleState, tuplePairs, runtime.registry, childExec);
|
|
3342
|
-
|
|
3507
|
+
const allRuntimeNodes = buildRuntimeNodesFromArray(parsers, stateArray, exec?.path);
|
|
3508
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
3509
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
3510
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), stateArray, runtime, childExec, preCompleted);
|
|
3511
|
+
if (effectfulFailure != null) return effectfulFailure;
|
|
3343
3512
|
const phase3Exec = {
|
|
3344
3513
|
...childExec,
|
|
3345
3514
|
preCompletedByParser: void 0
|
|
@@ -3423,7 +3592,11 @@ function tuple(labelOrParsers, maybeParsersOrOptions, maybeOptions) {
|
|
|
3423
3592
|
const tuplePairs = buildIndexedParserPairs(parsers);
|
|
3424
3593
|
const tupleState = createAnnotatedArrayStateRecord(stateArray);
|
|
3425
3594
|
const preCompleted = await preCompleteAndRegisterDependenciesAsync(tupleState, tuplePairs, runtime.registry, childExec);
|
|
3426
|
-
|
|
3595
|
+
const allRuntimeNodes = buildRuntimeNodesFromArray(parsers, stateArray, exec?.path);
|
|
3596
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
3597
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
3598
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), stateArray, runtime, childExec, preCompleted);
|
|
3599
|
+
if (effectfulFailure != null) return null;
|
|
3427
3600
|
const phase3Exec = {
|
|
3428
3601
|
...childExec,
|
|
3429
3602
|
preCompletedByParser: void 0
|
|
@@ -3685,7 +3858,11 @@ function seq(...rawArgs) {
|
|
|
3685
3858
|
const pairs = buildIndexedParserPairs(parsers);
|
|
3686
3859
|
const stateRecord = createAnnotatedArrayStateRecord(stateArray);
|
|
3687
3860
|
const preCompleted = await preCompleteAndRegisterDependenciesAsync(stateRecord, pairs, runtime.registry, childExec);
|
|
3688
|
-
|
|
3861
|
+
const allRuntimeNodes = buildRuntimeNodesFromArray(parsers, stateArray, exec?.path);
|
|
3862
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
3863
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
3864
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), stateArray, runtime, childExec, preCompleted);
|
|
3865
|
+
if (effectfulFailure != null) return null;
|
|
3689
3866
|
const phase3Exec = {
|
|
3690
3867
|
...childExec,
|
|
3691
3868
|
preCompletedByParser: void 0
|
|
@@ -3868,6 +4045,43 @@ function merge(...args) {
|
|
|
3868
4045
|
const noMatchContext = analyzeNoMatchContext(rawParsers);
|
|
3869
4046
|
const mergedFieldParsers = collectChildFieldParsers(parsers);
|
|
3870
4047
|
const duplicateOutputFieldNames = collectDuplicateFieldNames(mergedFieldParsers);
|
|
4048
|
+
const sortedIndexByOriginal = [];
|
|
4049
|
+
sorted.forEach(([, originalIndex], sortedIndex) => {
|
|
4050
|
+
sortedIndexByOriginal[originalIndex] = sortedIndex;
|
|
4051
|
+
});
|
|
4052
|
+
const buildMergeSchedulingNodes = (state, parentPath) => {
|
|
4053
|
+
const extractChildSchedulingState = (parser, sortedIndex) => {
|
|
4054
|
+
if (parser.initialState === void 0) {
|
|
4055
|
+
const key = parserStateKey(sortedIndex);
|
|
4056
|
+
return key in state ? state[key] : void 0;
|
|
4057
|
+
}
|
|
4058
|
+
if (parser.initialState && typeof parser.initialState === "object") {
|
|
4059
|
+
const key = localObjectStateKey(sortedIndex);
|
|
4060
|
+
if (shouldPreserveLocalChildState(parser) && key in state) return state[key];
|
|
4061
|
+
}
|
|
4062
|
+
return state;
|
|
4063
|
+
};
|
|
4064
|
+
const nodes = [];
|
|
4065
|
+
rawParsers.forEach((parser, originalIndex) => {
|
|
4066
|
+
if (!(fieldParsersKey in parser)) {
|
|
4067
|
+
if (effectfulSchedulingNodesKey in parser) {
|
|
4068
|
+
const sortedIndex = sortedIndexByOriginal[originalIndex];
|
|
4069
|
+
nodes.push({
|
|
4070
|
+
path: [...parentPath ?? [], sortedIndex],
|
|
4071
|
+
parser,
|
|
4072
|
+
state: extractChildSchedulingState(parser, sortedIndex)
|
|
4073
|
+
});
|
|
4074
|
+
}
|
|
4075
|
+
return;
|
|
4076
|
+
}
|
|
4077
|
+
const pairs = parser[fieldParsersKey];
|
|
4078
|
+
const unambiguousPairs = pairs.filter(([field]) => !duplicateOutputFieldNames.has(field));
|
|
4079
|
+
const annotatedState = {};
|
|
4080
|
+
for (const [field, fieldParser] of unambiguousPairs) annotatedState[field] = getAnnotatedFieldState(state, field, fieldParser);
|
|
4081
|
+
nodes.push(...buildRuntimeNodesFromPairs(unambiguousPairs, annotatedState, [...parentPath ?? [], sortedIndexByOriginal[originalIndex]]));
|
|
4082
|
+
});
|
|
4083
|
+
return nodes;
|
|
4084
|
+
};
|
|
3871
4085
|
const parserStateKey = (index) => `__parser_${index}`;
|
|
3872
4086
|
const localObjectStateKey = (index) => `__merge_local_${index}`;
|
|
3873
4087
|
const shouldPreserveLocalChildState = (parser) => parser.initialState != null && typeof parser.initialState === "object" && Object.keys(parser.initialState).some((field) => duplicateOutputFieldNames.has(field));
|
|
@@ -4271,6 +4485,7 @@ function merge(...args) {
|
|
|
4271
4485
|
$valueType: [],
|
|
4272
4486
|
$stateType: [],
|
|
4273
4487
|
[fieldParsersKey]: mergedFieldParsers,
|
|
4488
|
+
[effectfulSchedulingNodesKey]: ((state, parentPath) => state != null && typeof state === "object" ? buildMergeSchedulingNodes(state, parentPath) : []),
|
|
4274
4489
|
priority: Math.max(...mergeParseLanes.map((lane) => lane.priority)),
|
|
4275
4490
|
usage: applyHiddenToUsage(parsers.flatMap((p) => p.usage), options.hidden),
|
|
4276
4491
|
leadingNames: sharedBufferLeadingNames(mergeParseLanes),
|
|
@@ -4379,25 +4594,50 @@ function merge(...args) {
|
|
|
4379
4594
|
dependencyRuntime: runtime
|
|
4380
4595
|
};
|
|
4381
4596
|
const duplicateFieldNames = collectDuplicateFieldNames(mergedFieldParsers);
|
|
4382
|
-
const
|
|
4383
|
-
|
|
4384
|
-
|
|
4385
|
-
const
|
|
4597
|
+
const perChildPhase1 = new Array(parsers.length);
|
|
4598
|
+
for (let originalIndex = 0; originalIndex < rawParsers.length; originalIndex++) {
|
|
4599
|
+
const parser = rawParsers[originalIndex];
|
|
4600
|
+
const sortedIndex = sortedIndexByOriginal[originalIndex];
|
|
4386
4601
|
if (fieldParsersKey in parser) {
|
|
4387
4602
|
const pairs = parser[fieldParsersKey];
|
|
4388
4603
|
const excludedSourceFields = new Set(pairs.map(([field]) => field).filter((field) => duplicateFieldNames.has(field)));
|
|
4389
4604
|
const phase1Pairs = filterExcludedFieldParsers(pairs, excludedSourceFields);
|
|
4390
|
-
const preCompleted = await preCompleteAndRegisterDependenciesAsync(state, phase1Pairs, runtime.registry, withChildExecPath(childExec,
|
|
4391
|
-
|
|
4605
|
+
const preCompleted = await preCompleteAndRegisterDependenciesAsync(state, phase1Pairs, runtime.registry, withChildExecPath(childExec, sortedIndex));
|
|
4606
|
+
const failure = firstPreCompletedFailure(preCompleted);
|
|
4607
|
+
if (failure != null) return {
|
|
4608
|
+
success: false,
|
|
4609
|
+
error: failure
|
|
4610
|
+
};
|
|
4611
|
+
perChildPhase1[sortedIndex] = {
|
|
4392
4612
|
cache: filterDuplicateKeys(preCompleted, phase1Pairs),
|
|
4393
4613
|
excludedSourceFields: excludedSourceFields.size > 0 ? excludedSourceFields : void 0
|
|
4394
|
-
}
|
|
4395
|
-
} else perChildPhase1
|
|
4614
|
+
};
|
|
4615
|
+
} else perChildPhase1[sortedIndex] = {
|
|
4396
4616
|
cache: void 0,
|
|
4397
4617
|
excludedSourceFields: void 0
|
|
4398
|
-
}
|
|
4618
|
+
};
|
|
4619
|
+
}
|
|
4620
|
+
const mergeNodes = buildMergeSchedulingNodes(state, exec?.path);
|
|
4621
|
+
await collectExplicitSourceValuesAsync(mergeNodes, runtime);
|
|
4622
|
+
const effectfulPreCompleted = /* @__PURE__ */ new Map();
|
|
4623
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(mergeNodes, state, runtime, childExec, effectfulPreCompleted);
|
|
4624
|
+
if (effectfulFailure != null) return effectfulFailure;
|
|
4625
|
+
if (effectfulPreCompleted.size > 0) for (let i = 0; i < parsers.length; i++) {
|
|
4626
|
+
const parser = parsers[i];
|
|
4627
|
+
if (!(fieldParsersKey in parser)) continue;
|
|
4628
|
+
const pairs = parser[fieldParsersKey];
|
|
4629
|
+
let cache;
|
|
4630
|
+
for (const [field] of pairs) {
|
|
4631
|
+
const completed = effectfulPreCompleted.get(field);
|
|
4632
|
+
if (completed === void 0) continue;
|
|
4633
|
+
cache ??= new Map(perChildPhase1[i].cache);
|
|
4634
|
+
cache.set(field, completed);
|
|
4635
|
+
}
|
|
4636
|
+
if (cache != null) perChildPhase1[i] = {
|
|
4637
|
+
...perChildPhase1[i],
|
|
4638
|
+
cache
|
|
4639
|
+
};
|
|
4399
4640
|
}
|
|
4400
|
-
await collectExplicitSourceValuesAsync(buildRuntimeNodesFromPairs(unambiguousFieldParsers, state, exec?.path), runtime);
|
|
4401
4641
|
const resolvedState = await resolveStateWithRuntimeAsync(state, runtime);
|
|
4402
4642
|
const object$1 = {};
|
|
4403
4643
|
const deferredKeys = /* @__PURE__ */ new Map();
|
|
@@ -4525,25 +4765,46 @@ function merge(...args) {
|
|
|
4525
4765
|
const runtime = exec?.dependencyRuntime ?? createDependencyRuntimeContext(exec?.dependencyRegistry);
|
|
4526
4766
|
const childExec = withDependencyRuntimeExec(mergeParser.usage, exec, runtime);
|
|
4527
4767
|
const duplicateFieldNames = collectDuplicateFieldNames(mergedFieldParsers);
|
|
4528
|
-
const
|
|
4529
|
-
|
|
4530
|
-
|
|
4531
|
-
const
|
|
4768
|
+
const perChildPhase1 = new Array(parsers.length);
|
|
4769
|
+
for (let originalIndex = 0; originalIndex < rawParsers.length; originalIndex++) {
|
|
4770
|
+
const parser = rawParsers[originalIndex];
|
|
4771
|
+
const sortedIndex = sortedIndexByOriginal[originalIndex];
|
|
4532
4772
|
if (fieldParsersKey in parser) {
|
|
4533
4773
|
const pairs = parser[fieldParsersKey];
|
|
4534
4774
|
const excludedSourceFields = new Set(pairs.map(([field]) => field).filter((field) => duplicateFieldNames.has(field)));
|
|
4535
4775
|
const phase1Pairs = filterExcludedFieldParsers(pairs, excludedSourceFields);
|
|
4536
|
-
const preCompleted = await preCompleteAndRegisterDependenciesAsync(state, phase1Pairs, runtime.registry, withChildExecPath(childExec,
|
|
4537
|
-
|
|
4776
|
+
const preCompleted = await preCompleteAndRegisterDependenciesAsync(state, phase1Pairs, runtime.registry, withChildExecPath(childExec, sortedIndex));
|
|
4777
|
+
if (firstPreCompletedFailure(preCompleted) != null) return null;
|
|
4778
|
+
perChildPhase1[sortedIndex] = {
|
|
4538
4779
|
cache: filterDuplicateKeys(preCompleted, phase1Pairs),
|
|
4539
4780
|
excludedSourceFields: excludedSourceFields.size > 0 ? excludedSourceFields : void 0
|
|
4540
|
-
}
|
|
4541
|
-
} else perChildPhase1
|
|
4781
|
+
};
|
|
4782
|
+
} else perChildPhase1[sortedIndex] = {
|
|
4542
4783
|
cache: void 0,
|
|
4543
4784
|
excludedSourceFields: void 0
|
|
4544
|
-
}
|
|
4785
|
+
};
|
|
4786
|
+
}
|
|
4787
|
+
const mergeNodes = buildMergeSchedulingNodes(state, exec?.path);
|
|
4788
|
+
await collectExplicitSourceValuesAsync(mergeNodes, runtime);
|
|
4789
|
+
const effectfulPreCompleted = /* @__PURE__ */ new Map();
|
|
4790
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(mergeNodes, state, runtime, childExec, effectfulPreCompleted);
|
|
4791
|
+
if (effectfulFailure != null) return null;
|
|
4792
|
+
if (effectfulPreCompleted.size > 0) for (let i = 0; i < parsers.length; i++) {
|
|
4793
|
+
const parser = parsers[i];
|
|
4794
|
+
if (!(fieldParsersKey in parser)) continue;
|
|
4795
|
+
const pairs = parser[fieldParsersKey];
|
|
4796
|
+
let cache;
|
|
4797
|
+
for (const [field] of pairs) {
|
|
4798
|
+
const completed = effectfulPreCompleted.get(field);
|
|
4799
|
+
if (completed === void 0) continue;
|
|
4800
|
+
cache ??= new Map(perChildPhase1[i].cache);
|
|
4801
|
+
cache.set(field, completed);
|
|
4802
|
+
}
|
|
4803
|
+
if (cache != null) perChildPhase1[i] = {
|
|
4804
|
+
...perChildPhase1[i],
|
|
4805
|
+
cache
|
|
4806
|
+
};
|
|
4545
4807
|
}
|
|
4546
|
-
await collectExplicitSourceValuesAsync(buildRuntimeNodesFromPairs(unambiguousFieldParsers, state, exec?.path), runtime);
|
|
4547
4808
|
const resolvedState = await resolveStateWithRuntimeAsync(state, runtime);
|
|
4548
4809
|
const object$1 = {};
|
|
4549
4810
|
const deferredKeys = /* @__PURE__ */ new Map();
|
|
@@ -5179,7 +5440,11 @@ function concat(...parsers) {
|
|
|
5179
5440
|
const concatPairs = buildIndexedParserPairs(parsers);
|
|
5180
5441
|
const concatState = createAnnotatedArrayStateRecord(stateArray);
|
|
5181
5442
|
const preCompleted = await preCompleteAndRegisterDependenciesAsync(concatState, concatPairs, runtime.registry, childExec);
|
|
5182
|
-
|
|
5443
|
+
const allRuntimeNodes = buildRuntimeNodesFromArray(parsers, stateArray, exec?.path);
|
|
5444
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
5445
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
5446
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), stateArray, runtime, childExec, preCompleted);
|
|
5447
|
+
if (effectfulFailure != null) return effectfulFailure;
|
|
5183
5448
|
const phase3Exec = {
|
|
5184
5449
|
...childExec,
|
|
5185
5450
|
preCompletedByParser: void 0
|
|
@@ -5227,6 +5492,7 @@ function concat(...parsers) {
|
|
|
5227
5492
|
usage: parsers.flatMap((p) => p.usage),
|
|
5228
5493
|
leadingNames: sharedBufferLeadingNames(parsers),
|
|
5229
5494
|
acceptingAnyToken: parsers.some((p) => p.acceptingAnyToken),
|
|
5495
|
+
[fieldParsersKey]: parsers.map((parser, index) => [String(index), parser]),
|
|
5230
5496
|
initialState,
|
|
5231
5497
|
canSkip(state, exec) {
|
|
5232
5498
|
const stateArray = state;
|
|
@@ -5282,7 +5548,11 @@ function concat(...parsers) {
|
|
|
5282
5548
|
const concatPairs = buildIndexedParserPairs(parsers);
|
|
5283
5549
|
const concatState = createAnnotatedArrayStateRecord(stateArray);
|
|
5284
5550
|
const preCompleted = await preCompleteAndRegisterDependenciesAsync(concatState, concatPairs, runtime.registry, childExec);
|
|
5285
|
-
|
|
5551
|
+
const allRuntimeNodes = buildRuntimeNodesFromArray(parsers, stateArray, exec?.path);
|
|
5552
|
+
const runtimeNodes = filterPreCompletedRuntimeNodes(allRuntimeNodes, new Set(preCompleted.keys()));
|
|
5553
|
+
await collectExplicitSourceValuesAsync(runtimeNodes, runtime);
|
|
5554
|
+
const effectfulFailure = await scheduleEffectfulSourceCompletions(filterPreCompletedRuntimeNodes(allRuntimeNodes, settledPreCompletedKeys(preCompleted)), stateArray, runtime, childExec, preCompleted);
|
|
5555
|
+
if (effectfulFailure != null) return null;
|
|
5286
5556
|
const phase3Exec = {
|
|
5287
5557
|
...childExec,
|
|
5288
5558
|
preCompletedByParser: void 0
|
|
@@ -5379,6 +5649,7 @@ function group(label, parser, options = {}) {
|
|
|
5379
5649
|
acceptingAnyToken: parser.acceptingAnyToken,
|
|
5380
5650
|
initialState: parser.initialState,
|
|
5381
5651
|
...fieldParsersKey in parser ? { [fieldParsersKey]: parser[fieldParsersKey] } : {},
|
|
5652
|
+
...effectfulSchedulingNodesKey in parser ? { [effectfulSchedulingNodesKey]: parser[effectfulSchedulingNodesKey] } : {},
|
|
5382
5653
|
...typeof parser.shouldDeferCompletion === "function" ? { shouldDeferCompletion: parser.shouldDeferCompletion.bind(parser) } : {},
|
|
5383
5654
|
...typeof parser.canSkip === "function" ? { canSkip: parser.canSkip.bind(parser) } : {},
|
|
5384
5655
|
getSuggestRuntimeNodes(state, path) {
|
|
@@ -5440,6 +5711,11 @@ function group(label, parser, options = {}) {
|
|
|
5440
5711
|
configurable: true,
|
|
5441
5712
|
enumerable: false
|
|
5442
5713
|
});
|
|
5714
|
+
if (parser.dependencyMetadata != null) Object.defineProperty(groupParser, "dependencyMetadata", {
|
|
5715
|
+
value: parser.dependencyMetadata,
|
|
5716
|
+
configurable: true,
|
|
5717
|
+
enumerable: false
|
|
5718
|
+
});
|
|
5443
5719
|
if ("placeholder" in parser) Object.defineProperty(groupParser, "placeholder", {
|
|
5444
5720
|
get() {
|
|
5445
5721
|
return parser.placeholder;
|
|
@@ -6059,6 +6335,25 @@ function conditional(discriminator, branches, defaultBranch, options) {
|
|
|
6059
6335
|
} : {}
|
|
6060
6336
|
};
|
|
6061
6337
|
};
|
|
6338
|
+
const buildConditionalSchedulingNodes = (state, parentPath) => {
|
|
6339
|
+
if (state == null || typeof state !== "object") return [];
|
|
6340
|
+
const conditionalState = state;
|
|
6341
|
+
const nodes = [{
|
|
6342
|
+
path: [...parentPath ?? [], "_discriminator"],
|
|
6343
|
+
parser: discriminator,
|
|
6344
|
+
state: getWrappedChildState(conditionalState, conditionalState.discriminatorState, discriminator)
|
|
6345
|
+
}];
|
|
6346
|
+
const selected = conditionalState.selectedBranch;
|
|
6347
|
+
if (selected !== void 0 && conditionalState.speculative !== true) {
|
|
6348
|
+
const branchParser = selected.kind === "default" ? defaultBranch : branches[selected.key];
|
|
6349
|
+
if (branchParser != null) nodes.push({
|
|
6350
|
+
path: [...parentPath ?? [], "_branch"],
|
|
6351
|
+
parser: branchParser,
|
|
6352
|
+
state: getWrappedChildState(conditionalState, conditionalState.branchState, branchParser)
|
|
6353
|
+
});
|
|
6354
|
+
}
|
|
6355
|
+
return nodes;
|
|
6356
|
+
};
|
|
6062
6357
|
const completeAsync = async (state, exec) => {
|
|
6063
6358
|
let wasSpeculative = false;
|
|
6064
6359
|
if (state.speculative && state.selectedBranch?.kind === "branch") if (exec?.phase !== "parse" && exec?.phase !== "suggest") {
|
|
@@ -6156,6 +6451,12 @@ function conditional(discriminator, branches, defaultBranch, options) {
|
|
|
6156
6451
|
dependencyRuntime: runtime,
|
|
6157
6452
|
dependencyRegistry: runtime.registry
|
|
6158
6453
|
};
|
|
6454
|
+
{
|
|
6455
|
+
const allSchedulingNodes = buildConditionalSchedulingNodes(state, exec?.path);
|
|
6456
|
+
const schedulingNodes = wasSpeculative ? allSchedulingNodes.filter((node) => node.path.at(-1) === "_discriminator") : allSchedulingNodes;
|
|
6457
|
+
const schedulingFailure = await scheduleEffectfulSourceCompletions(schedulingNodes, combinedState, runtime, completionExec, /* @__PURE__ */ new Map());
|
|
6458
|
+
if (schedulingFailure != null) return schedulingFailure;
|
|
6459
|
+
}
|
|
6159
6460
|
const needsDiscriminatorCompletion = state.selectedBranch.kind !== "default" && !(state.discriminatorValue != null && state.discriminatorValue === state.selectedBranch.key);
|
|
6160
6461
|
let discriminatorCompletionExec = completionExec;
|
|
6161
6462
|
if (wasSpeculative && needsDiscriminatorCompletion) {
|
|
@@ -6426,6 +6727,11 @@ function conditional(discriminator, branches, defaultBranch, options) {
|
|
|
6426
6727
|
}
|
|
6427
6728
|
};
|
|
6428
6729
|
defineInheritedAnnotationParser(conditionalParser);
|
|
6730
|
+
Object.defineProperty(conditionalParser, effectfulSchedulingNodesKey, {
|
|
6731
|
+
value: buildConditionalSchedulingNodes,
|
|
6732
|
+
configurable: true,
|
|
6733
|
+
enumerable: false
|
|
6734
|
+
});
|
|
6429
6735
|
return fluent(conditionalParser);
|
|
6430
6736
|
}
|
|
6431
6737
|
|
|
@@ -74,6 +74,16 @@ function unwrapArrayThenExtract(innerExtract) {
|
|
|
74
74
|
};
|
|
75
75
|
}
|
|
76
76
|
/**
|
|
77
|
+
* Wraps an inner `completeSource` to unwrap `[innerState]` first, mirroring
|
|
78
|
+
* `unwrapArrayThenExtract` for the effectful completion operation.
|
|
79
|
+
*/
|
|
80
|
+
function unwrapArrayThenComplete(innerComplete) {
|
|
81
|
+
return (state, exec) => {
|
|
82
|
+
if (Array.isArray(state) && state.length === 1) return innerComplete(state[0], exec);
|
|
83
|
+
return innerComplete(state, exec);
|
|
84
|
+
};
|
|
85
|
+
}
|
|
86
|
+
/**
|
|
77
87
|
* Composes dependency metadata through a modifier wrapper.
|
|
78
88
|
*
|
|
79
89
|
* - `"optional"`: composes `extractSourceValue` with array unwrapping.
|
|
@@ -99,7 +109,8 @@ function composeDependencyMetadata(inner, wrapperKind, options) {
|
|
|
99
109
|
...inner,
|
|
100
110
|
source: {
|
|
101
111
|
...inner.source,
|
|
102
|
-
extractSourceValue: unwrapArrayThenExtract(inner.source.extractSourceValue)
|
|
112
|
+
extractSourceValue: unwrapArrayThenExtract(inner.source.extractSourceValue),
|
|
113
|
+
...inner.source.completeSource != null && { completeSource: unwrapArrayThenComplete(inner.source.completeSource) }
|
|
103
114
|
}
|
|
104
115
|
};
|
|
105
116
|
return inner;
|
|
@@ -112,6 +123,7 @@ function composeDependencyMetadata(inner, wrapperKind, options) {
|
|
|
112
123
|
source: {
|
|
113
124
|
...inner.source,
|
|
114
125
|
...wrappedExtract != null && { extractSourceValue: wrappedExtract },
|
|
126
|
+
...inner.source.completeSource != null && { completeSource: unwrapArrayThenComplete(inner.source.completeSource) },
|
|
115
127
|
...preservesSourceValue && options?.defaultValue != null && { getMissingSourceValue: options.defaultValue }
|
|
116
128
|
}
|
|
117
129
|
};
|