@optique/core 1.1.8 → 1.1.10

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.
@@ -16,6 +16,17 @@ function getDisplayWidth(text) {
16
16
  for (const { segment } of segmenter.segment(stripped)) width += graphemeWidth(segment);
17
17
  return width;
18
18
  }
19
+ /**
20
+ * Removes ANSI escape sequences (CSI and OSC) from a string, leaving only
21
+ * the text a terminal would print.
22
+ *
23
+ * @param text The string to strip.
24
+ * @returns The string without ANSI escape sequences.
25
+ * @internal
26
+ */
27
+ function stripAnsi(text) {
28
+ return text.replace(ansiRegex, "");
29
+ }
19
30
  const zeroWidthRegex = /^[\p{Cf}\p{Mn}\p{Me}]+$/u;
20
31
  const emojiPresentationRegex = /\p{Emoji_Presentation}/u;
21
32
  const emojiWithVS16Regex = /\p{Emoji}\uFE0F/u;
@@ -41,4 +52,5 @@ function isEastAsianWide(cp) {
41
52
  }
42
53
 
43
54
  //#endregion
44
- exports.getDisplayWidth = getDisplayWidth;
55
+ exports.getDisplayWidth = getDisplayWidth;
56
+ exports.stripAnsi = stripAnsi;
@@ -8,5 +8,14 @@
8
8
  * @internal
9
9
  */
10
10
  declare function getDisplayWidth(text: string): number;
11
+ /**
12
+ * Removes ANSI escape sequences (CSI and OSC) from a string, leaving only
13
+ * the text a terminal would print.
14
+ *
15
+ * @param text The string to strip.
16
+ * @returns The string without ANSI escape sequences.
17
+ * @internal
18
+ */
19
+ declare function stripAnsi(text: string): string;
11
20
  //#endregion
12
- export { getDisplayWidth };
21
+ export { getDisplayWidth, stripAnsi };
@@ -8,5 +8,14 @@
8
8
  * @internal
9
9
  */
10
10
  declare function getDisplayWidth(text: string): number;
11
+ /**
12
+ * Removes ANSI escape sequences (CSI and OSC) from a string, leaving only
13
+ * the text a terminal would print.
14
+ *
15
+ * @param text The string to strip.
16
+ * @returns The string without ANSI escape sequences.
17
+ * @internal
18
+ */
19
+ declare function stripAnsi(text: string): string;
11
20
  //#endregion
12
- export { getDisplayWidth };
21
+ export { getDisplayWidth, stripAnsi };
@@ -15,6 +15,17 @@ function getDisplayWidth(text) {
15
15
  for (const { segment } of segmenter.segment(stripped)) width += graphemeWidth(segment);
16
16
  return width;
17
17
  }
18
+ /**
19
+ * Removes ANSI escape sequences (CSI and OSC) from a string, leaving only
20
+ * the text a terminal would print.
21
+ *
22
+ * @param text The string to strip.
23
+ * @returns The string without ANSI escape sequences.
24
+ * @internal
25
+ */
26
+ function stripAnsi(text) {
27
+ return text.replace(ansiRegex, "");
28
+ }
18
29
  const zeroWidthRegex = /^[\p{Cf}\p{Mn}\p{Me}]+$/u;
19
30
  const emojiPresentationRegex = /\p{Emoji_Presentation}/u;
20
31
  const emojiWithVS16Regex = /\p{Emoji}\uFE0F/u;
@@ -40,4 +51,4 @@ function isEastAsianWide(cp) {
40
51
  }
41
52
 
42
53
  //#endregion
43
- export { getDisplayWidth };
54
+ export { getDisplayWidth, stripAnsi };
package/dist/doc.cjs CHANGED
@@ -341,13 +341,15 @@ function formatDocPage(programName, page, options = {}) {
341
341
  const suffix = typeof options.showDefault === "object" ? options.showDefault.suffix ?? "]" : "]";
342
342
  const prefixWidth = require_displaywidth.getDisplayWidth(prefix);
343
343
  const suffixWidth = require_displaywidth.getDisplayWidth(suffix);
344
+ let defaultPrefix = prefix;
344
345
  let defaultStartWidth;
345
346
  if (descColumnWidth != null) {
346
347
  const lastW = lastLineVisibleLength(description);
347
348
  const effectiveLastW = lastW + currentExtraOffset();
348
349
  if (effectiveLastW + prefixWidth >= descColumnWidth) {
349
350
  description += "\n";
350
- defaultStartWidth = prefixWidth;
351
+ defaultPrefix = prefix.trimStart();
352
+ defaultStartWidth = require_displaywidth.getDisplayWidth(defaultPrefix);
351
353
  } else defaultStartWidth = effectiveLastW + prefixWidth;
352
354
  }
353
355
  const defaultFormatOptions = {
@@ -357,7 +359,7 @@ function formatDocPage(programName, page, options = {}) {
357
359
  startWidth: defaultStartWidth
358
360
  };
359
361
  const defaultContent = require_message.formatMessage(entry.default, defaultFormatOptions);
360
- const defaultText = `${prefix}${defaultContent}${suffix}`;
362
+ const defaultText = `${defaultPrefix}${defaultContent}${suffix}`;
361
363
  const formattedDefault = options.colors ? `\x1b[2m${defaultText}\x1b[0m` : defaultText;
362
364
  description += formattedDefault;
363
365
  }
@@ -385,6 +387,7 @@ function formatDocPage(programName, page, options = {}) {
385
387
  const choicesPrefixWidth = require_displaywidth.getDisplayWidth(prefix);
386
388
  const choicesSuffixWidth = require_displaywidth.getDisplayWidth(suffix);
387
389
  const choicesLabelWidth = require_displaywidth.getDisplayWidth(label);
390
+ let choicesHeading = `${prefix}${label}`;
388
391
  let choicesStartWidth;
389
392
  if (descColumnWidth != null) {
390
393
  const lastW = lastLineVisibleLength(description);
@@ -392,7 +395,8 @@ function formatDocPage(programName, page, options = {}) {
392
395
  const prefixLabelLen = choicesPrefixWidth + choicesLabelWidth;
393
396
  if (effectiveLastW + prefixLabelLen >= descColumnWidth) {
394
397
  description += "\n";
395
- choicesStartWidth = prefixLabelLen;
398
+ choicesHeading = choicesHeading.trimStart();
399
+ choicesStartWidth = require_displaywidth.getDisplayWidth(choicesHeading);
396
400
  } else choicesStartWidth = effectiveLastW + prefixLabelLen;
397
401
  }
398
402
  const choicesFormatOptions = {
@@ -402,7 +406,7 @@ function formatDocPage(programName, page, options = {}) {
402
406
  startWidth: choicesStartWidth
403
407
  };
404
408
  const choicesDisplay = require_message.formatMessage(truncatedTerms, choicesFormatOptions);
405
- const choicesText = `${prefix}${label}${choicesDisplay}${suffix}`;
409
+ const choicesText = `${choicesHeading}${choicesDisplay}${suffix}`;
406
410
  const formattedChoices = options.colors ? `\x1b[2m${choicesText}\x1b[0m` : choicesText;
407
411
  description += formattedChoices;
408
412
  }
package/dist/doc.js CHANGED
@@ -341,13 +341,15 @@ function formatDocPage(programName, page, options = {}) {
341
341
  const suffix = typeof options.showDefault === "object" ? options.showDefault.suffix ?? "]" : "]";
342
342
  const prefixWidth = getDisplayWidth(prefix);
343
343
  const suffixWidth = getDisplayWidth(suffix);
344
+ let defaultPrefix = prefix;
344
345
  let defaultStartWidth;
345
346
  if (descColumnWidth != null) {
346
347
  const lastW = lastLineVisibleLength(description);
347
348
  const effectiveLastW = lastW + currentExtraOffset();
348
349
  if (effectiveLastW + prefixWidth >= descColumnWidth) {
349
350
  description += "\n";
350
- defaultStartWidth = prefixWidth;
351
+ defaultPrefix = prefix.trimStart();
352
+ defaultStartWidth = getDisplayWidth(defaultPrefix);
351
353
  } else defaultStartWidth = effectiveLastW + prefixWidth;
352
354
  }
353
355
  const defaultFormatOptions = {
@@ -357,7 +359,7 @@ function formatDocPage(programName, page, options = {}) {
357
359
  startWidth: defaultStartWidth
358
360
  };
359
361
  const defaultContent = formatMessage(entry.default, defaultFormatOptions);
360
- const defaultText = `${prefix}${defaultContent}${suffix}`;
362
+ const defaultText = `${defaultPrefix}${defaultContent}${suffix}`;
361
363
  const formattedDefault = options.colors ? `\x1b[2m${defaultText}\x1b[0m` : defaultText;
362
364
  description += formattedDefault;
363
365
  }
@@ -385,6 +387,7 @@ function formatDocPage(programName, page, options = {}) {
385
387
  const choicesPrefixWidth = getDisplayWidth(prefix);
386
388
  const choicesSuffixWidth = getDisplayWidth(suffix);
387
389
  const choicesLabelWidth = getDisplayWidth(label);
390
+ let choicesHeading = `${prefix}${label}`;
388
391
  let choicesStartWidth;
389
392
  if (descColumnWidth != null) {
390
393
  const lastW = lastLineVisibleLength(description);
@@ -392,7 +395,8 @@ function formatDocPage(programName, page, options = {}) {
392
395
  const prefixLabelLen = choicesPrefixWidth + choicesLabelWidth;
393
396
  if (effectiveLastW + prefixLabelLen >= descColumnWidth) {
394
397
  description += "\n";
395
- choicesStartWidth = prefixLabelLen;
398
+ choicesHeading = choicesHeading.trimStart();
399
+ choicesStartWidth = getDisplayWidth(choicesHeading);
396
400
  } else choicesStartWidth = effectiveLastW + prefixLabelLen;
397
401
  }
398
402
  const choicesFormatOptions = {
@@ -402,7 +406,7 @@ function formatDocPage(programName, page, options = {}) {
402
406
  startWidth: choicesStartWidth
403
407
  };
404
408
  const choicesDisplay = formatMessage(truncatedTerms, choicesFormatOptions);
405
- const choicesText = `${prefix}${label}${choicesDisplay}${suffix}`;
409
+ const choicesText = `${choicesHeading}${choicesDisplay}${suffix}`;
406
410
  const formattedChoices = options.colors ? `\x1b[2m${choicesText}\x1b[0m` : choicesText;
407
411
  description += formattedChoices;
408
412
  }
@@ -2,6 +2,7 @@ const require_internal_annotations = require('./internal/annotations.cjs');
2
2
  const require_mode_dispatch = require('./internal/mode-dispatch.cjs');
3
3
  const require_internal_parser = require('./internal/parser.cjs');
4
4
  const require_annotation_state = require('./annotation-state.cjs');
5
+ const require_passthrough = require('./internal/passthrough.cjs');
5
6
 
6
7
  //#region src/extension.ts
7
8
  const emptyTraits = Object.freeze({});
@@ -71,9 +72,25 @@ function delegateSuggestNodes(innerParser, outerParser, state, path, innerState,
71
72
  function mapSourceMetadata(parser, mapSource) {
72
73
  return require_internal_parser.composeWrappedSourceMetadata(parser.dependencyMetadata, mapSource);
73
74
  }
75
+ /**
76
+ * Delegates CLI option matching and capture priority through a parser wrapper.
77
+ * Use the same child-state projection as the wrapper's parse method. This
78
+ * preserves selected command options without changing public leading names.
79
+ *
80
+ * @param wrapper The parser being constructed.
81
+ * @param inner Its wrapped CLI parser.
82
+ * @param getInnerState Projects the wrapper state to the CLI parser state.
83
+ * @throws {TypeError} If metadata cannot be defined on the wrapper.
84
+ * @since 1.0.11
85
+ */
86
+ function delegateOptionParsing(wrapper, inner, getInnerState) {
87
+ require_passthrough.defineOptionMatch(wrapper, (state, token) => require_passthrough.getOptionMatch(inner, getInnerState(state), token));
88
+ require_passthrough.definePassThroughPriority(wrapper, [inner], (state, token) => require_passthrough.getPassThroughPriority(inner, getInnerState(state), token));
89
+ }
74
90
 
75
91
  //#endregion
76
92
  exports.defineTraits = defineTraits;
93
+ exports.delegateOptionParsing = delegateOptionParsing;
77
94
  exports.delegateSuggestNodes = delegateSuggestNodes;
78
95
  exports.dispatchByMode = require_mode_dispatch.dispatchByMode;
79
96
  exports.getTraits = getTraits;
@@ -93,5 +93,17 @@ declare function delegateSuggestNodes<TInnerState>(innerParser: Parser<Mode, unk
93
93
  * @since 1.0.0
94
94
  */
95
95
  declare function mapSourceMetadata<M extends Mode, TValue, TState>(parser: Pick<Parser<M, TValue, TState>, "dependencyMetadata">, mapSource: (source: ParserSourceMetadata<M, TValue, TState>) => ParserSourceMetadata<M, TValue, TState>): Parser<M, TValue, TState>["dependencyMetadata"] | undefined;
96
+ /**
97
+ * Delegates CLI option matching and capture priority through a parser wrapper.
98
+ * Use the same child-state projection as the wrapper's parse method. This
99
+ * preserves selected command options without changing public leading names.
100
+ *
101
+ * @param wrapper The parser being constructed.
102
+ * @param inner Its wrapped CLI parser.
103
+ * @param getInnerState Projects the wrapper state to the CLI parser state.
104
+ * @throws {TypeError} If metadata cannot be defined on the wrapper.
105
+ * @since 1.0.11
106
+ */
107
+ declare function delegateOptionParsing<TOuterState, TInnerState>(wrapper: Parser<Mode, unknown, TOuterState>, inner: Parser<Mode, unknown, TInnerState>, getInnerState: (state: TOuterState) => TInnerState): void;
96
108
  //#endregion
97
- export { ParserSourceMetadata, ParserTraits, SuggestNode, defineTraits, delegateSuggestNodes, dispatchByMode, getTraits, inheritAnnotations, injectAnnotations, isInjectedAnnotationState, mapModeValue, mapSourceMetadata, unwrapInjectedAnnotationState, withAnnotationView, wrapForMode };
109
+ export { ParserSourceMetadata, ParserTraits, SuggestNode, defineTraits, delegateOptionParsing, delegateSuggestNodes, dispatchByMode, getTraits, inheritAnnotations, injectAnnotations, isInjectedAnnotationState, mapModeValue, mapSourceMetadata, unwrapInjectedAnnotationState, withAnnotationView, wrapForMode };
@@ -93,5 +93,17 @@ declare function delegateSuggestNodes<TInnerState>(innerParser: Parser<Mode, unk
93
93
  * @since 1.0.0
94
94
  */
95
95
  declare function mapSourceMetadata<M extends Mode, TValue, TState>(parser: Pick<Parser<M, TValue, TState>, "dependencyMetadata">, mapSource: (source: ParserSourceMetadata<M, TValue, TState>) => ParserSourceMetadata<M, TValue, TState>): Parser<M, TValue, TState>["dependencyMetadata"] | undefined;
96
+ /**
97
+ * Delegates CLI option matching and capture priority through a parser wrapper.
98
+ * Use the same child-state projection as the wrapper's parse method. This
99
+ * preserves selected command options without changing public leading names.
100
+ *
101
+ * @param wrapper The parser being constructed.
102
+ * @param inner Its wrapped CLI parser.
103
+ * @param getInnerState Projects the wrapper state to the CLI parser state.
104
+ * @throws {TypeError} If metadata cannot be defined on the wrapper.
105
+ * @since 1.0.11
106
+ */
107
+ declare function delegateOptionParsing<TOuterState, TInnerState>(wrapper: Parser<Mode, unknown, TOuterState>, inner: Parser<Mode, unknown, TInnerState>, getInnerState: (state: TOuterState) => TInnerState): void;
96
108
  //#endregion
97
- export { ParserSourceMetadata, ParserTraits, SuggestNode, defineTraits, delegateSuggestNodes, dispatchByMode, getTraits, inheritAnnotations, injectAnnotations, isInjectedAnnotationState, mapModeValue, mapSourceMetadata, unwrapInjectedAnnotationState, withAnnotationView, wrapForMode };
109
+ export { ParserSourceMetadata, ParserTraits, SuggestNode, defineTraits, delegateOptionParsing, delegateSuggestNodes, dispatchByMode, getTraits, inheritAnnotations, injectAnnotations, isInjectedAnnotationState, mapModeValue, mapSourceMetadata, unwrapInjectedAnnotationState, withAnnotationView, wrapForMode };
package/dist/extension.js CHANGED
@@ -2,6 +2,7 @@ import { inheritAnnotations, injectAnnotations, isInjectedAnnotationState, unwra
2
2
  import { dispatchByMode, mapModeValue, wrapForMode } from "./internal/mode-dispatch.js";
3
3
  import { annotationWrapperRequiresSourceBindingKey, composeWrappedSourceMetadata, defineInheritedAnnotationParser, getDelegatingSuggestRuntimeNodes, inheritParentAnnotationsKey, unmatchedNonCliDependencySourceStateMarker } from "./internal/parser.js";
4
4
  import { withAnnotationView } from "./annotation-state.js";
5
+ import { defineOptionMatch, definePassThroughPriority, getOptionMatch, getPassThroughPriority } from "./internal/passthrough.js";
5
6
 
6
7
  //#region src/extension.ts
7
8
  const emptyTraits = Object.freeze({});
@@ -71,6 +72,21 @@ function delegateSuggestNodes(innerParser, outerParser, state, path, innerState,
71
72
  function mapSourceMetadata(parser, mapSource) {
72
73
  return composeWrappedSourceMetadata(parser.dependencyMetadata, mapSource);
73
74
  }
75
+ /**
76
+ * Delegates CLI option matching and capture priority through a parser wrapper.
77
+ * Use the same child-state projection as the wrapper's parse method. This
78
+ * preserves selected command options without changing public leading names.
79
+ *
80
+ * @param wrapper The parser being constructed.
81
+ * @param inner Its wrapped CLI parser.
82
+ * @param getInnerState Projects the wrapper state to the CLI parser state.
83
+ * @throws {TypeError} If metadata cannot be defined on the wrapper.
84
+ * @since 1.0.11
85
+ */
86
+ function delegateOptionParsing(wrapper, inner, getInnerState) {
87
+ defineOptionMatch(wrapper, (state, token) => getOptionMatch(inner, getInnerState(state), token));
88
+ definePassThroughPriority(wrapper, [inner], (state, token) => getPassThroughPriority(inner, getInnerState(state), token));
89
+ }
74
90
 
75
91
  //#endregion
76
- export { defineTraits, delegateSuggestNodes, dispatchByMode, getTraits, inheritAnnotations, injectAnnotations, isInjectedAnnotationState, mapModeValue, mapSourceMetadata, unwrapInjectedAnnotationState, withAnnotationView, wrapForMode };
92
+ export { defineTraits, delegateOptionParsing, delegateSuggestNodes, dispatchByMode, getTraits, inheritAnnotations, injectAnnotations, isInjectedAnnotationState, mapModeValue, mapSourceMetadata, unwrapInjectedAnnotationState, withAnnotationView, wrapForMode };
@@ -0,0 +1,230 @@
1
+
2
+ //#region src/internal/passthrough.ts
3
+ /** Retains the deepest diagnostic and highest matching lane priority. @internal */
4
+ function retainConsumingFailure(current, failure, priority) {
5
+ return {
6
+ failure: current != null && current.failure.consumed >= failure.consumed ? current.failure : failure,
7
+ priority: Math.max(current?.priority ?? -Infinity, priority)
8
+ };
9
+ }
10
+ const passThroughFailure = Symbol("passThroughFailure");
11
+ /**
12
+ * Gets the sibling failure that prevents pass-through capture at this cursor.
13
+ * Stale hints inherited through a successful child do not block later input.
14
+ * @param context The pass-through parser's context.
15
+ * @returns The failure at this cursor, or undefined if capture is allowed.
16
+ * @internal
17
+ */
18
+ function getPassThroughFailure(context, capturePriority$1 = -Infinity) {
19
+ const hinted = context;
20
+ const hint = hinted[passThroughFailure];
21
+ return hint?.buffer === context.buffer && hint.optionsTerminated === context.optionsTerminated && hint.failure.priority >= capturePriority$1 ? hint.failure : void 0;
22
+ }
23
+ /**
24
+ * Carries a sibling's consuming failure into a child parse call. Only
25
+ * passThrough consults the hint; ordinary alternatives may still recover.
26
+ * @param context The child context, without modifying the parent's context.
27
+ * @param failure The deepest matching consuming failure at this input position.
28
+ * @returns A context with a hint for active option-like input, or the original.
29
+ * @internal
30
+ */
31
+ function withPassThroughFailure(context, failure, capturePriority$1 = -Infinity) {
32
+ const token = context.buffer[0];
33
+ const existing = getPassThroughFailure(context);
34
+ if (existing != null && existing.priority < capturePriority$1) {
35
+ const hinted$1 = context;
36
+ const { [passThroughFailure]: _discarded,...rest } = hinted$1;
37
+ context = rest;
38
+ }
39
+ if (failure == null || failure.failure.consumed < 1 || failure.priority < capturePriority$1 || context.optionsTerminated || token == null || token === "--" || !/^[-/+]/.test(token)) return context;
40
+ const retained = getPassThroughFailure(context);
41
+ const combined = retainConsumingFailure(retained, failure.failure, failure.priority);
42
+ const hinted = {
43
+ ...context,
44
+ [passThroughFailure]: {
45
+ buffer: context.buffer,
46
+ optionsTerminated: context.optionsTerminated,
47
+ failure: combined
48
+ }
49
+ };
50
+ return hinted;
51
+ }
52
+ /** Retains a child's rejected option failure only at the parent's cursor. @internal */
53
+ function retainConsumingFailureHint(current, context, next) {
54
+ if (next.buffer !== context.buffer || next.optionsTerminated !== context.optionsTerminated) return current;
55
+ const hint = getPassThroughFailure(next);
56
+ return hint == null ? current : retainConsumingFailure(current, hint.failure, hint.priority);
57
+ }
58
+ const capturePriority = Symbol("capturePriority");
59
+ /** Checks for capture through usage-preserving wrappers. @internal */
60
+ function hasPassThroughUsage(usage) {
61
+ return usage.some((term) => term.type === "passthrough" || (term.type === "optional" || term.type === "multiple") && hasPassThroughUsage(term.terms) || term.type === "exclusive" && term.terms.some(hasPassThroughUsage));
62
+ }
63
+ /**
64
+ * Gets the priority of reachable capture, respecting an explicit override.
65
+ * @param parser The parser whose capture priority is needed.
66
+ * @param state The current parser state.
67
+ * @param token The current token, omitted for an unfiltered priority lookup.
68
+ * @returns The capture priority, or undefined when capture is absent.
69
+ * @internal
70
+ */
71
+ function getPassThroughPriority(parser, state = parser.initialState, token) {
72
+ if (!hasPassThroughUsage(parser.usage)) return void 0;
73
+ const annotated = parser;
74
+ const hint = annotated[capturePriority];
75
+ if (hint == null) return parser.priority;
76
+ const priority = hint.getPriority == null ? hint.priority : hint.getPriority(state, token);
77
+ return priority == null ? void 0 : hint.ownerPriority === parser.priority ? priority : parser.priority;
78
+ }
79
+ /**
80
+ * Records capture priority separately from unrelated children's priorities.
81
+ * @param parser The newly constructed parser.
82
+ * @param children Its transparent children.
83
+ * @param getPriority Optional state-aware capture priority lookup.
84
+ * @internal
85
+ */
86
+ function definePassThroughPriority(parser, children, getPriority) {
87
+ const priorities = children.filter((child) => hasPassThroughUsage(child.usage)).map((child) => getPassThroughPriority(child) ?? child.priority);
88
+ if (priorities.length === 0) return;
89
+ Object.defineProperty(parser, capturePriority, {
90
+ value: {
91
+ ownerPriority: parser.priority,
92
+ priority: Math.max(...priorities),
93
+ getPriority
94
+ },
95
+ enumerable: true
96
+ });
97
+ }
98
+ /**
99
+ * Copies only a cursor-valid hint when rebuilding a child context.
100
+ * @param context The successful child's context.
101
+ * @returns Private hint properties, or an empty object for stale hints.
102
+ * @internal
103
+ */
104
+ function getPassThroughFailureHint(context) {
105
+ const hinted = context;
106
+ const hint = hinted[passThroughFailure];
107
+ return hint != null && getPassThroughFailure(context) != null ? { [passThroughFailure]: hint } : {};
108
+ }
109
+ /** Finds a Boolean option through usage-preserving wrappers. */
110
+ function hasFlagUsage(usage, name) {
111
+ return usage.some((term) => term.type === "option" && term.metavar == null && term.names.some((optionName) => optionName === name) || (term.type === "optional" || term.type === "multiple") && hasFlagUsage(term.terms, name) || term.type === "exclusive" && term.terms.some((terms) => hasFlagUsage(terms, name)));
112
+ }
113
+ /** Matches exact options, attached values, and leading bundled flags. */
114
+ function matchesOptionToken(parser, token) {
115
+ if (token == null || token === "--" || !/^[-/+]/.test(token)) return false;
116
+ if (parser.leadingNames.has(token)) return true;
117
+ const slashOption = token.startsWith("/");
118
+ const separator = slashOption ? token.indexOf(":") : token.startsWith("-") ? token.indexOf("=") : -1;
119
+ if (separator > (slashOption ? 0 : 2) && parser.leadingNames.has(token.slice(0, separator))) return true;
120
+ const shortName = token.slice(0, 2);
121
+ return token.length > 2 && /^-[^-]$/.test(shortName) && parser.leadingNames.has(shortName) && hasFlagUsage(parser.usage, shortName);
122
+ }
123
+ const optionMatchKey = Symbol("optionMatch");
124
+ /**
125
+ * Records state-aware option matching without changing public leading names.
126
+ * @param parser The newly constructed transparent parser.
127
+ * @param match Finds a reachable known-option lane.
128
+ * @internal
129
+ */
130
+ function defineOptionMatch(parser, match) {
131
+ Object.defineProperty(parser, optionMatchKey, {
132
+ value: {
133
+ ownerPriority: parser.priority,
134
+ match
135
+ },
136
+ enumerable: true
137
+ });
138
+ }
139
+ /**
140
+ * Finds a matching option's actual priority, including selected command children.
141
+ * @param parser The parser to inspect.
142
+ * @param state Its current state.
143
+ * @param token The current token.
144
+ * @returns A reachable option match, or undefined.
145
+ * @internal
146
+ */
147
+ function getOptionMatch(parser, state, token) {
148
+ if (token == null || token === "--" || !/^[-/+]/.test(token)) return void 0;
149
+ const annotated = parser;
150
+ const matcher = annotated[optionMatchKey];
151
+ if (matcher != null) {
152
+ const match = matcher.match(state, token);
153
+ return match == null || matcher.ownerPriority === parser.priority ? match : {
154
+ ...match,
155
+ priority: parser.priority
156
+ };
157
+ }
158
+ return matchesOptionToken(parser, token) ? {
159
+ priority: parser.priority,
160
+ continuesCommand: false
161
+ } : void 0;
162
+ }
163
+ /**
164
+ * Combines option matches while retaining active command continuation.
165
+ * @param matches Matches from transparent children.
166
+ * @returns Their highest priority and whether any matching command continues.
167
+ * @internal
168
+ */
169
+ function combineOptionMatches(matches) {
170
+ const found = matches.filter((match) => match != null);
171
+ return found.length === 0 ? void 0 : {
172
+ priority: Math.max(...found.map((match) => match.priority)),
173
+ continuesCommand: found.some((match) => match.continuesCommand)
174
+ };
175
+ }
176
+ const knownCompletionKey = Symbol("knownCompletion");
177
+ /** Marks a completion value that can be inspected without running user code. @internal */
178
+ function defineKnownCompletion(parser, value) {
179
+ defineKnownCompletionLookup(parser, (state) => ({ value: value(state) }));
180
+ }
181
+ /** Registers a known-value lookup that may decline unknown completion. @internal */
182
+ function defineKnownCompletionLookup(parser, value) {
183
+ Object.defineProperty(parser, knownCompletionKey, {
184
+ value: {
185
+ complete: parser.complete,
186
+ value
187
+ },
188
+ enumerable: true
189
+ });
190
+ }
191
+ /** Looks up a known value only while the original completion is intact. @internal */
192
+ function getKnownCompletion(parser, state) {
193
+ const annotated = parser;
194
+ const hint = annotated[knownCompletionKey];
195
+ return hint != null && hint.complete === parser.complete ? hint.value(state) : void 0;
196
+ }
197
+ /** Combines the priorities of currently reachable capture lanes. @internal */
198
+ function combinePassThroughPriorities(priorities) {
199
+ const found = priorities.filter((priority) => priority != null);
200
+ return found.length === 0 ? void 0 : Math.max(...found);
201
+ }
202
+ /** Forwards known completion through a state-preserving wrapper. @internal */
203
+ function delegateKnownCompletion(wrapper, inner) {
204
+ Object.defineProperty(wrapper, knownCompletionKey, {
205
+ value: {
206
+ complete: wrapper.complete,
207
+ value: (state) => getKnownCompletion(inner, state)
208
+ },
209
+ enumerable: true
210
+ });
211
+ }
212
+
213
+ //#endregion
214
+ exports.combineOptionMatches = combineOptionMatches;
215
+ exports.combinePassThroughPriorities = combinePassThroughPriorities;
216
+ exports.defineKnownCompletion = defineKnownCompletion;
217
+ exports.defineKnownCompletionLookup = defineKnownCompletionLookup;
218
+ exports.defineOptionMatch = defineOptionMatch;
219
+ exports.definePassThroughPriority = definePassThroughPriority;
220
+ exports.delegateKnownCompletion = delegateKnownCompletion;
221
+ exports.getKnownCompletion = getKnownCompletion;
222
+ exports.getOptionMatch = getOptionMatch;
223
+ exports.getPassThroughFailure = getPassThroughFailure;
224
+ exports.getPassThroughFailureHint = getPassThroughFailureHint;
225
+ exports.getPassThroughPriority = getPassThroughPriority;
226
+ exports.hasPassThroughUsage = hasPassThroughUsage;
227
+ exports.matchesOptionToken = matchesOptionToken;
228
+ exports.retainConsumingFailure = retainConsumingFailure;
229
+ exports.retainConsumingFailureHint = retainConsumingFailureHint;
230
+ exports.withPassThroughFailure = withPassThroughFailure;