wp-typia 0.24.4 → 0.24.6

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.
Files changed (58) hide show
  1. package/README.md +8 -6
  2. package/bin/wp-typia.js +24 -103
  3. package/{dist-bunli/node-cli.js → dist/cli.js} +5086 -3693
  4. package/package.json +9 -36
  5. package/bin/routing-metadata.generated.d.ts +0 -8
  6. package/bin/routing-metadata.generated.js +0 -93
  7. package/bin/runtime-routing.d.ts +0 -34
  8. package/bin/runtime-routing.js +0 -124
  9. package/dist-bunli/.bunli/commands.gen.js +0 -304441
  10. package/dist-bunli/.bunli/highlights-eq9cgrbb.scm +0 -604
  11. package/dist-bunli/.bunli/highlights-ghv9g403.scm +0 -205
  12. package/dist-bunli/.bunli/highlights-hk7bwhj4.scm +0 -284
  13. package/dist-bunli/.bunli/highlights-r812a2qc.scm +0 -150
  14. package/dist-bunli/.bunli/highlights-x6tmsnaa.scm +0 -115
  15. package/dist-bunli/.bunli/injections-73j83es3.scm +0 -27
  16. package/dist-bunli/.bunli/tree-sitter-javascript-nd0q4pe9.wasm +0 -0
  17. package/dist-bunli/.bunli/tree-sitter-markdown-411r6y9b.wasm +0 -0
  18. package/dist-bunli/.bunli/tree-sitter-markdown_inline-j5349f42.wasm +0 -0
  19. package/dist-bunli/.bunli/tree-sitter-typescript-zxjzwt75.wasm +0 -0
  20. package/dist-bunli/.bunli/tree-sitter-zig-e78zbjpm.wasm +0 -0
  21. package/dist-bunli/agents-91fpdyyt.js +0 -12
  22. package/dist-bunli/chunk-bdqvmfwv-f5qmzmxg.js +0 -16825
  23. package/dist-bunli/cli-03j0axbt.js +0 -163
  24. package/dist-bunli/cli-1170yyve.js +0 -106
  25. package/dist-bunli/cli-368d4cgy.js +0 -1235
  26. package/dist-bunli/cli-377p86mf.js +0 -191
  27. package/dist-bunli/cli-6v0pcxw6.js +0 -314
  28. package/dist-bunli/cli-84c7wff4.js +0 -198
  29. package/dist-bunli/cli-8hxf9qw6.js +0 -198
  30. package/dist-bunli/cli-9fx0qgb7.js +0 -3680
  31. package/dist-bunli/cli-ac2ebaf8.js +0 -3
  32. package/dist-bunli/cli-add-qjd3ba8j.js +0 -10671
  33. package/dist-bunli/cli-am5x7tb4.js +0 -192
  34. package/dist-bunli/cli-bajwv85z.js +0 -24
  35. package/dist-bunli/cli-ccax7s0s.js +0 -34
  36. package/dist-bunli/cli-cvxvcw7c.js +0 -46
  37. package/dist-bunli/cli-diagnostics-10drxh34.js +0 -34
  38. package/dist-bunli/cli-doctor-6fyxq940.js +0 -1446
  39. package/dist-bunli/cli-e4bwd81c.js +0 -1260
  40. package/dist-bunli/cli-fv4h3ydt.js +0 -173823
  41. package/dist-bunli/cli-hv2yedw2.js +0 -74591
  42. package/dist-bunli/cli-init-7avk42dh.js +0 -880
  43. package/dist-bunli/cli-kfm9mm68.js +0 -14679
  44. package/dist-bunli/cli-prompt-ncyg68rn.js +0 -12
  45. package/dist-bunli/cli-rdcga1bd.js +0 -135
  46. package/dist-bunli/cli-scaffold-0bb6pr3w.js +0 -538
  47. package/dist-bunli/cli-t73q5aqz.js +0 -103
  48. package/dist-bunli/cli-templates-g8t4fm11.js +0 -167
  49. package/dist-bunli/cli-tj7ajdvf.js +0 -2612
  50. package/dist-bunli/cli-tq730sqt.js +0 -344
  51. package/dist-bunli/cli-xnn9xjcy.js +0 -68
  52. package/dist-bunli/cli-z48frc8t.js +0 -229
  53. package/dist-bunli/cli.js +0 -2523
  54. package/dist-bunli/command-list-y3g7e9rb.js +0 -4013
  55. package/dist-bunli/create-template-validation-4fr851vg.js +0 -16
  56. package/dist-bunli/migrations-3vngdy51.js +0 -47
  57. package/dist-bunli/sync-k2k8svyc.js +0 -13
  58. package/dist-bunli/workspace-project-gmv2a71z.js +0 -22
package/dist-bunli/cli.js DELETED
@@ -1,2523 +0,0 @@
1
- // @bun
2
- import {
3
- ALL_COMMAND_OPTION_METADATA,
4
- COMMAND_OPTION_METADATA_BY_GROUP,
5
- COMMAND_ROUTING_METADATA,
6
- GLOBAL_OPTION_METADATA,
7
- WP_TYPIA_CANONICAL_CREATE_USAGE,
8
- WP_TYPIA_COMMAND_OPTION_GROUP_NAMES_BY_TOP_LEVEL_COMMAND,
9
- WP_TYPIA_CONFIG_SOURCES,
10
- WP_TYPIA_RESERVED_TOP_LEVEL_COMMAND_NAMES,
11
- buildCommandOptionParser,
12
- collectOptionNamesByType,
13
- collectPositionalIndexes,
14
- createMissingOptionValueError,
15
- createPlugin,
16
- extractKnownOptionValuesFromArgv,
17
- findFirstPositionalIndex,
18
- loadWpTypiaUserConfig,
19
- loadWpTypiaUserConfigFromSource,
20
- mergeWpTypiaUserConfig,
21
- normalizeCliOutputFormatArgv,
22
- package_default,
23
- validateCliOutputFormatArgv,
24
- writeStructuredCliDiagnosticError
25
- } from "./cli-368d4cgy.js";
26
- import"./cli-03j0axbt.js";
27
- import {
28
- GLOBAL_FLAGS,
29
- Result,
30
- TaggedError,
31
- createCLI,
32
- deepMerge,
33
- defineCommand,
34
- defineConfig,
35
- defineGroup,
36
- exports_external
37
- } from "./cli-hv2yedw2.js";
38
- import"./cli-ac2ebaf8.js";
39
- import"./cli-6v0pcxw6.js";
40
- import"./cli-bajwv85z.js";
41
- import {
42
- CLI_DIAGNOSTIC_CODES,
43
- createCliDiagnosticCodeError
44
- } from "./cli-tq730sqt.js";
45
- import {
46
- __require
47
- } from "./cli-xnn9xjcy.js";
48
-
49
- // src/cli.ts
50
- import fs from "fs";
51
- import path2 from "path";
52
- import { fileURLToPath } from "url";
53
-
54
- // ../../node_modules/.bun/@bunli+plugin-ai-detect@0.6.4+44deef6f8e4a2f18/node_modules/@bunli/plugin-ai-detect/src/index.ts
55
- var AI_AGENTS = [
56
- {
57
- name: "claude",
58
- envVars: ["CLAUDECODE", "CLAUDE_CODE"],
59
- detect: (env) => !!env.CLAUDECODE || !!env.CLAUDE_CODE
60
- },
61
- {
62
- name: "cursor",
63
- envVars: ["CURSOR_AGENT"],
64
- detect: (env) => !!env.CURSOR_AGENT
65
- },
66
- {
67
- name: "codex",
68
- envVars: ["CODEX_CI", "CODEX_THREAD_ID", "CODEX_SANDBOX"],
69
- detect: (env) => !!env.CODEX_CI || !!env.CODEX_THREAD_ID || !!env.CODEX_SANDBOX
70
- },
71
- {
72
- name: "amp",
73
- envVars: ["AMP_CURRENT_THREAD_ID", "AGENT"],
74
- detect: (env) => !!env.AMP_CURRENT_THREAD_ID || env.AGENT === "amp"
75
- },
76
- {
77
- name: "gemini",
78
- envVars: ["GEMINI_CLI"],
79
- detect: (env) => !!env.GEMINI_CLI
80
- },
81
- {
82
- name: "opencode",
83
- envVars: ["OPENCODE"],
84
- detect: (env) => env.OPENCODE === "1"
85
- }
86
- ];
87
- var aiAgentPlugin = createPlugin((options = {}) => {
88
- const agents = [...AI_AGENTS, ...options.customAgents || []];
89
- return {
90
- name: "@bunli/plugin-ai-detect",
91
- version: "1.0.0",
92
- store: {
93
- isAIAgent: false,
94
- aiAgents: [],
95
- aiAgentEnvVars: []
96
- },
97
- beforeCommand(context) {
98
- const env = process.env;
99
- const detectedAgents = [];
100
- const allDetectedEnvVars = [];
101
- context.env.isAIAgent = false;
102
- context.env.aiAgents = [];
103
- for (const agent of agents) {
104
- if (agent.detect(env)) {
105
- detectedAgents.push(agent.name);
106
- const detectedVars = agent.envVars.filter((v) => !!env[v]);
107
- allDetectedEnvVars.push(...detectedVars);
108
- if (options.verbose) {
109
- console.log(`\uD83E\uDD16 AI agent detected: ${agent.name}`);
110
- console.log(` Environment variables: ${detectedVars.join(", ")}`);
111
- }
112
- }
113
- }
114
- if (detectedAgents.length > 0) {
115
- context.env.isAIAgent = true;
116
- context.env.aiAgents = detectedAgents;
117
- if (context.store) {
118
- context.store.isAIAgent = true;
119
- context.store.aiAgents = detectedAgents;
120
- context.store.aiAgentEnvVars = allDetectedEnvVars;
121
- }
122
- if (options.verbose) {
123
- if (detectedAgents.length === 1) {
124
- console.log(`\uD83E\uDD16 AI agent detected: ${detectedAgents[0]}`);
125
- } else {
126
- console.log(`\uD83E\uDD16 Multiple AI agents detected: ${detectedAgents.join(", ")}`);
127
- }
128
- }
129
- } else {
130
- if (context.store) {
131
- context.store.isAIAgent = false;
132
- context.store.aiAgents = [];
133
- context.store.aiAgentEnvVars = [];
134
- }
135
- }
136
- }
137
- };
138
- });
139
-
140
- // ../../node_modules/.bun/@bunli+plugin-completions@0.3.5+44deef6f8e4a2f18/node_modules/@bunli/plugin-completions/dist/index.js
141
- import { resolve } from "path";
142
- import { readFile } from "fs/promises";
143
- import { pathToFileURL } from "url";
144
- function generate(name, exec) {
145
- return `#compdef ${name}
146
- compdef _${name} ${name}
147
-
148
- # zsh completion for ${name} -*- shell-script -*-
149
-
150
- __${name}_debug() {
151
- local file="$BASH_COMP_DEBUG_FILE"
152
- if [[ -n \${file} ]]; then
153
- echo "$*" >> "\${file}"
154
- fi
155
- }
156
-
157
- _${name}() {
158
- local shellCompDirectiveError=${ShellCompDirective.ShellCompDirectiveError}
159
- local shellCompDirectiveNoSpace=${ShellCompDirective.ShellCompDirectiveNoSpace}
160
- local shellCompDirectiveNoFileComp=${ShellCompDirective.ShellCompDirectiveNoFileComp}
161
- local shellCompDirectiveFilterFileExt=${ShellCompDirective.ShellCompDirectiveFilterFileExt}
162
- local shellCompDirectiveFilterDirs=${ShellCompDirective.ShellCompDirectiveFilterDirs}
163
- local shellCompDirectiveKeepOrder=${ShellCompDirective.ShellCompDirectiveKeepOrder}
164
-
165
- local lastParam lastChar flagPrefix requestComp out directive comp lastComp noSpace keepOrder
166
- local -a completions
167
-
168
- __${name}_debug "\\n========= starting completion logic =========="
169
- __${name}_debug "CURRENT: \${CURRENT}, words[*]: \${words[*]}"
170
-
171
- # The user could have moved the cursor backwards on the command-line.
172
- # We need to trigger completion from the $CURRENT location, so we need
173
- # to truncate the command-line ($words) up to the $CURRENT location.
174
- # (We cannot use $CURSOR as its value does not work when a command is an alias.)
175
- words=( "\${=words[1,CURRENT]}" )
176
- __${name}_debug "Truncated words[*]: \${words[*]},"
177
-
178
- lastParam=\${words[-1]}
179
- lastChar=\${lastParam[-1]}
180
- __${name}_debug "lastParam: \${lastParam}, lastChar: \${lastChar}"
181
-
182
- # For zsh, when completing a flag with an = (e.g., ${name} -n=<TAB>)
183
- # completions must be prefixed with the flag
184
- setopt local_options BASH_REMATCH
185
- if [[ "\${lastParam}" =~ '-.*=' ]]; then
186
- # We are dealing with a flag with an =
187
- flagPrefix="-P \${BASH_REMATCH}"
188
- fi
189
-
190
- # Prepare the command to obtain completions, ensuring arguments are quoted for eval
191
- local -a args_to_quote=("\${(@)words[2,-1]}")
192
- if [ "\${lastChar}" = "" ]; then
193
- # If the last parameter is complete (there is a space following it)
194
- # We add an extra empty parameter so we can indicate this to the go completion code.
195
- __${name}_debug "Adding extra empty parameter"
196
- args_to_quote+=("")
197
- fi
198
-
199
- # Use Zsh's (q) flag to quote each argument safely for eval
200
- local quoted_args=("\${(@q)args_to_quote}")
201
-
202
- # Join the main command and the quoted arguments into a single string for eval
203
- requestComp="${exec} complete -- \${quoted_args[*]}"
204
-
205
- __${name}_debug "About to call: eval \${requestComp}"
206
-
207
- # Use eval to handle any environment variables and such
208
- out=$(eval \${requestComp} 2>/dev/null)
209
- __${name}_debug "completion output: \${out}"
210
-
211
- # Extract the directive integer following a : from the last line
212
- local lastLine
213
- while IFS='
214
- ' read -r line; do
215
- lastLine=\${line}
216
- done < <(printf "%s
217
- " "\${out[@]}")
218
- __${name}_debug "last line: \${lastLine}"
219
-
220
- if [ "\${lastLine[1]}" = : ]; then
221
- directive=\${lastLine[2,-1]}
222
- # Remove the directive including the : and the newline
223
- local suffix
224
- (( suffix=\${#lastLine}+2))
225
- out=\${out[1,-$suffix]}
226
- else
227
- # There is no directive specified. Leave $out as is.
228
- __${name}_debug "No directive found. Setting to default"
229
- directive=0
230
- fi
231
-
232
- __${name}_debug "directive: \${directive}"
233
- __${name}_debug "completions: \${out}"
234
- __${name}_debug "flagPrefix: \${flagPrefix}"
235
-
236
- if [ $((directive & shellCompDirectiveError)) -ne 0 ]; then
237
- __${name}_debug "Completion received error. Ignoring completions."
238
- return
239
- fi
240
-
241
- local activeHelpMarker="%"
242
- local endIndex=\${#activeHelpMarker}
243
- local startIndex=$((\${#activeHelpMarker}+1))
244
- local hasActiveHelp=0
245
- while IFS='
246
- ' read -r comp; do
247
- # Check if this is an activeHelp statement (i.e., prefixed with $activeHelpMarker)
248
- if [ "\${comp[1,$endIndex]}" = "$activeHelpMarker" ];then
249
- __${name}_debug "ActiveHelp found: $comp"
250
- comp="\${comp[$startIndex,-1]}"
251
- if [ -n "$comp" ]; then
252
- compadd -x "\${comp}"
253
- __${name}_debug "ActiveHelp will need delimiter"
254
- hasActiveHelp=1
255
- fi
256
- continue
257
- fi
258
-
259
- if [ -n "$comp" ]; then
260
- # If requested, completions are returned with a description.
261
- # The description is preceded by a TAB character.
262
- # For zsh's _describe, we need to use a : instead of a TAB.
263
- # We first need to escape any : as part of the completion itself.
264
- comp=\${comp//:/\\:}
265
-
266
- local tab="$(printf '\\t')"
267
- comp=\${comp//$tab/:}
268
-
269
- __${name}_debug "Adding completion: \${comp}"
270
- completions+=\${comp}
271
- lastComp=$comp
272
- fi
273
- done < <(printf "%s
274
- " "\${out[@]}")
275
-
276
- # Add a delimiter after the activeHelp statements, but only if:
277
- # - there are completions following the activeHelp statements, or
278
- # - file completion will be performed (so there will be choices after the activeHelp)
279
- if [ $hasActiveHelp -eq 1 ]; then
280
- if [ \${#completions} -ne 0 ] || [ $((directive & shellCompDirectiveNoFileComp)) -eq 0 ]; then
281
- __${name}_debug "Adding activeHelp delimiter"
282
- compadd -x "--"
283
- hasActiveHelp=0
284
- fi
285
- fi
286
-
287
- if [ $((directive & shellCompDirectiveNoSpace)) -ne 0 ]; then
288
- __${name}_debug "Activating nospace."
289
- noSpace="-S ''"
290
- fi
291
-
292
- if [ $((directive & shellCompDirectiveKeepOrder)) -ne 0 ]; then
293
- __${name}_debug "Activating keep order."
294
- keepOrder="-V"
295
- fi
296
-
297
- if [ $((directive & shellCompDirectiveFilterFileExt)) -ne 0 ]; then
298
- # File extension filtering
299
- local filteringCmd
300
- filteringCmd='_files'
301
- for filter in \${completions[@]}; do
302
- if [ \${filter[1]} != '*' ]; then
303
- # zsh requires a glob pattern to do file filtering
304
- filter="\\*.$filter"
305
- fi
306
- filteringCmd+=" -g $filter"
307
- done
308
- filteringCmd+=" \${flagPrefix}"
309
-
310
- __${name}_debug "File filtering command: $filteringCmd"
311
- _arguments '*:filename:'"$filteringCmd"
312
- elif [ $((directive & shellCompDirectiveFilterDirs)) -ne 0 ]; then
313
- # File completion for directories only
314
- local subdir
315
- subdir="\${completions[1]}"
316
- if [ -n "$subdir" ]; then
317
- __${name}_debug "Listing directories in $subdir"
318
- pushd "\${subdir}" >/dev/null 2>&1
319
- else
320
- __${name}_debug "Listing directories in ."
321
- fi
322
-
323
- local result
324
- _arguments '*:dirname:_files -/'" \${flagPrefix}"
325
- result=$?
326
- if [ -n "$subdir" ]; then
327
- popd >/dev/null 2>&1
328
- fi
329
- return $result
330
- else
331
- __${name}_debug "Calling _describe"
332
- if eval _describe $keepOrder "completions" completions -Q \${flagPrefix} \${noSpace}; then
333
- __${name}_debug "_describe found some completions"
334
-
335
- # Return the success of having called _describe
336
- return 0
337
- else
338
- __${name}_debug "_describe did not find completions."
339
- __${name}_debug "Checking if we should do file completion."
340
- if [ $((directive & shellCompDirectiveNoFileComp)) -ne 0 ]; then
341
- __${name}_debug "deactivating file completion"
342
-
343
- # Return 0 to indicate completion is finished and prevent zsh from
344
- # trying other completion algorithms (which could cause hanging).
345
- # We use NoFileComp directive to explicitly disable file completion.
346
- return 0
347
- else
348
- # Perform file completion
349
- __${name}_debug "Activating file completion"
350
-
351
- # We must return the result of this command, so it must be the
352
- # last command, or else we must store its result to return it.
353
- _arguments '*:filename:_files'" \${flagPrefix}"
354
- fi
355
- fi
356
- fi
357
- }
358
-
359
- # don't run the completion function when being sourced or eval-ed
360
- if [ "\${funcstack[1]}" = "_${name}" ]; then
361
- _${name}
362
- fi
363
- `;
364
- }
365
- function generate2(name, exec) {
366
- const nameForVar = name.replace(/[-:]/g, "_");
367
- const ShellCompDirectiveError = ShellCompDirective.ShellCompDirectiveError;
368
- const ShellCompDirectiveNoSpace = ShellCompDirective.ShellCompDirectiveNoSpace;
369
- const ShellCompDirectiveNoFileComp = ShellCompDirective.ShellCompDirectiveNoFileComp;
370
- const ShellCompDirectiveFilterFileExt = ShellCompDirective.ShellCompDirectiveFilterFileExt;
371
- const ShellCompDirectiveFilterDirs = ShellCompDirective.ShellCompDirectiveFilterDirs;
372
- const ShellCompDirectiveKeepOrder = ShellCompDirective.ShellCompDirectiveKeepOrder;
373
- return `# bash completion for ${name}
374
-
375
- # Define shell completion directives
376
- readonly ShellCompDirectiveError=${ShellCompDirectiveError}
377
- readonly ShellCompDirectiveNoSpace=${ShellCompDirectiveNoSpace}
378
- readonly ShellCompDirectiveNoFileComp=${ShellCompDirectiveNoFileComp}
379
- readonly ShellCompDirectiveFilterFileExt=${ShellCompDirectiveFilterFileExt}
380
- readonly ShellCompDirectiveFilterDirs=${ShellCompDirectiveFilterDirs}
381
- readonly ShellCompDirectiveKeepOrder=${ShellCompDirectiveKeepOrder}
382
-
383
- # Function to debug completion
384
- __${nameForVar}_debug() {
385
- if [[ -n \${BASH_COMP_DEBUG_FILE:-} ]]; then
386
- echo "$*" >> "\${BASH_COMP_DEBUG_FILE}"
387
- fi
388
- }
389
-
390
- # Function to handle completions
391
- __${nameForVar}_complete() {
392
- local cur prev words cword
393
- _get_comp_words_by_ref -n "=:" cur prev words cword
394
-
395
- local requestComp out directive
396
-
397
- # Build the command to get completions
398
- requestComp="${exec} complete -- \${words[@]:1}"
399
-
400
- # Add an empty parameter if the last parameter is complete
401
- if [[ -z "$cur" ]]; then
402
- requestComp="$requestComp ''"
403
- fi
404
-
405
- # Get completions from the program
406
- out=$(eval "$requestComp" 2>/dev/null)
407
-
408
- # Extract directive if present
409
- directive=0
410
- if [[ "$out" == *:* ]]; then
411
- directive=\${out##*:}
412
- out=\${out%:*}
413
- fi
414
-
415
- # Process completions based on directive
416
- if [[ $((directive & $ShellCompDirectiveError)) -ne 0 ]]; then
417
- # Error, no completion
418
- return
419
- fi
420
-
421
- # Apply directives
422
- if [[ $((directive & $ShellCompDirectiveNoSpace)) -ne 0 ]]; then
423
- compopt -o nospace
424
- fi
425
- if [[ $((directive & $ShellCompDirectiveKeepOrder)) -ne 0 ]]; then
426
- compopt -o nosort
427
- fi
428
- if [[ $((directive & $ShellCompDirectiveNoFileComp)) -ne 0 ]]; then
429
- compopt +o default
430
- fi
431
-
432
- # Handle file extension filtering
433
- if [[ $((directive & $ShellCompDirectiveFilterFileExt)) -ne 0 ]]; then
434
- local filter=""
435
- for ext in $out; do
436
- filter="$filter|$ext"
437
- done
438
- filter="\\.($filter)"
439
- compopt -o filenames
440
- COMPREPLY=( $(compgen -f -X "!$filter" -- "$cur") )
441
- return
442
- fi
443
-
444
- # Handle directory filtering
445
- if [[ $((directive & $ShellCompDirectiveFilterDirs)) -ne 0 ]]; then
446
- compopt -o dirnames
447
- COMPREPLY=( $(compgen -d -- "$cur") )
448
- return
449
- fi
450
-
451
- # Process completions
452
- local IFS=$'\\n'
453
- local tab=$(printf '\\t')
454
-
455
- # Parse completions with descriptions
456
- local completions=()
457
- while read -r comp; do
458
- if [[ "$comp" == *$tab* ]]; then
459
- # Split completion and description
460
- local value=\${comp%%$tab*}
461
- local desc=\${comp#*$tab}
462
- completions+=("$value")
463
- else
464
- completions+=("$comp")
465
- fi
466
- done <<< "$out"
467
-
468
- # Return completions
469
- COMPREPLY=( $(compgen -W "\${completions[*]}" -- "$cur") )
470
- }
471
-
472
- # Register completion function
473
- complete -F __${nameForVar}_complete ${name}
474
- `;
475
- }
476
- function generate3(name, exec) {
477
- const nameForVar = name.replace(/[-:]/g, "_");
478
- const ShellCompDirectiveError = ShellCompDirective.ShellCompDirectiveError;
479
- const ShellCompDirectiveNoSpace = ShellCompDirective.ShellCompDirectiveNoSpace;
480
- const ShellCompDirectiveNoFileComp = ShellCompDirective.ShellCompDirectiveNoFileComp;
481
- const ShellCompDirectiveFilterFileExt = ShellCompDirective.ShellCompDirectiveFilterFileExt;
482
- const ShellCompDirectiveFilterDirs = ShellCompDirective.ShellCompDirectiveFilterDirs;
483
- const ShellCompDirectiveKeepOrder = ShellCompDirective.ShellCompDirectiveKeepOrder;
484
- return `# fish completion for ${name} -*- shell-script -*-
485
-
486
- function __${nameForVar}_debug
487
- set -l file "$BASH_COMP_DEBUG_FILE"
488
- if test -n "$file"
489
- echo "$argv" >> $file
490
- end
491
- end
492
-
493
- function __${nameForVar}_perform_completion
494
- __${nameForVar}_debug "Starting __${nameForVar}_perform_completion"
495
-
496
- # Extract all args except the last one
497
- set -l args (commandline -opc)
498
- # Extract the last arg and escape it in case it is a space or wildcard
499
- set -l lastArg (string escape -- (commandline -ct))
500
-
501
- __${nameForVar}_debug "args: $args"
502
- __${nameForVar}_debug "last arg: $lastArg"
503
-
504
- # Build the completion request command
505
- set -l requestComp "${exec} complete -- (string join ' ' -- (string escape -- $args[2..-1])) $lastArg"
506
-
507
- __${nameForVar}_debug "Calling $requestComp"
508
- set -l results (eval $requestComp 2> /dev/null)
509
-
510
- # Some programs may output extra empty lines after the directive.
511
- # Let's ignore them or else it will break completion.
512
- # Ref: https://github.com/spf13/cobra/issues/1279
513
- for line in $results[-1..1]
514
- if test (string trim -- $line) = ""
515
- # Found an empty line, remove it
516
- set results $results[1..-2]
517
- else
518
- # Found non-empty line, we have our proper output
519
- break
520
- end
521
- end
522
-
523
- set -l comps $results[1..-2]
524
- set -l directiveLine $results[-1]
525
-
526
- # For Fish, when completing a flag with an = (e.g., <program> -n=<TAB>)
527
- # completions must be prefixed with the flag
528
- set -l flagPrefix (string match -r -- '-.*=' "$lastArg")
529
-
530
- __${nameForVar}_debug "Comps: $comps"
531
- __${nameForVar}_debug "DirectiveLine: $directiveLine"
532
- __${nameForVar}_debug "flagPrefix: $flagPrefix"
533
-
534
- for comp in $comps
535
- printf "%s%s\\n" "$flagPrefix" "$comp"
536
- end
537
-
538
- printf "%s\\n" "$directiveLine"
539
- end
540
-
541
- # This function limits calls to __${nameForVar}_perform_completion, by caching the result
542
- function __${nameForVar}_perform_completion_once
543
- __${nameForVar}_debug "Starting __${nameForVar}_perform_completion_once"
544
-
545
- if test -n "$__${nameForVar}_perform_completion_once_result"
546
- __${nameForVar}_debug "Seems like a valid result already exists, skipping __${nameForVar}_perform_completion"
547
- return 0
548
- end
549
-
550
- set --global __${nameForVar}_perform_completion_once_result (__${nameForVar}_perform_completion)
551
- if test -z "$__${nameForVar}_perform_completion_once_result"
552
- __${nameForVar}_debug "No completions, probably due to a failure"
553
- return 1
554
- end
555
-
556
- __${nameForVar}_debug "Performed completions and set __${nameForVar}_perform_completion_once_result"
557
- return 0
558
- end
559
-
560
- # This function is used to clear the cached result after completions are run
561
- function __${nameForVar}_clear_perform_completion_once_result
562
- __${nameForVar}_debug ""
563
- __${nameForVar}_debug "========= clearing previously set __${nameForVar}_perform_completion_once_result variable =========="
564
- set --erase __${nameForVar}_perform_completion_once_result
565
- __${nameForVar}_debug "Successfully erased the variable __${nameForVar}_perform_completion_once_result"
566
- end
567
-
568
- function __${nameForVar}_requires_order_preservation
569
- __${nameForVar}_debug ""
570
- __${nameForVar}_debug "========= checking if order preservation is required =========="
571
-
572
- __${nameForVar}_perform_completion_once
573
- if test -z "$__${nameForVar}_perform_completion_once_result"
574
- __${nameForVar}_debug "Error determining if order preservation is required"
575
- return 1
576
- end
577
-
578
- set -l directive (string sub --start 2 $__${nameForVar}_perform_completion_once_result[-1])
579
- __${nameForVar}_debug "Directive is: $directive"
580
-
581
- set -l shellCompDirectiveKeepOrder ${ShellCompDirectiveKeepOrder}
582
- set -l keeporder (math (math --scale 0 $directive / $shellCompDirectiveKeepOrder) % 2)
583
- __${nameForVar}_debug "Keeporder is: $keeporder"
584
-
585
- if test $keeporder -ne 0
586
- __${nameForVar}_debug "This does require order preservation"
587
- return 0
588
- end
589
-
590
- __${nameForVar}_debug "This doesn't require order preservation"
591
- return 1
592
- end
593
-
594
- # This function does two things:
595
- # - Obtain the completions and store them in the global __${nameForVar}_comp_results
596
- # - Return false if file completion should be performed
597
- function __${nameForVar}_prepare_completions
598
- __${nameForVar}_debug ""
599
- __${nameForVar}_debug "========= starting completion logic =========="
600
-
601
- # Start fresh
602
- set --erase __${nameForVar}_comp_results
603
-
604
- __${nameForVar}_perform_completion_once
605
- __${nameForVar}_debug "Completion results: $__${nameForVar}_perform_completion_once_result"
606
-
607
- if test -z "$__${nameForVar}_perform_completion_once_result"
608
- __${nameForVar}_debug "No completion, probably due to a failure"
609
- # Might as well do file completion, in case it helps
610
- return 1
611
- end
612
-
613
- set -l directive (string sub --start 2 $__${nameForVar}_perform_completion_once_result[-1])
614
- set --global __${nameForVar}_comp_results $__${nameForVar}_perform_completion_once_result[1..-2]
615
-
616
- __${nameForVar}_debug "Completions are: $__${nameForVar}_comp_results"
617
- __${nameForVar}_debug "Directive is: $directive"
618
-
619
- set -l shellCompDirectiveError ${ShellCompDirectiveError}
620
- set -l shellCompDirectiveNoSpace ${ShellCompDirectiveNoSpace}
621
- set -l shellCompDirectiveNoFileComp ${ShellCompDirectiveNoFileComp}
622
- set -l shellCompDirectiveFilterFileExt ${ShellCompDirectiveFilterFileExt}
623
- set -l shellCompDirectiveFilterDirs ${ShellCompDirectiveFilterDirs}
624
-
625
- if test -z "$directive"
626
- set directive 0
627
- end
628
-
629
- set -l compErr (math (math --scale 0 $directive / $shellCompDirectiveError) % 2)
630
- if test $compErr -eq 1
631
- __${nameForVar}_debug "Received error directive: aborting."
632
- # Might as well do file completion, in case it helps
633
- return 1
634
- end
635
-
636
- set -l filefilter (math (math --scale 0 $directive / $shellCompDirectiveFilterFileExt) % 2)
637
- set -l dirfilter (math (math --scale 0 $directive / $shellCompDirectiveFilterDirs) % 2)
638
- if test $filefilter -eq 1; or test $dirfilter -eq 1
639
- __${nameForVar}_debug "File extension filtering or directory filtering not supported"
640
- # Do full file completion instead
641
- return 1
642
- end
643
-
644
- set -l nospace (math (math --scale 0 $directive / $shellCompDirectiveNoSpace) % 2)
645
- set -l nofiles (math (math --scale 0 $directive / $shellCompDirectiveNoFileComp) % 2)
646
-
647
- __${nameForVar}_debug "nospace: $nospace, nofiles: $nofiles"
648
-
649
- # If we want to prevent a space, or if file completion is NOT disabled,
650
- # we need to count the number of valid completions.
651
- # To do so, we will filter on prefix as the completions we have received
652
- # may not already be filtered so as to allow fish to match on different
653
- # criteria than the prefix.
654
- if test $nospace -ne 0; or test $nofiles -eq 0
655
- set -l prefix (commandline -t | string escape --style=regex)
656
- __${nameForVar}_debug "prefix: $prefix"
657
-
658
- set -l completions (string match -r -- "^$prefix.*" $__${nameForVar}_comp_results)
659
- set --global __${nameForVar}_comp_results $completions
660
- __${nameForVar}_debug "Filtered completions are: $__${nameForVar}_comp_results"
661
-
662
- # Important not to quote the variable for count to work
663
- set -l numComps (count $__${nameForVar}_comp_results)
664
- __${nameForVar}_debug "numComps: $numComps"
665
-
666
- if test $numComps -eq 1; and test $nospace -ne 0
667
- # We must first split on \\t to get rid of the descriptions to be
668
- # able to check what the actual completion will be.
669
- # We don't need descriptions anyway since there is only a single
670
- # real completion which the shell will expand immediately.
671
- set -l split (string split --max 1 "\\t" $__${nameForVar}_comp_results[1])
672
-
673
- # Fish won't add a space if the completion ends with any
674
- # of the following characters: @=/:.,
675
- set -l lastChar (string sub -s -1 -- $split)
676
- if not string match -r -q "[@=/:.,]" -- "$lastChar"
677
- # In other cases, to support the "nospace" directive we trick the shell
678
- # by outputting an extra, longer completion.
679
- __${nameForVar}_debug "Adding second completion to perform nospace directive"
680
- set --global __${nameForVar}_comp_results $split[1] $split[1].
681
- __${nameForVar}_debug "Completions are now: $__${nameForVar}_comp_results"
682
- end
683
- end
684
-
685
- if test $numComps -eq 0; and test $nofiles -eq 0
686
- # To be consistent with bash and zsh, we only trigger file
687
- # completion when there are no other completions
688
- __${nameForVar}_debug "Requesting file completion"
689
- return 1
690
- end
691
- end
692
-
693
- return 0
694
- end
695
-
696
- # Since Fish completions are only loaded once the user triggers them, we trigger them ourselves
697
- # so we can properly delete any completions provided by another script.
698
- # Only do this if the program can be found, or else fish may print some errors; besides,
699
- # the existing completions will only be loaded if the program can be found.
700
- if type -q "${name}"
701
- # The space after the program name is essential to trigger completion for the program
702
- # and not completion of the program name itself.
703
- # Also, we use '> /dev/null 2>&1' since '&>' is not supported in older versions of fish.
704
- complete --do-complete "${name} " > /dev/null 2>&1
705
- end
706
-
707
- # Remove any pre-existing completions for the program since we will be handling all of them.
708
- complete -c ${name} -e
709
-
710
- # This will get called after the two calls below and clear the cached result
711
- complete -c ${name} -n '__${nameForVar}_clear_perform_completion_once_result'
712
- # The call to __${nameForVar}_prepare_completions will setup __${nameForVar}_comp_results
713
- # which provides the program's completion choices.
714
- # If this doesn't require order preservation, we don't use the -k flag
715
- complete -c ${name} -n 'not __${nameForVar}_requires_order_preservation && __${nameForVar}_prepare_completions' -f -a '$__${nameForVar}_comp_results'
716
- # Otherwise we use the -k flag
717
- complete -k -c ${name} -n '__${nameForVar}_requires_order_preservation && __${nameForVar}_prepare_completions' -f -a '$__${nameForVar}_comp_results'
718
- `;
719
- }
720
- function generate4(name, exec) {
721
- const nameForVar = name.replace(/[-:]/g, "_");
722
- const ShellCompDirectiveError = ShellCompDirective.ShellCompDirectiveError;
723
- const ShellCompDirectiveNoSpace = ShellCompDirective.ShellCompDirectiveNoSpace;
724
- const ShellCompDirectiveNoFileComp = ShellCompDirective.ShellCompDirectiveNoFileComp;
725
- const ShellCompDirectiveFilterFileExt = ShellCompDirective.ShellCompDirectiveFilterFileExt;
726
- const ShellCompDirectiveFilterDirs = ShellCompDirective.ShellCompDirectiveFilterDirs;
727
- const ShellCompDirectiveKeepOrder = ShellCompDirective.ShellCompDirectiveKeepOrder;
728
- return `# powershell completion for ${name} -*- shell-script -*-
729
-
730
- [Console]::OutputEncoding = [System.Text.Encoding]::UTF8
731
- function __${name}_debug {
732
- if ($env:BASH_COMP_DEBUG_FILE) {
733
- "$args" | Out-File -Append -FilePath "$env:BASH_COMP_DEBUG_FILE"
734
- }
735
- }
736
-
737
- filter __${name}_escapeStringWithSpecialChars {
738
- $_ -replace '\\s|#|@|\\$|;|,|''|\\{|\\}|\\(|\\)|"|\\||<|>|&','\`$&'
739
- }
740
-
741
- [scriptblock]$__${nameForVar}CompleterBlock = {
742
- param(
743
- $WordToComplete,
744
- $CommandAst,
745
- $CursorPosition
746
- )
747
-
748
- # Get the current command line and convert into a string
749
- $Command = $CommandAst.CommandElements
750
- $Command = "$Command"
751
-
752
- __${name}_debug ""
753
- __${name}_debug "========= starting completion logic =========="
754
- __${name}_debug "WordToComplete: $WordToComplete Command: $Command CursorPosition: $CursorPosition"
755
-
756
- # The user could have moved the cursor backwards on the command-line.
757
- # We need to trigger completion from the $CursorPosition location, so we need
758
- # to truncate the command-line ($Command) up to the $CursorPosition location.
759
- # Make sure the $Command is longer then the $CursorPosition before we truncate.
760
- # This happens because the $Command does not include the last space.
761
- if ($Command.Length -gt $CursorPosition) {
762
- $Command = $Command.Substring(0, $CursorPosition)
763
- }
764
- __${name}_debug "Truncated command: $Command"
765
-
766
- $ShellCompDirectiveError=${ShellCompDirectiveError}
767
- $ShellCompDirectiveNoSpace=${ShellCompDirectiveNoSpace}
768
- $ShellCompDirectiveNoFileComp=${ShellCompDirectiveNoFileComp}
769
- $ShellCompDirectiveFilterFileExt=${ShellCompDirectiveFilterFileExt}
770
- $ShellCompDirectiveFilterDirs=${ShellCompDirectiveFilterDirs}
771
- $ShellCompDirectiveKeepOrder=${ShellCompDirectiveKeepOrder}
772
-
773
- # Prepare the command to request completions for the program.
774
- # Split the command at the first space to separate the program and arguments.
775
- $Program, $Arguments = $Command.Split(" ", 2)
776
-
777
- $QuotedArgs = ($Arguments -split ' ' | ForEach-Object { "'" + ($_ -replace "'", "''") + "'" }) -join ' '
778
- __${name}_debug "QuotedArgs: $QuotedArgs"
779
-
780
- $RequestComp = "& ${exec} complete '--' $QuotedArgs"
781
- __${name}_debug "RequestComp: $RequestComp"
782
-
783
- # we cannot use $WordToComplete because it
784
- # has the wrong values if the cursor was moved
785
- # so use the last argument
786
- if ($WordToComplete -ne "" ) {
787
- $WordToComplete = $Arguments.Split(" ")[-1]
788
- }
789
- __${name}_debug "New WordToComplete: $WordToComplete"
790
-
791
-
792
- # Check for flag with equal sign
793
- $IsEqualFlag = ($WordToComplete -Like "--*=*" )
794
- if ( $IsEqualFlag ) {
795
- __${name}_debug "Completing equal sign flag"
796
- # Remove the flag part
797
- $Flag, $WordToComplete = $WordToComplete.Split("=", 2)
798
- }
799
-
800
- if ( $WordToComplete -eq "" -And ( -Not $IsEqualFlag )) {
801
- # If the last parameter is complete (there is a space following it)
802
- # We add an extra empty parameter so we can indicate this to the go method.
803
- __${name}_debug "Adding extra empty parameter"
804
- # PowerShell 7.2+ changed the way how the arguments are passed to executables,
805
- # so for pre-7.2 or when Legacy argument passing is enabled we need to use
806
- if ($PSVersionTable.PsVersion -lt [version]'7.2.0' -or
807
- ($PSVersionTable.PsVersion -lt [version]'7.3.0' -and -not [ExperimentalFeature]::IsEnabled("PSNativeCommandArgumentPassing")) -or
808
- (($PSVersionTable.PsVersion -ge [version]'7.3.0' -or [ExperimentalFeature]::IsEnabled("PSNativeCommandArgumentPassing")) -and
809
- $PSNativeCommandArgumentPassing -eq 'Legacy')) {
810
- $RequestComp="$RequestComp" + ' \`"\`"'
811
- } else {
812
- $RequestComp = "$RequestComp" + ' ""'
813
- }
814
- }
815
-
816
- __${name}_debug "Calling $RequestComp"
817
- # First disable ActiveHelp which is not supported for Powershell
818
- $env:ActiveHelp = 0
819
-
820
- # call the command store the output in $out and redirect stderr and stdout to null
821
- # $Out is an array contains each line per element
822
- Invoke-Expression -OutVariable out "$RequestComp" 2>&1 | Out-Null
823
-
824
- # get directive from last line
825
- [int]$Directive = $Out[-1].TrimStart(':')
826
- if ($Directive -eq "") {
827
- # There is no directive specified
828
- $Directive = 0
829
- }
830
- __${name}_debug "The completion directive is: $Directive"
831
-
832
- # remove directive (last element) from out
833
- $Out = $Out | Where-Object { $_ -ne $Out[-1] }
834
- __${name}_debug "The completions are: $Out"
835
-
836
- if (($Directive -band $ShellCompDirectiveError) -ne 0 ) {
837
- # Error code. No completion.
838
- __${name}_debug "Received error from custom completion go code"
839
- return
840
- }
841
-
842
- $Longest = 0
843
- [Array]$Values = $Out | ForEach-Object {
844
- # Split the output in name and description
845
- $Name, $Description = $_.Split("\`t", 2)
846
- __${name}_debug "Name: $Name Description: $Description"
847
-
848
- # Look for the longest completion so that we can format things nicely
849
- if ($Longest -lt $Name.Length) {
850
- $Longest = $Name.Length
851
- }
852
-
853
- # Set the description to a one space string if there is none set.
854
- # This is needed because the CompletionResult does not accept an empty string as argument
855
- if (-Not $Description) {
856
- $Description = " "
857
- }
858
- @{ Name = "$Name"; Description = "$Description" }
859
- }
860
-
861
-
862
- $Space = " "
863
- if (($Directive -band $ShellCompDirectiveNoSpace) -ne 0 ) {
864
- # remove the space here
865
- __${name}_debug "ShellCompDirectiveNoSpace is called"
866
- $Space = ""
867
- }
868
-
869
- if ((($Directive -band $ShellCompDirectiveFilterFileExt) -ne 0 ) -or
870
- (($Directive -band $ShellCompDirectiveFilterDirs) -ne 0 )) {
871
- __${name}_debug "ShellCompDirectiveFilterFileExt ShellCompDirectiveFilterDirs are not supported"
872
-
873
- # return here to prevent the completion of the extensions
874
- return
875
- }
876
-
877
- $Values = $Values | Where-Object {
878
- # filter the result
879
- $_.Name -like "$WordToComplete*"
880
-
881
- # Join the flag back if we have an equal sign flag
882
- if ( $IsEqualFlag ) {
883
- __${name}_debug "Join the equal sign flag back to the completion value"
884
- $_.Name = $Flag + "=" + $_.Name
885
- }
886
- }
887
-
888
- # we sort the values in ascending order by name if keep order isn't passed
889
- if (($Directive -band $ShellCompDirectiveKeepOrder) -eq 0 ) {
890
- $Values = $Values | Sort-Object -Property Name
891
- }
892
-
893
- if (($Directive -band $ShellCompDirectiveNoFileComp) -ne 0 ) {
894
- __${name}_debug "ShellCompDirectiveNoFileComp is called"
895
-
896
- if ($Values.Length -eq 0) {
897
- # Just print an empty string here so the
898
- # shell does not start to complete paths.
899
- # We cannot use CompletionResult here because
900
- # it does not accept an empty string as argument.
901
- ""
902
- return
903
- }
904
- }
905
-
906
- # Get the current mode
907
- $Mode = (Get-PSReadLineKeyHandler | Where-Object { $_.Key -eq "Tab" }).Function
908
- __${name}_debug "Mode: $Mode"
909
-
910
- $Values | ForEach-Object {
911
-
912
- # store temporary because switch will overwrite $_
913
- $comp = $_
914
-
915
- # PowerShell supports three different completion modes
916
- # - TabCompleteNext (default windows style - on each key press the next option is displayed)
917
- # - Complete (works like bash)
918
- # - MenuComplete (works like zsh)
919
- # You set the mode with Set-PSReadLineKeyHandler -Key Tab -Function <mode>
920
-
921
- # CompletionResult Arguments:
922
- # 1) CompletionText text to be used as the auto completion result
923
- # 2) ListItemText text to be displayed in the suggestion list
924
- # 3) ResultType type of completion result
925
- # 4) ToolTip text for the tooltip with details about the object
926
-
927
- switch ($Mode) {
928
-
929
- # bash like
930
- "Complete" {
931
-
932
- if ($Values.Length -eq 1) {
933
- __${name}_debug "Only one completion left"
934
-
935
- # insert space after value
936
- [System.Management.Automation.CompletionResult]::new($($comp.Name | __${name}_escapeStringWithSpecialChars) + $Space, "$($comp.Name)", 'ParameterValue', "$($comp.Description)")
937
-
938
- } else {
939
- # Add the proper number of spaces to align the descriptions
940
- while($comp.Name.Length -lt $Longest) {
941
- $comp.Name = $comp.Name + " "
942
- }
943
-
944
- # Check for empty description and only add parentheses if needed
945
- if ($($comp.Description) -eq " " ) {
946
- $Description = ""
947
- } else {
948
- $Description = " ($($comp.Description))"
949
- }
950
-
951
- [System.Management.Automation.CompletionResult]::new("$($comp.Name)$Description", "$($comp.Name)$Description", 'ParameterValue', "$($comp.Description)")
952
- }
953
- }
954
-
955
- # zsh like
956
- "MenuComplete" {
957
- # insert space after value
958
- # MenuComplete will automatically show the ToolTip of
959
- # the highlighted value at the bottom of the suggestions.
960
- [System.Management.Automation.CompletionResult]::new($($comp.Name | __${name}_escapeStringWithSpecialChars) + $Space, "$($comp.Name)", 'ParameterValue', "$($comp.Description)")
961
- }
962
-
963
- # TabCompleteNext and in case we get something unknown
964
- Default {
965
- # Like MenuComplete but we don't want to add a space here because
966
- # the user need to press space anyway to get the completion.
967
- # Description will not be shown because that's not possible with TabCompleteNext
968
- [System.Management.Automation.CompletionResult]::new($($comp.Name | __${name}_escapeStringWithSpecialChars), "$($comp.Name)", 'ParameterValue', "$($comp.Description)")
969
- }
970
- }
971
-
972
- }
973
- }
974
-
975
- Register-ArgumentCompleter -CommandName '${name}' -ScriptBlock $__${nameForVar}CompleterBlock
976
- `;
977
- }
978
- var ShellCompDirective = {
979
- ShellCompDirectiveError: 1 << 0,
980
- ShellCompDirectiveNoSpace: 1 << 1,
981
- ShellCompDirectiveNoFileComp: 1 << 2,
982
- ShellCompDirectiveFilterFileExt: 1 << 3,
983
- ShellCompDirectiveFilterDirs: 1 << 4,
984
- ShellCompDirectiveKeepOrder: 1 << 5,
985
- shellCompDirectiveMaxValue: 1 << 6,
986
- ShellCompDirectiveDefault: 0
987
- };
988
-
989
- class Argument {
990
- name;
991
- variadic;
992
- command;
993
- handler;
994
- constructor(command, name, handler, variadic = false) {
995
- this.command = command;
996
- this.name = name;
997
- this.handler = handler;
998
- this.variadic = variadic;
999
- }
1000
- }
1001
-
1002
- class Option {
1003
- value;
1004
- description;
1005
- command;
1006
- handler;
1007
- alias;
1008
- isBoolean;
1009
- constructor(command, value, description, handler, alias, isBoolean) {
1010
- this.command = command;
1011
- this.value = value;
1012
- this.description = description;
1013
- this.handler = handler;
1014
- this.alias = alias;
1015
- this.isBoolean = isBoolean;
1016
- }
1017
- }
1018
-
1019
- class Command {
1020
- value;
1021
- description;
1022
- options = new Map;
1023
- arguments = new Map;
1024
- parent;
1025
- constructor(value, description) {
1026
- this.value = value;
1027
- this.description = description;
1028
- }
1029
- option(value, description, handlerOrAlias, alias) {
1030
- let handler;
1031
- let aliasStr;
1032
- let isBoolean;
1033
- if (typeof handlerOrAlias === "function") {
1034
- handler = handlerOrAlias;
1035
- aliasStr = alias;
1036
- isBoolean = false;
1037
- } else if (typeof handlerOrAlias === "string") {
1038
- handler = undefined;
1039
- aliasStr = handlerOrAlias;
1040
- isBoolean = true;
1041
- } else {
1042
- handler = undefined;
1043
- aliasStr = undefined;
1044
- isBoolean = true;
1045
- }
1046
- const option = new Option(this, value, description, handler, aliasStr, isBoolean);
1047
- this.options.set(value, option);
1048
- return this;
1049
- }
1050
- argument(name, handler, variadic = false) {
1051
- const arg = new Argument(this, name, handler, variadic);
1052
- this.arguments.set(name, arg);
1053
- return this;
1054
- }
1055
- }
1056
- var SUPPORTED_SHELLS = new Set(["zsh", "bash", "fish", "powershell"]);
1057
-
1058
- class RootCommand extends Command {
1059
- commands = new Map;
1060
- completions = [];
1061
- directive = ShellCompDirective.ShellCompDirectiveDefault;
1062
- constructor() {
1063
- super("", "");
1064
- }
1065
- command(value, description) {
1066
- const c = new Command(value, description);
1067
- this.commands.set(value, c);
1068
- return c;
1069
- }
1070
- stripOptions(args) {
1071
- const parts = [];
1072
- let i = 0;
1073
- while (i < args.length) {
1074
- const arg = args[i];
1075
- if (arg.startsWith("-")) {
1076
- i++;
1077
- const hasInlineValue = arg.includes("=");
1078
- let isBoolean = false;
1079
- const rootOption = this.findOption(this, arg);
1080
- if (rootOption) {
1081
- isBoolean = rootOption.isBoolean ?? false;
1082
- } else {
1083
- for (const [, command] of this.commands) {
1084
- const option = this.findOption(command, arg);
1085
- if (option) {
1086
- isBoolean = option.isBoolean ?? false;
1087
- break;
1088
- }
1089
- }
1090
- }
1091
- if (!hasInlineValue && !isBoolean && i < args.length && !args[i].startsWith("-")) {
1092
- i++;
1093
- }
1094
- } else {
1095
- parts.push(arg);
1096
- i++;
1097
- }
1098
- }
1099
- return parts;
1100
- }
1101
- matchCommand(args) {
1102
- args = this.stripOptions(args);
1103
- const parts = [];
1104
- let remaining = [];
1105
- let matchedCommand = null;
1106
- for (let i = 0;i < args.length; i++) {
1107
- const k = args[i];
1108
- parts.push(k);
1109
- const potential = this.commands.get(parts.join(" "));
1110
- if (potential) {
1111
- matchedCommand = potential;
1112
- } else {
1113
- remaining = args.slice(i, args.length);
1114
- break;
1115
- }
1116
- }
1117
- return [matchedCommand || this, remaining];
1118
- }
1119
- shouldCompleteFlags(lastPrevArg, toComplete) {
1120
- if (toComplete.startsWith("-")) {
1121
- return true;
1122
- }
1123
- if (lastPrevArg?.startsWith("-")) {
1124
- let option = this.findOption(this, lastPrevArg);
1125
- if (!option) {
1126
- for (const [, command] of this.commands) {
1127
- option = this.findOption(command, lastPrevArg);
1128
- if (option)
1129
- break;
1130
- }
1131
- }
1132
- if (option && option.isBoolean) {
1133
- return false;
1134
- }
1135
- return true;
1136
- }
1137
- return false;
1138
- }
1139
- shouldCompleteCommands(toComplete) {
1140
- return !toComplete.startsWith("-");
1141
- }
1142
- handleFlagCompletion(command, previousArgs, toComplete, lastPrevArg) {
1143
- let optionName;
1144
- if (toComplete.includes("=")) {
1145
- const [flag] = toComplete.split("=");
1146
- optionName = flag;
1147
- } else if (lastPrevArg?.startsWith("-")) {
1148
- const option = this.findOption(command, lastPrevArg);
1149
- if (option && !option.isBoolean) {
1150
- optionName = lastPrevArg;
1151
- }
1152
- }
1153
- if (optionName) {
1154
- const option = this.findOption(command, optionName);
1155
- if (option?.handler) {
1156
- const suggestions = [];
1157
- option.handler.call(option, (value, description) => suggestions.push({ value, description }), command.options);
1158
- this.completions = suggestions;
1159
- }
1160
- return;
1161
- }
1162
- if (toComplete.startsWith("-")) {
1163
- const isShortFlag = toComplete.startsWith("-") && !toComplete.startsWith("--");
1164
- const cleanToComplete = toComplete.replace(/^-+/, "");
1165
- for (const [name, option] of command.options) {
1166
- if (isShortFlag && option.alias && `-${option.alias}`.startsWith(toComplete)) {
1167
- this.completions.push({
1168
- value: `-${option.alias}`,
1169
- description: option.description
1170
- });
1171
- } else if (!isShortFlag && name.startsWith(cleanToComplete)) {
1172
- this.completions.push({
1173
- value: `--${name}`,
1174
- description: option.description
1175
- });
1176
- }
1177
- }
1178
- }
1179
- }
1180
- findOption(command, optionName) {
1181
- const normalized = this.normalizeOptionToken(optionName);
1182
- let option = command.options.get(optionName);
1183
- if (option)
1184
- return option;
1185
- option = command.options.get(normalized);
1186
- if (option)
1187
- return option;
1188
- for (const [_name, opt] of command.options) {
1189
- if (opt.alias === normalized) {
1190
- return opt;
1191
- }
1192
- }
1193
- return;
1194
- }
1195
- normalizeOptionToken(optionName) {
1196
- return optionName.replace(/^-+/, "").split("=")[0] ?? "";
1197
- }
1198
- handleCommandCompletion(previousArgs, toComplete) {
1199
- const commandParts = this.stripOptions(previousArgs);
1200
- for (const [k, command] of this.commands) {
1201
- if (k === "")
1202
- continue;
1203
- const parts = k.split(" ");
1204
- const match = parts.slice(0, commandParts.length).every((part, i) => part === commandParts[i]);
1205
- if (match && parts[commandParts.length]?.startsWith(toComplete)) {
1206
- this.completions.push({
1207
- value: parts[commandParts.length],
1208
- description: command.description
1209
- });
1210
- }
1211
- }
1212
- }
1213
- handlePositionalCompletion(command, previousArgs) {
1214
- const commandParts = command.value.split(" ").length;
1215
- const currentArgIndex = Math.max(0, previousArgs.length - commandParts);
1216
- const argumentEntries = Array.from(command.arguments.entries());
1217
- if (argumentEntries.length > 0) {
1218
- let targetArgument;
1219
- if (currentArgIndex < argumentEntries.length) {
1220
- const [_argName, argument] = argumentEntries[currentArgIndex];
1221
- targetArgument = argument;
1222
- } else {
1223
- const lastArgument = argumentEntries[argumentEntries.length - 1][1];
1224
- if (lastArgument.variadic) {
1225
- targetArgument = lastArgument;
1226
- }
1227
- }
1228
- if (targetArgument && targetArgument.handler && typeof targetArgument.handler === "function") {
1229
- const suggestions = [];
1230
- targetArgument.handler.call(targetArgument, (value, description) => suggestions.push({ value, description }), command.options);
1231
- this.completions.push(...suggestions);
1232
- }
1233
- }
1234
- }
1235
- complete(toComplete) {
1236
- this.directive = ShellCompDirective.ShellCompDirectiveNoFileComp;
1237
- const seen = new Set;
1238
- this.completions.filter((comp) => {
1239
- if (seen.has(comp.value))
1240
- return false;
1241
- seen.add(comp.value);
1242
- return true;
1243
- }).filter((comp) => {
1244
- if (toComplete.includes("=")) {
1245
- const [, valueToComplete] = toComplete.split("=");
1246
- return comp.value.startsWith(valueToComplete ?? "");
1247
- }
1248
- return comp.value.startsWith(toComplete);
1249
- }).forEach((comp) => console.log(`${comp.value} ${comp.description ?? ""}`));
1250
- console.log(`:${this.directive}`);
1251
- }
1252
- parse(args) {
1253
- this.completions = [];
1254
- const endsWithSpace = args[args.length - 1] === "";
1255
- if (endsWithSpace) {
1256
- args.pop();
1257
- }
1258
- let toComplete = args[args.length - 1] || "";
1259
- const previousArgs = args.slice(0, -1);
1260
- if (endsWithSpace) {
1261
- if (toComplete !== "") {
1262
- previousArgs.push(toComplete);
1263
- }
1264
- toComplete = "";
1265
- }
1266
- const [matchedCommand] = this.matchCommand(previousArgs);
1267
- const lastPrevArg = previousArgs[previousArgs.length - 1];
1268
- if (this.shouldCompleteFlags(lastPrevArg, toComplete)) {
1269
- this.handleFlagCompletion(matchedCommand, previousArgs, toComplete, lastPrevArg);
1270
- } else {
1271
- if (lastPrevArg?.startsWith("-") && toComplete === "" && endsWithSpace) {
1272
- let option = this.findOption(this, lastPrevArg);
1273
- if (!option) {
1274
- for (const [, command] of this.commands) {
1275
- option = this.findOption(command, lastPrevArg);
1276
- if (option)
1277
- break;
1278
- }
1279
- }
1280
- if (option && option.isBoolean) {
1281
- this.complete(toComplete);
1282
- return;
1283
- }
1284
- }
1285
- if (this.shouldCompleteCommands(toComplete)) {
1286
- this.handleCommandCompletion(previousArgs, toComplete);
1287
- }
1288
- if (matchedCommand && matchedCommand.arguments.size > 0) {
1289
- this.handlePositionalCompletion(matchedCommand, previousArgs);
1290
- }
1291
- }
1292
- this.complete(toComplete);
1293
- }
1294
- setup(name, executable, shell) {
1295
- if (!SUPPORTED_SHELLS.has(shell)) {
1296
- throw new Error(`Unsupported shell: ${shell}`);
1297
- }
1298
- switch (shell) {
1299
- case "zsh": {
1300
- const script = generate(name, executable);
1301
- console.log(script);
1302
- break;
1303
- }
1304
- case "bash": {
1305
- const script = generate2(name, executable);
1306
- console.log(script);
1307
- break;
1308
- }
1309
- case "fish": {
1310
- const script = generate3(name, executable);
1311
- console.log(script);
1312
- break;
1313
- }
1314
- case "powershell": {
1315
- const script = generate4(name, executable);
1316
- console.log(script);
1317
- break;
1318
- }
1319
- }
1320
- }
1321
- }
1322
- var t = new RootCommand;
1323
- function dual(arity, body) {
1324
- if (arity === 2)
1325
- return (...args) => {
1326
- if (args.length >= 2)
1327
- return body(args[0], args[1]);
1328
- return (self) => body(self, args[0]);
1329
- };
1330
- if (arity === 3)
1331
- return (...args) => {
1332
- if (args.length >= 3)
1333
- return body(args[0], args[1], args[2]);
1334
- return (self) => body(self, args[0], args[1]);
1335
- };
1336
- if (arity === 4)
1337
- return (...args) => {
1338
- if (args.length >= 4)
1339
- return body(args[0], args[1], args[2], args[3]);
1340
- return (self) => body(self, args[0], args[1], args[2]);
1341
- };
1342
- return (...args) => {
1343
- if (args.length >= arity)
1344
- return body(...args);
1345
- return (self) => body(self, ...args);
1346
- };
1347
- }
1348
- var serializeCause = (cause) => {
1349
- if (cause instanceof Error)
1350
- return {
1351
- name: cause.name,
1352
- message: cause.message,
1353
- stack: cause.stack
1354
- };
1355
- return cause;
1356
- };
1357
- var isAnyTaggedError = (value) => {
1358
- return value instanceof Error && "_tag" in value && typeof value._tag === "string";
1359
- };
1360
- var TaggedError2 = Object.assign((tag) => () => {
1361
-
1362
- class Base extends Error {
1363
- _tag = tag;
1364
- static is(value) {
1365
- return value instanceof Base;
1366
- }
1367
- constructor(args) {
1368
- const message = args && "message" in args && typeof args.message === "string" ? args.message : undefined;
1369
- const cause = args && "cause" in args ? args.cause : undefined;
1370
- super(message, cause !== undefined ? { cause } : undefined);
1371
- if (args)
1372
- Object.assign(this, args);
1373
- Object.setPrototypeOf(this, new.target.prototype);
1374
- this.name = tag;
1375
- if (cause instanceof Error && cause.stack) {
1376
- const indented = cause.stack.replace(/\n/g, `
1377
- `);
1378
- this.stack = `${this.stack}
1379
- Caused by: ${indented}`;
1380
- }
1381
- }
1382
- toJSON() {
1383
- return {
1384
- ...this,
1385
- _tag: this._tag,
1386
- name: this.name,
1387
- message: this.message,
1388
- cause: serializeCause(this.cause),
1389
- stack: this.stack
1390
- };
1391
- }
1392
- }
1393
- return Base;
1394
- }, { is: isAnyTaggedError });
1395
- var matchError = dual(2, (err$1, handlers) => {
1396
- const handler = handlers[err$1._tag];
1397
- return handler(err$1);
1398
- });
1399
- var matchErrorPartial = dual(3, (err$1, handlers, fallback) => {
1400
- const handler = handlers[err$1._tag];
1401
- if (typeof handler === "function")
1402
- return handler(err$1);
1403
- return fallback(err$1);
1404
- });
1405
- var UnhandledException = class extends TaggedError2("UnhandledException")() {
1406
- constructor(args) {
1407
- const message = args.cause instanceof Error ? `Unhandled exception: ${args.cause.message}` : `Unhandled exception: ${String(args.cause)}`;
1408
- super({
1409
- message,
1410
- cause: args.cause
1411
- });
1412
- }
1413
- };
1414
- var Panic = class extends TaggedError2("Panic")() {
1415
- };
1416
- var ResultDeserializationError = class extends TaggedError2("ResultDeserializationError")() {
1417
- constructor(args) {
1418
- super({
1419
- message: `Failed to deserialize value as Result: expected { status: "ok", value } or { status: "error", error }`,
1420
- value: args.value
1421
- });
1422
- }
1423
- };
1424
- var panic = (message, cause) => {
1425
- throw new Panic({
1426
- message,
1427
- cause
1428
- });
1429
- };
1430
- var tryOrPanic = (fn, message) => {
1431
- try {
1432
- return fn();
1433
- } catch (cause) {
1434
- throw panic(message, cause);
1435
- }
1436
- };
1437
- var tryOrPanicAsync = async (fn, message) => {
1438
- try {
1439
- return await fn();
1440
- } catch (cause) {
1441
- throw panic(message, cause);
1442
- }
1443
- };
1444
- var Ok = class Ok2 {
1445
- status = "ok";
1446
- constructor(value) {
1447
- this.value = value;
1448
- }
1449
- isOk() {
1450
- return true;
1451
- }
1452
- isErr() {
1453
- return false;
1454
- }
1455
- map(fn) {
1456
- return tryOrPanic(() => new Ok2(fn(this.value)), "map callback threw");
1457
- }
1458
- mapError(_fn) {
1459
- return this;
1460
- }
1461
- andThen(fn) {
1462
- return tryOrPanic(() => fn(this.value), "andThen callback threw");
1463
- }
1464
- andThenAsync(fn) {
1465
- return tryOrPanicAsync(() => fn(this.value), "andThenAsync callback threw");
1466
- }
1467
- match(handlers) {
1468
- return tryOrPanic(() => handlers.ok(this.value), "match ok handler threw");
1469
- }
1470
- unwrap(_message) {
1471
- return this.value;
1472
- }
1473
- unwrapOr(_fallback) {
1474
- return this.value;
1475
- }
1476
- tap(fn) {
1477
- return tryOrPanic(() => {
1478
- fn(this.value);
1479
- return this;
1480
- }, "tap callback threw");
1481
- }
1482
- tapAsync(fn) {
1483
- return tryOrPanicAsync(async () => {
1484
- await fn(this.value);
1485
- return this;
1486
- }, "tapAsync callback threw");
1487
- }
1488
- *[Symbol.iterator]() {
1489
- return this.value;
1490
- }
1491
- };
1492
- var Err = class Err2 {
1493
- status = "error";
1494
- constructor(error) {
1495
- this.error = error;
1496
- }
1497
- isOk() {
1498
- return false;
1499
- }
1500
- isErr() {
1501
- return true;
1502
- }
1503
- map(_fn) {
1504
- return this;
1505
- }
1506
- mapError(fn) {
1507
- return tryOrPanic(() => new Err2(fn(this.error)), "mapError callback threw");
1508
- }
1509
- andThen(_fn) {
1510
- return this;
1511
- }
1512
- andThenAsync(_fn) {
1513
- return Promise.resolve(this);
1514
- }
1515
- match(handlers) {
1516
- return tryOrPanic(() => handlers.err(this.error), "match err handler threw");
1517
- }
1518
- unwrap(message) {
1519
- return panic(message ?? `Unwrap called on Err: ${String(this.error)}`, this.error);
1520
- }
1521
- unwrapOr(fallback) {
1522
- return fallback;
1523
- }
1524
- tap(_fn) {
1525
- return this;
1526
- }
1527
- tapAsync(_fn) {
1528
- return Promise.resolve(this);
1529
- }
1530
- *[Symbol.iterator]() {
1531
- yield this;
1532
- return panic("Unreachable: Err yielded in Result.gen but generator continued", this.error);
1533
- }
1534
- };
1535
- function ok(value) {
1536
- return new Ok(value);
1537
- }
1538
- var isOk = (result) => {
1539
- return result.status === "ok";
1540
- };
1541
- var err = (error) => new Err(error);
1542
- var isError = (result) => {
1543
- return result.status === "error";
1544
- };
1545
- var tryFn = (options, config) => {
1546
- const execute = () => {
1547
- if (typeof options === "function")
1548
- try {
1549
- return ok(options());
1550
- } catch (cause) {
1551
- return err(new UnhandledException({ cause }));
1552
- }
1553
- try {
1554
- return ok(options.try());
1555
- } catch (originalCause) {
1556
- try {
1557
- return err(options.catch(originalCause));
1558
- } catch (catchHandlerError) {
1559
- throw panic("Result.try catch handler threw", catchHandlerError);
1560
- }
1561
- }
1562
- };
1563
- const times = config?.retry?.times ?? 0;
1564
- let result = execute();
1565
- for (let retry = 0;retry < times && result.status === "error"; retry++)
1566
- result = execute();
1567
- return result;
1568
- };
1569
- var tryPromise = async (options, config) => {
1570
- const execute = async () => {
1571
- if (typeof options === "function")
1572
- try {
1573
- return ok(await options());
1574
- } catch (cause) {
1575
- return err(new UnhandledException({ cause }));
1576
- }
1577
- try {
1578
- return ok(await options.try());
1579
- } catch (originalCause) {
1580
- try {
1581
- return err(await options.catch(originalCause));
1582
- } catch (catchHandlerError) {
1583
- throw panic("Result.tryPromise catch handler threw", catchHandlerError);
1584
- }
1585
- }
1586
- };
1587
- const retry = config?.retry;
1588
- if (!retry)
1589
- return execute();
1590
- const getDelay = (retryAttempt) => {
1591
- switch (retry.backoff) {
1592
- case "constant":
1593
- return retry.delayMs;
1594
- case "linear":
1595
- return retry.delayMs * (retryAttempt + 1);
1596
- case "exponential":
1597
- return retry.delayMs * 2 ** retryAttempt;
1598
- }
1599
- };
1600
- const sleep = (ms) => new Promise((resolve2) => setTimeout(resolve2, ms));
1601
- let result = await execute();
1602
- const shouldRetryFn = retry.shouldRetry ?? (() => true);
1603
- for (let attempt = 0;attempt < retry.times; attempt++) {
1604
- if (result.status !== "error")
1605
- break;
1606
- const error = result.error;
1607
- if (!tryOrPanic(() => shouldRetryFn(error), "shouldRetry predicate threw"))
1608
- break;
1609
- await sleep(getDelay(attempt));
1610
- result = await execute();
1611
- }
1612
- return result;
1613
- };
1614
- var map = dual(2, (result, fn) => {
1615
- return result.map(fn);
1616
- });
1617
- var mapError = dual(2, (result, fn) => {
1618
- return result.mapError(fn);
1619
- });
1620
- var andThen = dual(2, (result, fn) => {
1621
- return result.andThen(fn);
1622
- });
1623
- var andThenAsync = dual(2, (result, fn) => {
1624
- return result.andThenAsync(fn);
1625
- });
1626
- var match = dual(2, (result, handlers) => {
1627
- return result.match(handlers);
1628
- });
1629
- var tap = dual(2, (result, fn) => {
1630
- return result.tap(fn);
1631
- });
1632
- var tapAsync = dual(2, (result, fn) => {
1633
- return result.tapAsync(fn);
1634
- });
1635
- var unwrap = (result, message) => {
1636
- return result.unwrap(message);
1637
- };
1638
- function assertIsResult(value) {
1639
- if (value !== null && typeof value === "object" && "status" in value && (value.status === "ok" || value.status === "error"))
1640
- return;
1641
- return panic("Result.gen body must return Result.ok() or Result.err(), got: " + (value === null ? "null" : typeof value === "object" ? JSON.stringify(value) : String(value)));
1642
- }
1643
- var unwrapOr = dual(2, (result, fallback) => {
1644
- return result.unwrapOr(fallback);
1645
- });
1646
- var gen = (body, thisArg) => {
1647
- const iterator = body.call(thisArg);
1648
- if (Symbol.asyncIterator in iterator)
1649
- return (async () => {
1650
- const asyncIter = iterator;
1651
- let state$1;
1652
- try {
1653
- state$1 = await asyncIter.next();
1654
- } catch (cause) {
1655
- throw panic("generator body threw", cause);
1656
- }
1657
- assertIsResult(state$1.value);
1658
- if (!state$1.done)
1659
- try {
1660
- await asyncIter.return?.(undefined);
1661
- } catch (cause) {
1662
- throw panic("generator cleanup threw", cause);
1663
- }
1664
- return state$1.value;
1665
- })();
1666
- const syncIter = iterator;
1667
- let state;
1668
- try {
1669
- state = syncIter.next();
1670
- } catch (cause) {
1671
- throw panic("generator body threw", cause);
1672
- }
1673
- assertIsResult(state.value);
1674
- if (!state.done)
1675
- try {
1676
- syncIter.return?.(undefined);
1677
- } catch (cause) {
1678
- throw panic("generator cleanup threw", cause);
1679
- }
1680
- return state.value;
1681
- };
1682
- async function* resultAwait(promise) {
1683
- return yield* await promise;
1684
- }
1685
- function isSerializedResult(obj) {
1686
- return obj !== null && typeof obj === "object" && "status" in obj && (obj.status === "ok" && ("value" in obj) || obj.status === "error" && ("error" in obj));
1687
- }
1688
- var serialize = (result) => {
1689
- return result.status === "ok" ? {
1690
- status: "ok",
1691
- value: result.value
1692
- } : {
1693
- status: "error",
1694
- error: result.error
1695
- };
1696
- };
1697
- var deserialize = (value) => {
1698
- if (isSerializedResult(value))
1699
- return value.status === "ok" ? new Ok(value.value) : new Err(value.error);
1700
- return err(new ResultDeserializationError({ value }));
1701
- };
1702
- var hydrate = (value) => {
1703
- return deserialize(value);
1704
- };
1705
- var partition = (results) => {
1706
- const oks = [];
1707
- const errs = [];
1708
- for (const r of results)
1709
- if (r.status === "ok")
1710
- oks.push(r.value);
1711
- else
1712
- errs.push(r.error);
1713
- return [oks, errs];
1714
- };
1715
- var flatten = (result) => {
1716
- if (result.status === "ok")
1717
- return result.value;
1718
- return result;
1719
- };
1720
- var Result2 = {
1721
- ok,
1722
- isOk,
1723
- err,
1724
- isError,
1725
- try: tryFn,
1726
- tryPromise,
1727
- map,
1728
- mapError,
1729
- andThen,
1730
- andThenAsync,
1731
- match,
1732
- tap,
1733
- tapAsync,
1734
- unwrap,
1735
- unwrapOr,
1736
- gen,
1737
- await: resultAwait,
1738
- serialize,
1739
- deserialize,
1740
- hydrate,
1741
- partition,
1742
- flatten
1743
- };
1744
-
1745
- class PackageJsonReadError extends TaggedError2("PackageJsonReadError")() {
1746
- }
1747
-
1748
- class LoadGeneratedMetadataError extends TaggedError2("LoadGeneratedMetadataError")() {
1749
- }
1750
- function stripScope(name) {
1751
- const idx = name.lastIndexOf("/");
1752
- return idx >= 0 ? name.slice(idx + 1) : name;
1753
- }
1754
- async function resolveCliInfo(options = {}) {
1755
- if (options.commandName && options.executable) {
1756
- return { commandName: options.commandName, executable: options.executable };
1757
- }
1758
- const packageJsonResult = await readProjectPackageJson();
1759
- const pkg = Result2.isOk(packageJsonResult) ? packageJsonResult.value : null;
1760
- const pkgName = typeof pkg?.name === "string" ? pkg.name : undefined;
1761
- const pkgNameStripped = pkgName ? stripScope(pkgName) : undefined;
1762
- let inferredCommandName;
1763
- const bin = pkg?.bin;
1764
- if (typeof bin === "string") {
1765
- inferredCommandName = pkgNameStripped;
1766
- } else if (bin && typeof bin === "object") {
1767
- const keys = Object.keys(bin);
1768
- if (pkgNameStripped && keys.includes(pkgNameStripped))
1769
- inferredCommandName = pkgNameStripped;
1770
- else
1771
- inferredCommandName = keys[0];
1772
- if (inferredCommandName)
1773
- inferredCommandName = stripScope(inferredCommandName);
1774
- } else {
1775
- inferredCommandName = pkgNameStripped;
1776
- }
1777
- const commandName = options.commandName ?? inferredCommandName ?? "cli";
1778
- const executable = options.executable ?? commandName;
1779
- return { commandName, executable };
1780
- }
1781
- async function loadGeneratedMetadata(options = {}) {
1782
- const generatedPath = options.generatedPath ?? ".bunli/commands.gen.ts";
1783
- const absolute = resolve(process.cwd(), generatedPath);
1784
- const url = pathToFileURL(absolute).href;
1785
- return await Result2.tryPromise({
1786
- try: async () => {
1787
- const mod = await import(url);
1788
- const list = mod.generated?.list?.() ?? [];
1789
- return { commands: list.map((i) => i.metadata) };
1790
- },
1791
- catch: (cause) => new LoadGeneratedMetadataError({
1792
- generatedPath,
1793
- message: `Could not load command metadata from ${generatedPath}. Make sure it exists (run "bunli generate").`,
1794
- cause
1795
- })
1796
- });
1797
- }
1798
- async function readProjectPackageJson() {
1799
- return Result2.tryPromise({
1800
- try: async () => {
1801
- const pkgPath = resolve(process.cwd(), "package.json");
1802
- const pkgContent = await readFile(pkgPath, "utf-8");
1803
- const parsed = JSON.parse(pkgContent);
1804
- if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
1805
- throw new Error("package.json must be a JSON object");
1806
- }
1807
- return parsed;
1808
- },
1809
- catch: (cause) => new PackageJsonReadError({
1810
- message: "Could not read project package.json",
1811
- cause
1812
- })
1813
- });
1814
- }
1815
- function canonicalCommandPath(name) {
1816
- return name.replace(/\s+/g, "/").replace(/\/+/g, "/").replace(/^\/+|\/+$/g, "").trim();
1817
- }
1818
- function resolveNestedCommandName(parentPath, rawName) {
1819
- const child = canonicalCommandPath(rawName);
1820
- if (!child)
1821
- return parentPath ?? "";
1822
- if (!parentPath)
1823
- return child;
1824
- if (!child.includes("/")) {
1825
- return `${parentPath}/${child}`;
1826
- }
1827
- if (child === parentPath || child.startsWith(`${parentPath}/`)) {
1828
- return child;
1829
- }
1830
- return child;
1831
- }
1832
- function flattenCommandTree(commands) {
1833
- const flattened = [];
1834
- const walk = (meta, parentPath) => {
1835
- const resolvedName = resolveNestedCommandName(parentPath, meta.name);
1836
- if (!resolvedName)
1837
- return;
1838
- flattened.push({
1839
- ...meta,
1840
- name: resolvedName
1841
- });
1842
- for (const nested of meta.commands ?? []) {
1843
- walk(nested, resolvedName);
1844
- }
1845
- };
1846
- for (const meta of commands) {
1847
- walk(meta);
1848
- }
1849
- return flattened;
1850
- }
1851
- function normalizeCommandPath(name) {
1852
- return name.replace(/\//g, " ").trim();
1853
- }
1854
- function isBooleanOption(meta) {
1855
- const t2 = meta.type.toLowerCase();
1856
- return t2.includes("boolean") || t2.includes("bool");
1857
- }
1858
- function addGlobalFlags(cmd) {
1859
- for (const [name, flag] of Object.entries(GLOBAL_FLAGS)) {
1860
- const desc = flag.description ?? "";
1861
- const short = "short" in flag ? flag.short : undefined;
1862
- const handler = createGlobalFlagHandler(name);
1863
- if (handler) {
1864
- if (short)
1865
- cmd.option(name, desc, handler, short);
1866
- else
1867
- cmd.option(name, desc, handler);
1868
- continue;
1869
- }
1870
- if (short)
1871
- cmd.option(name, desc, short);
1872
- else
1873
- cmd.option(name, desc);
1874
- }
1875
- }
1876
- function createGlobalFlagHandler(name) {
1877
- const enumValues = name === "format" ? ["json", "yaml", "md", "toon"] : name === "image-mode" ? ["off", "auto", "on"] : undefined;
1878
- if (!enumValues)
1879
- return;
1880
- return (complete) => {
1881
- for (const value of enumValues)
1882
- complete(value, "");
1883
- };
1884
- }
1885
- function addOption(cmd, name, meta) {
1886
- const desc = meta.description ?? "";
1887
- const short = meta.short;
1888
- if (isBooleanOption(meta)) {
1889
- if (short)
1890
- cmd.option(name, desc, short);
1891
- else
1892
- cmd.option(name, desc);
1893
- return;
1894
- }
1895
- const enumValues = meta.enumValues;
1896
- const literalValue = meta.literalValue;
1897
- const handler = (complete) => {
1898
- if (enumValues && enumValues.length > 0) {
1899
- for (const v of enumValues)
1900
- complete(String(v), "");
1901
- return;
1902
- }
1903
- if (literalValue !== undefined) {
1904
- complete(String(literalValue), "");
1905
- }
1906
- };
1907
- if (short)
1908
- cmd.option(name, desc, handler, short);
1909
- else
1910
- cmd.option(name, desc, handler);
1911
- }
1912
- function addCommandOptions(cmd, meta) {
1913
- for (const [name, opt] of Object.entries(meta.options ?? {})) {
1914
- addOption(cmd, name, opt);
1915
- }
1916
- }
1917
- function expandAliases(meta, opts) {
1918
- const primary = normalizeCommandPath(meta.name);
1919
- if (!opts.includeAliases || !meta.alias)
1920
- return [primary];
1921
- const aliases = Array.isArray(meta.alias) ? meta.alias : [meta.alias];
1922
- const parts = primary.split(" ").filter(Boolean);
1923
- const parent = parts.slice(0, -1);
1924
- const expanded = [primary];
1925
- for (const a of aliases) {
1926
- const aliasRaw = String(a).trim();
1927
- if (!aliasRaw)
1928
- continue;
1929
- if (aliasRaw.includes("/") || aliasRaw.includes(" ")) {
1930
- expanded.push(normalizeCommandPath(aliasRaw));
1931
- continue;
1932
- }
1933
- expanded.push([...parent, aliasRaw].join(" ").trim());
1934
- }
1935
- return expanded;
1936
- }
1937
- function buildRegistry(commands, options = {}) {
1938
- const opts = {
1939
- includeAliases: options.includeAliases ?? true,
1940
- includeGlobalFlags: options.includeGlobalFlags ?? true
1941
- };
1942
- const root = new RootCommand;
1943
- const flattenedCommands = flattenCommandTree(commands);
1944
- const metaByPath = new Map;
1945
- const allPaths = new Set;
1946
- for (const meta of flattenedCommands) {
1947
- for (const path of expandAliases(meta, opts)) {
1948
- metaByPath.set(path, meta);
1949
- const parts = path.split(" ").filter(Boolean);
1950
- for (let i = 1;i <= parts.length; i += 1) {
1951
- allPaths.add(parts.slice(0, i).join(" "));
1952
- }
1953
- }
1954
- }
1955
- const sortedPaths = Array.from(allPaths).sort((a, b) => {
1956
- const al = a.split(" ").length;
1957
- const bl = b.split(" ").length;
1958
- if (al !== bl)
1959
- return al - bl;
1960
- return a.localeCompare(b);
1961
- });
1962
- const tabCommands = new Map;
1963
- for (const path of sortedPaths) {
1964
- const meta = metaByPath.get(path);
1965
- const desc = meta?.description ?? "";
1966
- const cmd = root.command(path, desc);
1967
- tabCommands.set(path, cmd);
1968
- if (opts.includeGlobalFlags)
1969
- addGlobalFlags(cmd);
1970
- if (meta)
1971
- addCommandOptions(cmd, meta);
1972
- }
1973
- if (opts.includeGlobalFlags)
1974
- addGlobalFlags(root);
1975
- return root;
1976
- }
1977
- var SHELLS = ["bash", "zsh", "fish", "powershell"];
1978
- function isShell(value) {
1979
- return SHELLS.includes(value);
1980
- }
1981
-
1982
- class CompletionProtocolError extends TaggedError2("CompletionProtocolError")() {
1983
- }
1984
- function completionsCommand(pluginOptions) {
1985
- return defineCommand({
1986
- name: "completions",
1987
- alias: ["complete"],
1988
- description: "Generate shell completion scripts and handle completion protocol callbacks",
1989
- handler: async ({ runtime, colors }) => {
1990
- const argv = runtime.args;
1991
- const invokedCommand = runtime.command.split(/\s+/).at(-1) ?? "completions";
1992
- const isProtocolCommand = invokedCommand === "complete";
1993
- if (!isProtocolCommand) {
1994
- const first = argv[0];
1995
- if (argv.length === 1 && typeof first === "string" && isShell(first)) {
1996
- const shell = first;
1997
- const { commandName, executable } = await resolveCliInfo(pluginOptions);
1998
- const root = new RootCommand;
1999
- root.setup(commandName, executable, shell);
2000
- return;
2001
- }
2002
- console.error(colors.red("Missing or invalid shell name for completions script generation."));
2003
- console.error(colors.dim("Usage: <cli> completions <bash|zsh|fish|powershell>"));
2004
- console.error(colors.dim("Protocol callback form: <cli> complete -- <args...>"));
2005
- return;
2006
- }
2007
- const metadataResult = await loadGeneratedMetadata(pluginOptions);
2008
- if (Result2.isError(metadataResult)) {
2009
- console.log(":1");
2010
- if (process.env.BUNLI_DEBUG_COMPLETIONS) {
2011
- console.error(colors.red(metadataResult.error.message));
2012
- }
2013
- return;
2014
- }
2015
- const parseResult = Result2.try({
2016
- try: () => {
2017
- const root = buildRegistry(metadataResult.value.commands, {
2018
- includeAliases: pluginOptions.includeAliases,
2019
- includeGlobalFlags: pluginOptions.includeGlobalFlags
2020
- });
2021
- root.parse(argv);
2022
- },
2023
- catch: (cause) => new CompletionProtocolError({
2024
- message: "Completion registry failed to parse protocol arguments.",
2025
- cause
2026
- })
2027
- });
2028
- if (Result2.isError(parseResult)) {
2029
- console.log(":1");
2030
- if (process.env.BUNLI_DEBUG_COMPLETIONS) {
2031
- console.error(colors.red(parseResult.error.message));
2032
- }
2033
- }
2034
- }
2035
- });
2036
- }
2037
- var completionsPlugin = createPlugin((options = {}) => ({
2038
- name: "completions",
2039
- setup(context) {
2040
- const command = completionsCommand(options);
2041
- context.registerCommand(command);
2042
- }
2043
- }));
2044
-
2045
- // ../../node_modules/.bun/@bunli+plugin-config@0.4.4+44deef6f8e4a2f18/node_modules/@bunli/plugin-config/src/index.ts
2046
- import { readFile as readFile2, access } from "fs/promises";
2047
- import { homedir } from "os";
2048
- class ConfigFileNotFoundError extends TaggedError("ConfigFileNotFoundError")() {
2049
- }
2050
-
2051
- class ConfigFileReadError extends TaggedError("ConfigFileReadError")() {
2052
- }
2053
-
2054
- class ConfigFileParseError extends TaggedError("ConfigFileParseError")() {
2055
- }
2056
- var configMergerPlugin = createPlugin((options = {}) => {
2057
- const sources = options.sources || [
2058
- "~/.config/{{name}}/config.json",
2059
- ".{{name}}rc",
2060
- ".{{name}}rc.json",
2061
- ".config/{{name}}.json"
2062
- ];
2063
- return {
2064
- name: "@bunli/plugin-config",
2065
- version: "1.0.0",
2066
- async setup(context) {
2067
- const appName = context.config.name || "bunli";
2068
- const configs = [];
2069
- for (const source of sources) {
2070
- const configPath = source.replace(/^~/, homedir()).replace(/\{\{name\}\}/g, appName);
2071
- const loadedConfig = await readConfigSource(configPath);
2072
- if (Result.isError(loadedConfig)) {
2073
- if (ConfigFileNotFoundError.is(loadedConfig.error)) {
2074
- context.logger.debug(`Config file not found: ${configPath}`);
2075
- continue;
2076
- }
2077
- if (ConfigFileParseError.is(loadedConfig.error)) {
2078
- context.logger.warn(`Failed to parse config file ${configPath}: ${loadedConfig.error.message}`);
2079
- continue;
2080
- }
2081
- context.logger.warn(`Failed to load config file ${configPath}: ${loadedConfig.error.message}`);
2082
- continue;
2083
- }
2084
- configs.push(loadedConfig.value);
2085
- context.logger.debug(`Loaded config from ${configPath}`);
2086
- if (options.stopOnFirst) {
2087
- break;
2088
- }
2089
- }
2090
- if (configs.length > 0) {
2091
- let merged;
2092
- if (options.mergeStrategy === "shallow") {
2093
- merged = Object.assign({}, ...configs);
2094
- } else {
2095
- merged = deepMerge(...configs);
2096
- }
2097
- context.updateConfig(merged);
2098
- context.logger.info(`Merged ${configs.length} config file(s)`);
2099
- }
2100
- }
2101
- };
2102
- });
2103
- async function readConfigSource(path) {
2104
- const existsResult = await Result.tryPromise({
2105
- try: async () => {
2106
- await access(path);
2107
- },
2108
- catch: (cause) => new ConfigFileNotFoundError({
2109
- path,
2110
- message: `Config file not found: ${path}`,
2111
- cause
2112
- })
2113
- });
2114
- if (Result.isError(existsResult)) {
2115
- return existsResult;
2116
- }
2117
- const readResult = await Result.tryPromise({
2118
- try: async () => await readFile2(path, "utf-8"),
2119
- catch: (cause) => new ConfigFileReadError({
2120
- path,
2121
- message: `Unable to read config file: ${path}`,
2122
- cause
2123
- })
2124
- });
2125
- if (Result.isError(readResult)) {
2126
- return readResult;
2127
- }
2128
- return Result.try({
2129
- try: () => {
2130
- const parsed = JSON.parse(readResult.value);
2131
- if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
2132
- throw new Error("Config file must contain a JSON object");
2133
- }
2134
- return parsed;
2135
- },
2136
- catch: (cause) => new ConfigFileParseError({
2137
- path,
2138
- message: `Invalid JSON in config file: ${path}`,
2139
- cause
2140
- })
2141
- });
2142
- }
2143
-
2144
- // ../../node_modules/.bun/@bunli+plugin-skills@0.1.0+44deef6f8e4a2f18/node_modules/@bunli/plugin-skills/src/plugin.ts
2145
- var skillsPlugin = createPlugin((options = {}) => ({
2146
- name: "skills",
2147
- setup(context) {
2148
- const skillsGroup = defineGroup({
2149
- name: "skills",
2150
- description: "Manage agent skill files",
2151
- commands: [
2152
- defineCommand({
2153
- name: "sync",
2154
- description: "Generate and install skill files for detected agents",
2155
- options: {
2156
- global: {
2157
- schema: exports_external.boolean().default(true),
2158
- description: "Install globally (default) or project-local",
2159
- argumentKind: "flag"
2160
- },
2161
- force: {
2162
- schema: exports_external.boolean().default(false),
2163
- short: "f",
2164
- description: "Force regeneration even if up to date",
2165
- argumentKind: "flag"
2166
- }
2167
- },
2168
- async handler({ flags, colors, output }) {
2169
- const typedFlags = flags;
2170
- const { syncSkills } = await import("./sync-k2k8svyc.js");
2171
- const { detectAgents, builtinAgents } = await import("./agents-91fpdyyt.js");
2172
- const allAgents = options.agents ? [...builtinAgents, ...options.agents] : builtinAgents;
2173
- const detected = detectAgents(allAgents);
2174
- const commands = context.store.get("_skillsCommands");
2175
- if (!commands || commands.size === 0) {
2176
- console.log(colors.yellow("No commands registered. Nothing to sync."));
2177
- return;
2178
- }
2179
- const cliName = context.store.get("_skillsCliName") || "cli";
2180
- const result = await syncSkills(cliName, commands, {
2181
- global: typedFlags.global,
2182
- force: typedFlags.force,
2183
- description: options.description,
2184
- agents: detected
2185
- });
2186
- if (!result.updated && !typedFlags.force) {
2187
- console.log(colors.dim("Skills are up to date."));
2188
- output({ updated: false, agents: detected.map((a) => a.name) });
2189
- return;
2190
- }
2191
- console.log(colors.green(`Synced skills to ${result.paths.length} location(s)`));
2192
- for (const install of result.agents) {
2193
- console.log(colors.dim(` ${install.agent}: ${install.mode} \u2192 ${install.path}`));
2194
- }
2195
- output({
2196
- updated: true,
2197
- paths: result.paths,
2198
- agents: result.agents.map((a) => ({
2199
- agent: a.agent,
2200
- path: a.path,
2201
- mode: a.mode
2202
- }))
2203
- });
2204
- }
2205
- }),
2206
- defineCommand({
2207
- name: "list",
2208
- description: "List detected agents on this system",
2209
- async handler({ colors, output }) {
2210
- const { detectAgents, builtinAgents } = await import("./agents-91fpdyyt.js");
2211
- const allAgents = options.agents ? [...builtinAgents, ...options.agents] : builtinAgents;
2212
- const detected = detectAgents(allAgents);
2213
- if (detected.length === 0) {
2214
- console.log(colors.dim("No agents detected."));
2215
- output({ agents: [] });
2216
- return;
2217
- }
2218
- console.log(`Detected ${detected.length} agent(s):
2219
- `);
2220
- for (const agent of detected) {
2221
- const tag = agent.universal ? colors.dim(" (universal)") : "";
2222
- console.log(` ${colors.bold(agent.name)}${tag}`);
2223
- console.log(colors.dim(` ${agent.projectSkillsDir}`));
2224
- }
2225
- output({
2226
- agents: detected.map((a) => ({
2227
- name: a.name,
2228
- universal: a.universal,
2229
- projectSkillsDir: a.projectSkillsDir,
2230
- globalSkillsDir: a.globalSkillsDir
2231
- }))
2232
- });
2233
- }
2234
- })
2235
- ]
2236
- });
2237
- context.registerCommand(skillsGroup);
2238
- }
2239
- }));
2240
- // bunli.config.ts
2241
- var bunliConfig = defineConfig({
2242
- name: package_default.name,
2243
- version: package_default.version,
2244
- description: package_default.description,
2245
- commands: {
2246
- entry: "./src/cli.ts",
2247
- directory: "./src/commands",
2248
- generateReport: true
2249
- },
2250
- build: {
2251
- entry: "./src/cli.ts",
2252
- outdir: "./dist-bunli",
2253
- sourcemap: true
2254
- },
2255
- test: {
2256
- pattern: ["tests/*.test.ts"],
2257
- coverage: false,
2258
- watch: false
2259
- },
2260
- tui: {
2261
- renderer: {
2262
- bufferMode: "alternate"
2263
- }
2264
- }
2265
- });
2266
-
2267
- // src/command-contract.ts
2268
- import path from "path";
2269
- var SHARED_OPTION_PARSER = buildCommandOptionParser(ALL_COMMAND_OPTION_METADATA);
2270
- var STRING_OPTION_NAMES_BY_GROUP = Object.fromEntries(Object.entries(COMMAND_OPTION_METADATA_BY_GROUP).map(([groupName, metadata]) => [
2271
- groupName,
2272
- new Set(collectOptionNamesByType(metadata, "string"))
2273
- ]));
2274
- var STRING_OPTION_NAMES_BY_COMMAND = Object.fromEntries(WP_TYPIA_RESERVED_TOP_LEVEL_COMMAND_NAMES.map((commandName) => [
2275
- commandName,
2276
- new Set(WP_TYPIA_COMMAND_OPTION_GROUP_NAMES_BY_TOP_LEVEL_COMMAND[commandName].flatMap((groupName) => Array.from(STRING_OPTION_NAMES_BY_GROUP[groupName])))
2277
- ]));
2278
- var GLOBAL_STRING_OPTION_NAMES = new Set(collectOptionNamesByType(GLOBAL_OPTION_METADATA, "string"));
2279
- var SHORT_OPTION_NAMES_WITH_VALUES = new Set([...SHARED_OPTION_PARSER.shortFlagMap.entries()].filter(([, option]) => option.type === "string").map(([short]) => short));
2280
- function isReservedTopLevelCommandName(value) {
2281
- return WP_TYPIA_RESERVED_TOP_LEVEL_COMMAND_NAMES.includes(value);
2282
- }
2283
- function assertStringOptionValues(argv) {
2284
- const firstPositionalIndex = findFirstPositionalIndex(argv, COMMAND_ROUTING_METADATA);
2285
- if (firstPositionalIndex === -1) {
2286
- return;
2287
- }
2288
- const commandName = argv[firstPositionalIndex];
2289
- const stringOptionNames = new Set(GLOBAL_STRING_OPTION_NAMES);
2290
- for (const optionName of STRING_OPTION_NAMES_BY_COMMAND[commandName] ?? []) {
2291
- stringOptionNames.add(optionName);
2292
- }
2293
- for (let index = firstPositionalIndex + 1;index < argv.length; index += 1) {
2294
- const arg = argv[index];
2295
- if (arg === "--") {
2296
- break;
2297
- }
2298
- if (arg.length === 2 && arg.startsWith("-")) {
2299
- if (SHORT_OPTION_NAMES_WITH_VALUES.has(arg.slice(1))) {
2300
- const next2 = argv[index + 1];
2301
- if (!next2 || next2.startsWith("-")) {
2302
- throw createMissingOptionValueError(arg);
2303
- }
2304
- index += 1;
2305
- }
2306
- continue;
2307
- }
2308
- if (!arg.startsWith("--")) {
2309
- continue;
2310
- }
2311
- const [rawName, inlineValue] = arg.slice(2).split("=", 2);
2312
- if (!stringOptionNames.has(rawName)) {
2313
- continue;
2314
- }
2315
- if (arg.includes("=")) {
2316
- if (!inlineValue) {
2317
- throw createMissingOptionValueError(`--${rawName}`);
2318
- }
2319
- continue;
2320
- }
2321
- const next = argv[index + 1];
2322
- if (!next || next.startsWith("-")) {
2323
- throw createMissingOptionValueError(`--${rawName}`);
2324
- }
2325
- index += 1;
2326
- }
2327
- }
2328
- function isWindowsDrivePath(value) {
2329
- return /^[A-Za-z]:([\\/]|$)/.test(value);
2330
- }
2331
- function looksLikeStructuredProjectInput(value) {
2332
- if (value.includes("#")) {
2333
- return true;
2334
- }
2335
- if (!isWindowsDrivePath(value) && /^[A-Za-z][A-Za-z0-9+.-]*:/u.test(value)) {
2336
- return true;
2337
- }
2338
- return value.startsWith("@") && value.includes("/");
2339
- }
2340
- function assertPositionalAliasProjectDir(projectDir) {
2341
- const normalizedProjectDir = path.normalize(projectDir).replace(/[\\/]+$/u, "") || path.normalize(projectDir);
2342
- if (normalizedProjectDir === "." || normalizedProjectDir === "..") {
2343
- throw createCliDiagnosticCodeError(CLI_DIAGNOSTIC_CODES.INVALID_ARGUMENT, `The positional alias does not scaffold into \`${projectDir}\`. Use \`${WP_TYPIA_CANONICAL_CREATE_USAGE}\` with an explicit child directory instead.`);
2344
- }
2345
- if (looksLikeStructuredProjectInput(projectDir)) {
2346
- throw createCliDiagnosticCodeError(CLI_DIAGNOSTIC_CODES.INVALID_ARGUMENT, `The positional alias only accepts unambiguous local project directories. Use \`${WP_TYPIA_CANONICAL_CREATE_USAGE}\` for \`${projectDir}\`.`);
2347
- }
2348
- }
2349
- function normalizeWpTypiaArgv(argv) {
2350
- const positionalIndexes = collectPositionalIndexes(argv, COMMAND_ROUTING_METADATA);
2351
- const firstPositionalIndex = positionalIndexes[0] ?? -1;
2352
- if (firstPositionalIndex === -1) {
2353
- return argv;
2354
- }
2355
- const firstPositional = argv[firstPositionalIndex];
2356
- if (!firstPositional) {
2357
- return argv;
2358
- }
2359
- if (firstPositional === "migrations") {
2360
- throw createCliDiagnosticCodeError(CLI_DIAGNOSTIC_CODES.INVALID_ARGUMENT, "`wp-typia migrations` was removed in favor of `wp-typia migrate`. Use `wp-typia migrate <subcommand>` instead.");
2361
- }
2362
- if (isReservedTopLevelCommandName(firstPositional)) {
2363
- assertStringOptionValues(argv);
2364
- return argv;
2365
- }
2366
- if (positionalIndexes.length > 1) {
2367
- const extraPositionals = positionalIndexes.slice(1).map((index) => argv[index]).filter((value) => typeof value === "string" && value.length > 0);
2368
- throw createCliDiagnosticCodeError(CLI_DIAGNOSTIC_CODES.INVALID_ARGUMENT, `The positional alias only accepts a single project directory. Use \`${WP_TYPIA_CANONICAL_CREATE_USAGE}\` for scaffold invocations with additional positional arguments, or check the command spelling if you meant another top-level command. Extra positional arguments: ${extraPositionals.map((value) => `\`${value}\``).join(", ")}.`);
2369
- }
2370
- assertPositionalAliasProjectDir(firstPositional);
2371
- const normalizedArgv = [
2372
- ...argv.slice(0, firstPositionalIndex),
2373
- "create",
2374
- ...argv.slice(firstPositionalIndex)
2375
- ];
2376
- assertStringOptionValues(normalizedArgv);
2377
- return normalizedArgv;
2378
- }
2379
-
2380
- // src/config-override.ts
2381
- var GLOBAL_OPTION_PARSER = buildCommandOptionParser(GLOBAL_OPTION_METADATA);
2382
- function extractWpTypiaConfigOverride(argv) {
2383
- const { argv: nextArgv, flags } = extractKnownOptionValuesFromArgv(argv, {
2384
- optionNames: ["config"],
2385
- parser: GLOBAL_OPTION_PARSER
2386
- });
2387
- return {
2388
- argv: nextArgv,
2389
- configOverridePath: typeof flags.config === "string" ? flags.config : undefined
2390
- };
2391
- }
2392
-
2393
- // src/plugins/wp-typia-skills.ts
2394
- function createWpTypiaSkillsMetadataPlugin(commands) {
2395
- return {
2396
- name: "wp-typia-skills-metadata",
2397
- setup(context) {
2398
- context.store.set("_skillsCommands", new Map(commands.map((command) => [command.name, command])));
2399
- context.store.set("_skillsCliName", "wp-typia");
2400
- }
2401
- };
2402
- }
2403
-
2404
- // src/plugins/wp-typia-user-config.ts
2405
- var wpTypiaUserConfigPlugin = createPlugin((options = {}) => {
2406
- let resolvedConfig = {};
2407
- return {
2408
- name: "wp-typia-user-config",
2409
- async setup(context) {
2410
- resolvedConfig = await loadWpTypiaUserConfig(context.paths.cwd);
2411
- if (options.overrideSource) {
2412
- const overrideConfig = await loadWpTypiaUserConfigFromSource(context.paths.cwd, options.overrideSource);
2413
- resolvedConfig = mergeWpTypiaUserConfig(resolvedConfig, overrideConfig);
2414
- }
2415
- },
2416
- beforeCommand(context) {
2417
- context.store.wpTypiaUserConfig = resolvedConfig;
2418
- }
2419
- };
2420
- });
2421
-
2422
- // src/cli.ts
2423
- function applyStandaloneSupportLayoutEnv() {
2424
- if (process.env.WP_TYPIA_PROJECT_TOOLS_PACKAGE_ROOT) {
2425
- return;
2426
- }
2427
- const executableDir = path2.dirname(process.execPath);
2428
- const candidateRoots = [
2429
- path2.join(executableDir, ".wp-typia", "share", "wp-typia-project-tools"),
2430
- path2.resolve(executableDir, "..", ".wp-typia", "share", "wp-typia-project-tools")
2431
- ];
2432
- for (const candidateRoot of candidateRoots) {
2433
- if (fs.existsSync(path2.join(candidateRoot, "package.json"))) {
2434
- process.env.WP_TYPIA_PROJECT_TOOLS_PACKAGE_ROOT = candidateRoot;
2435
- return;
2436
- }
2437
- }
2438
- }
2439
- function resolveGeneratedMetadataPath(moduleUrl) {
2440
- const candidates = [
2441
- new URL("./.bunli/commands.gen.js", moduleUrl),
2442
- new URL("../lib/.bunli/commands.gen.js", moduleUrl),
2443
- new URL("../.bunli/commands.gen.ts", moduleUrl)
2444
- ];
2445
- for (const candidate of candidates) {
2446
- const candidatePath = fileURLToPath(candidate);
2447
- if (fs.existsSync(candidatePath)) {
2448
- return candidatePath;
2449
- }
2450
- }
2451
- return fileURLToPath(new URL("../.bunli/commands.gen.ts", moduleUrl));
2452
- }
2453
- async function formatCliError(error) {
2454
- try {
2455
- const { formatCliDiagnosticError } = await import("./cli-diagnostics-10drxh34.js");
2456
- return formatCliDiagnosticError(error);
2457
- } catch {
2458
- return error instanceof Error ? error.message : String(error);
2459
- }
2460
- }
2461
- async function createWpTypiaCli(options = {}) {
2462
- applyStandaloneSupportLayoutEnv();
2463
- const { wpTypiaCommands } = await import("./command-list-y3g7e9rb.js");
2464
- const cli = await createCLI({
2465
- ...bunliConfig,
2466
- description: package_default.description,
2467
- name: package_default.name,
2468
- plugins: [
2469
- configMergerPlugin({
2470
- mergeStrategy: "deep",
2471
- sources: [...WP_TYPIA_CONFIG_SOURCES]
2472
- }),
2473
- wpTypiaUserConfigPlugin({
2474
- overrideSource: options.configOverridePath
2475
- }),
2476
- aiAgentPlugin({}),
2477
- createWpTypiaSkillsMetadataPlugin(wpTypiaCommands),
2478
- skillsPlugin({
2479
- description: package_default.description
2480
- }),
2481
- completionsPlugin({
2482
- commandName: "wp-typia",
2483
- executable: "wp-typia",
2484
- generatedPath: resolveGeneratedMetadataPath(import.meta.url)
2485
- })
2486
- ],
2487
- version: package_default.version
2488
- });
2489
- for (const command of wpTypiaCommands) {
2490
- cli.command(command);
2491
- }
2492
- return cli;
2493
- }
2494
- async function main(argv = process.argv.slice(2)) {
2495
- const normalizedArgv = normalizeWpTypiaArgv(argv);
2496
- const { argv: cliArgv, configOverridePath } = extractWpTypiaConfigOverride(normalizedArgv);
2497
- validateCliOutputFormatArgv(cliArgv);
2498
- const cli = await createWpTypiaCli({ configOverridePath });
2499
- await cli.run(normalizeCliOutputFormatArgv(cliArgv));
2500
- }
2501
- async function runCliEntrypoint(argv = process.argv.slice(2)) {
2502
- try {
2503
- await main(argv);
2504
- } catch (error) {
2505
- if (writeStructuredCliDiagnosticError(argv, error)) {
2506
- return;
2507
- }
2508
- console.error(`Error: ${await formatCliError(error)}`);
2509
- process.exitCode = 1;
2510
- }
2511
- }
2512
- if (import.meta.main) {
2513
- runCliEntrypoint();
2514
- }
2515
- var cli_default = createWpTypiaCli;
2516
- export {
2517
- runCliEntrypoint,
2518
- main,
2519
- cli_default as default,
2520
- createWpTypiaCli
2521
- };
2522
-
2523
- //# debugId=C2A72BC9D07456AF64756E2164756E21