@outfitter/cli 0.1.0-rc.1 → 0.1.0-rc.3

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 (266) hide show
  1. package/README.md +21 -32
  2. package/dist/actions.js +1 -1
  3. package/dist/borders/index.d.ts +3 -0
  4. package/dist/borders/index.js +13 -0
  5. package/dist/box/index.d.ts +4 -0
  6. package/dist/box/index.js +13 -0
  7. package/dist/cli.d.ts +2 -103
  8. package/dist/cli.js +4 -51
  9. package/dist/colors/index.d.ts +3 -0
  10. package/dist/colors/index.js +18 -0
  11. package/dist/command.d.ts +3 -37
  12. package/dist/command.js +5 -1
  13. package/dist/demo/index.d.ts +78 -0
  14. package/dist/demo/index.js +148 -0
  15. package/dist/demo/registry.d.ts +7 -0
  16. package/dist/demo/registry.js +28 -0
  17. package/dist/demo/renderers/borders.d.ts +7 -0
  18. package/dist/demo/renderers/borders.js +17 -0
  19. package/dist/demo/renderers/box.d.ts +7 -0
  20. package/dist/demo/renderers/box.js +18 -0
  21. package/dist/demo/renderers/colors.d.ts +7 -0
  22. package/dist/demo/renderers/colors.js +18 -0
  23. package/dist/demo/renderers/indicators.d.ts +7 -0
  24. package/dist/demo/renderers/indicators.js +17 -0
  25. package/dist/demo/renderers/list.d.ts +7 -0
  26. package/dist/demo/renderers/list.js +19 -0
  27. package/dist/demo/renderers/markdown.d.ts +7 -0
  28. package/dist/demo/renderers/markdown.js +18 -0
  29. package/dist/demo/renderers/progress.d.ts +7 -0
  30. package/dist/demo/renderers/progress.js +17 -0
  31. package/dist/demo/renderers/spinner.d.ts +7 -0
  32. package/dist/demo/renderers/spinner.js +19 -0
  33. package/dist/demo/renderers/table.d.ts +7 -0
  34. package/dist/demo/renderers/table.js +19 -0
  35. package/dist/demo/renderers/text.d.ts +7 -0
  36. package/dist/demo/renderers/text.js +16 -0
  37. package/dist/demo/renderers/tree.d.ts +7 -0
  38. package/dist/demo/renderers/tree.js +18 -0
  39. package/dist/demo/section.d.ts +5 -0
  40. package/dist/demo/section.js +23 -0
  41. package/dist/demo/templates.d.ts +4 -0
  42. package/dist/demo/templates.js +10 -0
  43. package/dist/demo/types.d.ts +3 -0
  44. package/dist/demo/types.js +8 -0
  45. package/dist/index.d.ts +5 -607
  46. package/dist/index.js +10 -44
  47. package/dist/input.d.ts +9 -123
  48. package/dist/input.js +2 -3
  49. package/dist/list/index.d.ts +3 -0
  50. package/dist/list/index.js +9 -0
  51. package/dist/output.d.ts +2 -68
  52. package/dist/output.js +4 -150
  53. package/dist/pagination.d.ts +1 -34
  54. package/dist/pagination.js +1 -1
  55. package/dist/preset/full.d.ts +14 -0
  56. package/dist/preset/full.js +41 -0
  57. package/dist/preset/standard.d.ts +11 -0
  58. package/dist/preset/standard.js +30 -0
  59. package/dist/prompt/confirm.d.ts +4 -0
  60. package/dist/prompt/confirm.js +9 -0
  61. package/dist/prompt/group.d.ts +4 -0
  62. package/dist/prompt/group.js +9 -0
  63. package/dist/prompt/index.d.ts +7 -0
  64. package/dist/prompt/index.js +32 -0
  65. package/dist/prompt/select.d.ts +4 -0
  66. package/dist/prompt/select.js +11 -0
  67. package/dist/prompt/text.d.ts +4 -0
  68. package/dist/prompt/text.js +11 -0
  69. package/dist/prompt/types.d.ts +3 -0
  70. package/dist/prompt/types.js +8 -0
  71. package/dist/prompt/validators.d.ts +2 -0
  72. package/dist/prompt/validators.js +8 -0
  73. package/dist/render/borders.d.ts +2 -0
  74. package/dist/render/borders.js +15 -0
  75. package/dist/render/box.d.ts +3 -0
  76. package/dist/render/box.js +23 -0
  77. package/dist/render/colors.d.ts +2 -0
  78. package/dist/render/colors.js +20 -0
  79. package/dist/render/date.d.ts +2 -0
  80. package/dist/render/date.js +12 -0
  81. package/dist/render/format-relative.d.ts +2 -0
  82. package/dist/render/format-relative.js +8 -0
  83. package/dist/render/format.d.ts +2 -0
  84. package/dist/render/format.js +10 -0
  85. package/dist/render/heading.d.ts +3 -0
  86. package/dist/render/heading.js +14 -0
  87. package/dist/render/index.d.ts +32 -0
  88. package/dist/render/index.js +235 -0
  89. package/dist/render/indicators.d.ts +2 -0
  90. package/dist/render/indicators.js +14 -0
  91. package/dist/render/json.d.ts +2 -0
  92. package/dist/render/json.js +10 -0
  93. package/dist/render/layout.d.ts +5 -0
  94. package/dist/render/layout.js +25 -0
  95. package/dist/render/list.d.ts +2 -0
  96. package/dist/render/list.js +8 -0
  97. package/dist/render/markdown.d.ts +2 -0
  98. package/dist/render/markdown.js +10 -0
  99. package/dist/render/progress.d.ts +2 -0
  100. package/dist/render/progress.js +8 -0
  101. package/dist/render/separator.d.ts +3 -0
  102. package/dist/render/separator.js +14 -0
  103. package/dist/render/shapes.d.ts +2 -0
  104. package/dist/render/shapes.js +35 -0
  105. package/dist/render/spinner.d.ts +2 -0
  106. package/dist/render/spinner.js +12 -0
  107. package/dist/render/stack.d.ts +3 -0
  108. package/dist/render/stack.js +38 -0
  109. package/dist/render/table.d.ts +3 -0
  110. package/dist/render/table.js +12 -0
  111. package/dist/render/text.d.ts +2 -0
  112. package/dist/render/text.js +27 -0
  113. package/dist/render/tree.d.ts +2 -0
  114. package/dist/render/tree.js +10 -0
  115. package/dist/render/types.d.ts +2 -0
  116. package/dist/render/types.js +1 -0
  117. package/dist/shared/@outfitter/cli-0ggcy7fa.js +20 -0
  118. package/dist/shared/@outfitter/cli-0psys2vm.js +7 -0
  119. package/dist/shared/@outfitter/cli-1bghjef6.js +352 -0
  120. package/dist/shared/@outfitter/cli-1kwbnt86.d.ts +45 -0
  121. package/dist/shared/@outfitter/cli-2g8bx1aq.d.ts +50 -0
  122. package/dist/shared/@outfitter/cli-33e97cjs.d.ts +42 -0
  123. package/dist/shared/@outfitter/cli-34fqr7bp.js +37 -0
  124. package/dist/shared/@outfitter/cli-3b7ed3rm.d.ts +97 -0
  125. package/dist/shared/@outfitter/cli-3dxmmy4c.d.ts +20 -0
  126. package/dist/shared/@outfitter/cli-3f12z5kf.d.ts +83 -0
  127. package/dist/shared/@outfitter/cli-3hp8qwx3.js +11 -0
  128. package/dist/shared/@outfitter/cli-3t2zaenc.d.ts +59 -0
  129. package/dist/shared/@outfitter/cli-4cb5g831.d.ts +147 -0
  130. package/dist/shared/@outfitter/cli-4w2a1rfy.d.ts +23 -0
  131. package/dist/shared/@outfitter/cli-4x6pqnez.js +20 -0
  132. package/dist/shared/@outfitter/cli-671sxkhj.js +146 -0
  133. package/dist/shared/@outfitter/cli-6bztk73z.d.ts +51 -0
  134. package/dist/shared/@outfitter/cli-6fxffp8k.js +1 -0
  135. package/dist/shared/@outfitter/cli-6j9qynm8.js +118 -0
  136. package/dist/shared/@outfitter/cli-6m988kh0.d.ts +61 -0
  137. package/dist/shared/@outfitter/cli-72kg550t.d.ts +53 -0
  138. package/dist/shared/@outfitter/cli-74ba31gz.js +134 -0
  139. package/dist/shared/@outfitter/cli-7gnrb8cr.js +214 -0
  140. package/dist/shared/@outfitter/cli-7na6p4fs.d.ts +59 -0
  141. package/dist/shared/@outfitter/cli-7nm6edvh.d.ts +17 -0
  142. package/dist/shared/@outfitter/cli-85fg2vr5.js +123 -0
  143. package/dist/shared/@outfitter/cli-8a8xrzhy.js +20 -0
  144. package/dist/shared/@outfitter/cli-8aa1vhdn.d.ts +119 -0
  145. package/dist/shared/@outfitter/cli-8bwaw3pz.js +7 -0
  146. package/dist/shared/@outfitter/cli-8j5k6mr3.js +71 -0
  147. package/dist/shared/@outfitter/cli-8rx4g3s5.d.ts +41 -0
  148. package/dist/shared/@outfitter/cli-8xsmsbbd.d.ts +223 -0
  149. package/dist/shared/@outfitter/cli-96b2p4td.d.ts +56 -0
  150. package/dist/shared/@outfitter/cli-9khk3cbq.d.ts +190 -0
  151. package/dist/shared/@outfitter/cli-9mtjjykw.js +67 -0
  152. package/dist/shared/@outfitter/cli-9nbyj2bt.js +128 -0
  153. package/dist/shared/@outfitter/cli-a4q87517.d.ts +64 -0
  154. package/dist/shared/@outfitter/cli-afhjqmg3.js +63 -0
  155. package/dist/shared/@outfitter/cli-an9j0h80.js +117 -0
  156. package/dist/shared/@outfitter/cli-ay411nbr.js +122 -0
  157. package/dist/shared/@outfitter/cli-b0tzqgnf.d.ts +132 -0
  158. package/dist/shared/@outfitter/cli-b5c2k0d7.js +39 -0
  159. package/dist/shared/@outfitter/cli-b5epywry.js +1 -0
  160. package/dist/shared/@outfitter/cli-bc17qeh2.js +19 -0
  161. package/dist/shared/@outfitter/cli-bcmcaz1b.js +23 -0
  162. package/dist/shared/@outfitter/cli-bf3vma4q.js +61 -0
  163. package/dist/shared/@outfitter/cli-c8q4f71g.js +144 -0
  164. package/dist/shared/@outfitter/cli-c9knfqn5.d.ts +30 -0
  165. package/dist/shared/@outfitter/cli-cf1xexgn.d.ts +53 -0
  166. package/dist/shared/@outfitter/cli-cf2s94s1.d.ts +42 -0
  167. package/dist/shared/@outfitter/cli-cs45xd6q.js +59 -0
  168. package/dist/shared/@outfitter/cli-d7jpshq5.d.ts +128 -0
  169. package/dist/shared/@outfitter/cli-d9ad0rqj.js +75 -0
  170. package/dist/shared/@outfitter/cli-daw296mv.js +61 -0
  171. package/dist/shared/@outfitter/cli-e5ms1y0x.d.ts +91 -0
  172. package/dist/shared/@outfitter/cli-e73v3qqy.d.ts +93 -0
  173. package/dist/shared/@outfitter/cli-efy6jfcj.js +52 -0
  174. package/dist/shared/@outfitter/cli-en6zn6sj.js +1 -0
  175. package/dist/shared/@outfitter/cli-ep2cvtk8.js +48 -0
  176. package/dist/shared/@outfitter/cli-evx7qcp1.d.ts +300 -0
  177. package/dist/shared/@outfitter/cli-f75h8e94.js +7 -0
  178. package/dist/shared/@outfitter/cli-fakncnjp.d.ts +106 -0
  179. package/dist/shared/@outfitter/cli-feb5j90n.js +94 -0
  180. package/dist/shared/@outfitter/cli-h20jc0bs.d.ts +66 -0
  181. package/dist/shared/@outfitter/cli-hnpbqmc8.d.ts +328 -0
  182. package/dist/shared/@outfitter/cli-j19a91ck.js +30 -0
  183. package/dist/shared/@outfitter/cli-j4n8gaf3.js +95 -0
  184. package/dist/shared/@outfitter/cli-jejfypgf.js +85 -0
  185. package/dist/shared/@outfitter/cli-jhcdwvpn.js +135 -0
  186. package/dist/shared/@outfitter/cli-jjemfdta.js +85 -0
  187. package/dist/shared/@outfitter/cli-kc84wmch.js +267 -0
  188. package/dist/shared/@outfitter/cli-ktqme80d.js +7 -0
  189. package/dist/shared/@outfitter/cli-mhamvbty.d.ts +34 -0
  190. package/dist/shared/@outfitter/cli-mq0jp15z.js +1 -0
  191. package/dist/shared/@outfitter/cli-mymyavvj.d.ts +26 -0
  192. package/dist/shared/@outfitter/cli-n17gt1dz.js +19 -0
  193. package/dist/shared/@outfitter/cli-n9dbh0hp.js +51 -0
  194. package/dist/shared/@outfitter/cli-nvvc92c8.js +128 -0
  195. package/dist/shared/@outfitter/cli-p1m5dhrs.js +169 -0
  196. package/dist/shared/@outfitter/cli-p38sfxyk.js +25 -0
  197. package/dist/shared/@outfitter/cli-p3dqm1vd.js +22 -0
  198. package/dist/shared/@outfitter/cli-p9j1phge.js +20 -0
  199. package/dist/shared/@outfitter/cli-pkxmzavm.js +62 -0
  200. package/dist/shared/@outfitter/cli-q8r6jarq.d.ts +24 -0
  201. package/dist/shared/@outfitter/cli-qj83y5wj.d.ts +71 -0
  202. package/dist/shared/@outfitter/cli-qjfc3j11.d.ts +112 -0
  203. package/dist/shared/@outfitter/cli-qp4cbhqr.js +70 -0
  204. package/dist/shared/@outfitter/cli-s0kkx9m1.d.ts +164 -0
  205. package/dist/shared/@outfitter/cli-snxj55n6.js +43 -0
  206. package/dist/shared/@outfitter/cli-swwxvjvm.d.ts +24 -0
  207. package/dist/shared/@outfitter/cli-sx67mmfx.d.ts +98 -0
  208. package/dist/shared/@outfitter/cli-tarpsa8a.js +30 -0
  209. package/dist/shared/@outfitter/cli-thvzhjd1.js +126 -0
  210. package/dist/shared/@outfitter/cli-tqewy503.d.ts +36 -0
  211. package/dist/shared/@outfitter/cli-ttt7r0j7.d.ts +253 -0
  212. package/dist/shared/@outfitter/cli-tvw1xrdj.js +20 -0
  213. package/dist/shared/@outfitter/cli-v1tzwxkt.js +32 -0
  214. package/dist/shared/@outfitter/cli-vd60dj65.js +1 -0
  215. package/dist/shared/@outfitter/cli-vp88gxev.js +279 -0
  216. package/dist/shared/@outfitter/cli-vstbkzky.d.ts +74 -0
  217. package/dist/shared/@outfitter/cli-vtg0sqk2.d.ts +54 -0
  218. package/dist/shared/@outfitter/cli-w5y3xepp.js +20 -0
  219. package/dist/shared/@outfitter/cli-x4cavvc0.js +1 -0
  220. package/dist/shared/@outfitter/cli-xep6v2c0.js +52 -0
  221. package/dist/shared/@outfitter/cli-xg5y5fhk.js +86 -0
  222. package/dist/shared/@outfitter/cli-xsaheemc.d.ts +248 -0
  223. package/dist/shared/@outfitter/cli-xvqtqjxk.js +82 -0
  224. package/dist/shared/@outfitter/cli-y25tt8nc.d.ts +48 -0
  225. package/dist/shared/@outfitter/cli-zact3325.js +152 -0
  226. package/dist/shared/@outfitter/cli-zx598p8q.d.ts +26 -0
  227. package/dist/streaming/ansi.d.ts +2 -0
  228. package/dist/streaming/ansi.js +8 -0
  229. package/dist/streaming/index.d.ts +4 -0
  230. package/dist/streaming/index.js +17 -0
  231. package/dist/streaming/spinner.d.ts +3 -0
  232. package/dist/streaming/spinner.js +10 -0
  233. package/dist/streaming/writer.d.ts +2 -0
  234. package/dist/streaming/writer.js +9 -0
  235. package/dist/table/index.d.ts +4 -0
  236. package/dist/table/index.js +13 -0
  237. package/dist/terminal/detection.d.ts +2 -0
  238. package/dist/terminal/detection.js +23 -0
  239. package/dist/terminal/index.d.ts +2 -0
  240. package/dist/terminal/index.js +24 -0
  241. package/dist/theme/context.d.ts +9 -0
  242. package/dist/theme/context.js +14 -0
  243. package/dist/theme/create.d.ts +8 -0
  244. package/dist/theme/create.js +12 -0
  245. package/dist/theme/index.d.ts +17 -0
  246. package/dist/theme/index.js +42 -0
  247. package/dist/theme/presets/bold.d.ts +8 -0
  248. package/dist/theme/presets/bold.js +12 -0
  249. package/dist/theme/presets/default.d.ts +8 -0
  250. package/dist/theme/presets/default.js +11 -0
  251. package/dist/theme/presets/index.d.ts +12 -0
  252. package/dist/theme/presets/index.js +24 -0
  253. package/dist/theme/presets/minimal.d.ts +8 -0
  254. package/dist/theme/presets/minimal.js +12 -0
  255. package/dist/theme/presets/rounded.d.ts +8 -0
  256. package/dist/theme/presets/rounded.js +12 -0
  257. package/dist/theme/resolve.d.ts +8 -0
  258. package/dist/theme/resolve.js +11 -0
  259. package/dist/theme/types.d.ts +7 -0
  260. package/dist/theme/types.js +1 -0
  261. package/dist/tree/index.d.ts +3 -0
  262. package/dist/tree/index.js +11 -0
  263. package/dist/types.d.ts +1 -252
  264. package/dist/types.js +1 -1
  265. package/package.json +228 -20
  266. package/dist/shared/@outfitter/cli-4yy82cmp.js +0 -20
@@ -0,0 +1,253 @@
1
+ import { Command } from "commander";
2
+ import { CancelledError, ErrorCategory, ValidationError } from "@outfitter/contracts";
3
+ import { Result } from "better-result";
4
+ /**
5
+ * Configuration for creating a CLI instance.
6
+ *
7
+ * @example
8
+ * ```typescript
9
+ * const config: CLIConfig = {
10
+ * name: "waymark",
11
+ * version: "1.0.0",
12
+ * description: "A note management CLI",
13
+ * };
14
+ * ```
15
+ */
16
+ interface CLIConfig {
17
+ /** CLI name (used in help output and error messages) */
18
+ readonly name: string;
19
+ /** CLI version (displayed with --version) */
20
+ readonly version: string;
21
+ /** CLI description (displayed in help output) */
22
+ readonly description?: string;
23
+ /** Custom error handler */
24
+ readonly onError?: (error: Error) => void;
25
+ /** Custom exit handler (defaults to process.exit) */
26
+ readonly onExit?: (code: number) => never;
27
+ }
28
+ /**
29
+ * CLI instance returned by createCLI.
30
+ */
31
+ interface CLI {
32
+ /** Register a command with the CLI */
33
+ register(command: CommandBuilder | Command): this;
34
+ /** Parse arguments and execute the matched command */
35
+ parse(argv?: readonly string[]): Promise<void>;
36
+ /** Get the underlying Commander program */
37
+ readonly program: Command;
38
+ }
39
+ /**
40
+ * Configuration for a single command.
41
+ */
42
+ interface CommandConfig {
43
+ /** Command name and argument syntax (e.g., "list" or "get <id>") */
44
+ readonly name: string;
45
+ /** Command description */
46
+ readonly description?: string;
47
+ /** Command aliases */
48
+ readonly aliases?: readonly string[];
49
+ /** Whether to hide from help output */
50
+ readonly hidden?: boolean;
51
+ }
52
+ /**
53
+ * Action function executed when a command is invoked.
54
+ *
55
+ * @typeParam TFlags - Type of parsed command flags
56
+ */
57
+ type CommandAction<TFlags extends CommandFlags = CommandFlags> = (context: {
58
+ /** Parsed command-line arguments */
59
+ readonly args: readonly string[];
60
+ /** Parsed command flags */
61
+ readonly flags: TFlags;
62
+ /** Raw Commander command instance */
63
+ readonly command: Command;
64
+ }) => Promise<void> | void;
65
+ /**
66
+ * Base type for command flags.
67
+ * All flag types must extend this.
68
+ */
69
+ type CommandFlags = Record<string, unknown>;
70
+ /**
71
+ * Builder interface for constructing commands fluently.
72
+ */
73
+ interface CommandBuilder {
74
+ /** Set command description */
75
+ description(text: string): this;
76
+ /** Add a command option/flag */
77
+ option(flags: string, description: string, defaultValue?: unknown): this;
78
+ /** Add a required option */
79
+ requiredOption(flags: string, description: string, defaultValue?: unknown): this;
80
+ /** Add command aliases */
81
+ alias(alias: string): this;
82
+ /** Set the action handler */
83
+ action<TFlags extends CommandFlags = CommandFlags>(handler: CommandAction<TFlags>): this;
84
+ /** Build the underlying Commander command */
85
+ build(): Command;
86
+ }
87
+ /**
88
+ * Available output modes for CLI commands.
89
+ */
90
+ type OutputMode = "human" | "json" | "jsonl" | "tree" | "table";
91
+ /**
92
+ * Options for the output() function.
93
+ */
94
+ interface OutputOptions {
95
+ /** Force a specific output mode (overrides flag detection) */
96
+ readonly mode?: OutputMode;
97
+ /** Stream to write to (defaults to stdout) */
98
+ readonly stream?: NodeJS.WritableStream;
99
+ /** Whether to pretty-print JSON output */
100
+ readonly pretty?: boolean;
101
+ /** Exit code to use after output (undefined = don't exit) */
102
+ readonly exitCode?: number;
103
+ }
104
+ /**
105
+ * Options for collectIds() input utility.
106
+ *
107
+ * @example
108
+ * ```typescript
109
+ * const ids = await collectIds(args, {
110
+ * allowFile: true, // @file expansion
111
+ * allowStdin: true, // - reads from stdin
112
+ * });
113
+ * ```
114
+ */
115
+ interface CollectIdsOptions {
116
+ /** Allow @file expansion (reads IDs from file) */
117
+ readonly allowFile?: boolean;
118
+ /** Allow glob patterns */
119
+ readonly allowGlob?: boolean;
120
+ /** Allow reading from stdin with "-" */
121
+ readonly allowStdin?: boolean;
122
+ /** Separator for comma-separated values */
123
+ readonly separator?: string;
124
+ }
125
+ /**
126
+ * Options for expandFileArg() input utility.
127
+ */
128
+ interface ExpandFileOptions {
129
+ /** Encoding for file reads (defaults to utf-8) */
130
+ readonly encoding?: BufferEncoding;
131
+ /** Maximum file size to read (in bytes) */
132
+ readonly maxSize?: number;
133
+ /** Whether to trim the file content */
134
+ readonly trim?: boolean;
135
+ }
136
+ /**
137
+ * Options for parseGlob() input utility.
138
+ */
139
+ interface ParseGlobOptions {
140
+ /** Current working directory for glob resolution */
141
+ readonly cwd?: string;
142
+ /** Whether to follow symlinks */
143
+ readonly followSymlinks?: boolean;
144
+ /** Patterns to exclude */
145
+ readonly ignore?: readonly string[];
146
+ /** Only match files (not directories) */
147
+ readonly onlyFiles?: boolean;
148
+ /** Only match directories (not files) */
149
+ readonly onlyDirectories?: boolean;
150
+ }
151
+ /**
152
+ * Options for normalizeId().
153
+ */
154
+ interface NormalizeIdOptions {
155
+ /** Whether to lowercase the ID */
156
+ readonly lowercase?: boolean;
157
+ /** Whether to trim whitespace */
158
+ readonly trim?: boolean;
159
+ /** Minimum length requirement */
160
+ readonly minLength?: number;
161
+ /** Maximum length requirement */
162
+ readonly maxLength?: number;
163
+ /** Pattern the ID must match */
164
+ readonly pattern?: RegExp;
165
+ }
166
+ /**
167
+ * Options for confirmDestructive().
168
+ */
169
+ interface ConfirmDestructiveOptions {
170
+ /** Message to display to the user */
171
+ readonly message: string;
172
+ /** Whether to bypass confirmation (e.g., --yes flag) */
173
+ readonly bypassFlag?: boolean;
174
+ /** Number of items affected (shown in confirmation) */
175
+ readonly itemCount?: number;
176
+ }
177
+ /**
178
+ * Numeric or date range parsed from CLI input.
179
+ */
180
+ type Range = NumericRange | DateRange;
181
+ /**
182
+ * Numeric range (e.g., "1-10").
183
+ */
184
+ interface NumericRange {
185
+ readonly type: "number";
186
+ readonly min: number;
187
+ readonly max: number;
188
+ }
189
+ /**
190
+ * Date range (e.g., "2024-01-01..2024-12-31").
191
+ */
192
+ interface DateRange {
193
+ readonly type: "date";
194
+ readonly start: Date;
195
+ readonly end: Date;
196
+ }
197
+ /**
198
+ * Filter expression parsed from CLI input.
199
+ */
200
+ interface FilterExpression {
201
+ readonly field: string;
202
+ readonly value: string;
203
+ readonly operator?: "eq" | "ne" | "gt" | "lt" | "gte" | "lte" | "contains";
204
+ }
205
+ /**
206
+ * Sort criteria parsed from CLI input.
207
+ */
208
+ interface SortCriteria {
209
+ readonly field: string;
210
+ readonly direction: "asc" | "desc";
211
+ }
212
+ /**
213
+ * Key-value pair parsed from CLI input.
214
+ */
215
+ interface KeyValuePair {
216
+ readonly key: string;
217
+ readonly value: string;
218
+ }
219
+ /**
220
+ * State for paginated command results.
221
+ */
222
+ interface PaginationState {
223
+ /** Cursor for the next page */
224
+ readonly cursor: string;
225
+ /** Command that generated this state */
226
+ readonly command: string;
227
+ /** Context key for scoping pagination */
228
+ readonly context?: string;
229
+ /** Timestamp when state was created */
230
+ readonly timestamp: number;
231
+ /** Whether there are more results */
232
+ readonly hasMore: boolean;
233
+ /** Total count (if known) */
234
+ readonly total?: number;
235
+ }
236
+ /**
237
+ * Options for cursor persistence operations.
238
+ */
239
+ interface CursorOptions {
240
+ /** Command name for cursor scoping */
241
+ readonly command: string;
242
+ /** Context key for additional scoping */
243
+ readonly context?: string;
244
+ /** Tool name for XDG path resolution */
245
+ readonly toolName: string;
246
+ /** Maximum age in milliseconds before a cursor is treated as expired */
247
+ readonly maxAgeMs?: number;
248
+ /** Whether there are more results (defaults to true) */
249
+ readonly hasMore?: boolean;
250
+ /** Total count of results (if known) */
251
+ readonly total?: number;
252
+ }
253
+ export { CLIConfig, CLI, CommandConfig, CommandAction, CommandFlags, CommandBuilder, OutputMode, OutputOptions, CollectIdsOptions, ExpandFileOptions, ParseGlobOptions, NormalizeIdOptions, ConfirmDestructiveOptions, Range, NumericRange, DateRange, FilterExpression, SortCriteria, KeyValuePair, PaginationState, CursorOptions, CancelledError, ErrorCategory, ValidationError, Result };
@@ -0,0 +1,20 @@
1
+ // @bun
2
+ // packages/cli/src/demo/types.ts
3
+ function isPrimitiveId(value) {
4
+ const validIds = [
5
+ "colors",
6
+ "borders",
7
+ "spinner",
8
+ "list",
9
+ "box",
10
+ "table",
11
+ "progress",
12
+ "tree",
13
+ "text",
14
+ "markdown",
15
+ "indicators"
16
+ ];
17
+ return validIds.includes(value);
18
+ }
19
+
20
+ export { isPrimitiveId };
@@ -0,0 +1,32 @@
1
+ // @bun
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropNames = Object.getOwnPropertyNames;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __moduleCache = /* @__PURE__ */ new WeakMap;
7
+ var __toCommonJS = (from) => {
8
+ var entry = __moduleCache.get(from), desc;
9
+ if (entry)
10
+ return entry;
11
+ entry = __defProp({}, "__esModule", { value: true });
12
+ if (from && typeof from === "object" || typeof from === "function")
13
+ __getOwnPropNames(from).map((key) => !__hasOwnProp.call(entry, key) && __defProp(entry, key, {
14
+ get: () => from[key],
15
+ enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable
16
+ }));
17
+ __moduleCache.set(from, entry);
18
+ return entry;
19
+ };
20
+ var __export = (target, all) => {
21
+ for (var name in all)
22
+ __defProp(target, name, {
23
+ get: all[name],
24
+ enumerable: true,
25
+ configurable: true,
26
+ set: (newValue) => all[name] = () => newValue
27
+ });
28
+ };
29
+ var __esm = (fn, res) => () => (fn && (res = fn(fn = 0)), res);
30
+ var __require = import.meta.require;
31
+
32
+ export { __toCommonJS, __export, __esm, __require };
@@ -0,0 +1 @@
1
+ // @bun
@@ -0,0 +1,279 @@
1
+ // @bun
2
+ import {
3
+ getStringWidth,
4
+ init_text,
5
+ truncateText,
6
+ wrapText
7
+ } from "./cli-jjemfdta.js";
8
+ import {
9
+ getBorderCharacters,
10
+ init_borders
11
+ } from "./cli-85fg2vr5.js";
12
+ import {
13
+ __esm,
14
+ __export
15
+ } from "./cli-v1tzwxkt.js";
16
+
17
+ // packages/cli/src/render/box.ts
18
+ var exports_box = {};
19
+ __export(exports_box, {
20
+ renderBox: () => renderBox,
21
+ normalizePadding: () => normalizePadding,
22
+ normalizeMargin: () => normalizeMargin,
23
+ normalizeBorders: () => normalizeBorders,
24
+ createBox: () => createBox
25
+ });
26
+ function alignLine(line, width, align) {
27
+ const lineWidth = getStringWidth(line);
28
+ const padding = width - lineWidth;
29
+ if (padding <= 0) {
30
+ return line;
31
+ }
32
+ switch (align) {
33
+ case "center": {
34
+ const leftPad = Math.floor(padding / 2);
35
+ const rightPad = padding - leftPad;
36
+ return " ".repeat(leftPad) + line + " ".repeat(rightPad);
37
+ }
38
+ case "right":
39
+ return " ".repeat(padding) + line;
40
+ default:
41
+ return line + " ".repeat(padding);
42
+ }
43
+ }
44
+ function normalizePadding(padding, defaultValue) {
45
+ if (padding === undefined) {
46
+ return { top: 0, right: defaultValue, bottom: 0, left: defaultValue };
47
+ }
48
+ if (typeof padding === "number") {
49
+ return { top: 0, right: padding, bottom: 0, left: padding };
50
+ }
51
+ return {
52
+ top: padding.top ?? 0,
53
+ right: padding.right ?? defaultValue,
54
+ bottom: padding.bottom ?? 0,
55
+ left: padding.left ?? defaultValue
56
+ };
57
+ }
58
+ function normalizeMargin(margin, defaultValue) {
59
+ if (margin === undefined) {
60
+ return {
61
+ top: defaultValue,
62
+ right: defaultValue,
63
+ bottom: defaultValue,
64
+ left: defaultValue
65
+ };
66
+ }
67
+ if (typeof margin === "number") {
68
+ return { top: margin, right: margin, bottom: margin, left: margin };
69
+ }
70
+ return {
71
+ top: margin.top ?? defaultValue,
72
+ right: margin.right ?? defaultValue,
73
+ bottom: margin.bottom ?? defaultValue,
74
+ left: margin.left ?? defaultValue
75
+ };
76
+ }
77
+ function normalizeBorders(borders) {
78
+ if (borders === undefined) {
79
+ return { top: true, right: true, bottom: true, left: true };
80
+ }
81
+ return {
82
+ top: borders.top ?? true,
83
+ right: borders.right ?? true,
84
+ bottom: borders.bottom ?? true,
85
+ left: borders.left ?? true
86
+ };
87
+ }
88
+ function renderBox(content, options) {
89
+ const border = options?.border ?? "single";
90
+ const title = options?.title;
91
+ const align = options?.align ?? "left";
92
+ const fixedWidth = options?.width;
93
+ const sections = options?.sections;
94
+ const pad = normalizePadding(options?.padding, 1);
95
+ const margin = normalizeMargin(options?.margin, 0);
96
+ const borders = normalizeBorders(options?.borders);
97
+ const chars = getBorderCharacters(border);
98
+ let lines;
99
+ let sectionBoundaries = [];
100
+ if (sections && sections.length > 0) {
101
+ lines = [];
102
+ for (const [idx, section] of sections.entries()) {
103
+ const sectionLines = typeof section === "string" ? section.split(`
104
+ `) : section;
105
+ lines.push(...sectionLines);
106
+ if (idx < sections.length - 1) {
107
+ sectionBoundaries.push(lines.length);
108
+ }
109
+ }
110
+ } else if (typeof content === "string") {
111
+ lines = content.split(`
112
+ `);
113
+ } else {
114
+ lines = content;
115
+ }
116
+ const leftOverhead = (borders.left ? 1 : 0) + pad.left;
117
+ const rightOverhead = (borders.right ? 1 : 0) + pad.right;
118
+ const horizontalOverhead = leftOverhead + rightOverhead;
119
+ if (fixedWidth) {
120
+ const contentWidthForWrap = fixedWidth - horizontalOverhead;
121
+ if (contentWidthForWrap > 0) {
122
+ const wrappedLines = [];
123
+ const newBoundaries = [];
124
+ let boundaryIdx2 = 0;
125
+ let originalLineCount = 0;
126
+ for (const line of lines) {
127
+ if (getStringWidth(line) > contentWidthForWrap) {
128
+ const wrapped = wrapText(line, contentWidthForWrap);
129
+ wrappedLines.push(...wrapped.split(`
130
+ `));
131
+ } else {
132
+ wrappedLines.push(line);
133
+ }
134
+ originalLineCount++;
135
+ const boundary = sectionBoundaries[boundaryIdx2];
136
+ if (boundary !== undefined && originalLineCount === boundary) {
137
+ newBoundaries.push(wrappedLines.length);
138
+ boundaryIdx2++;
139
+ }
140
+ }
141
+ lines = wrappedLines;
142
+ sectionBoundaries = newBoundaries;
143
+ }
144
+ }
145
+ let contentWidth = 0;
146
+ for (const line of lines) {
147
+ const w = getStringWidth(line);
148
+ if (w > contentWidth) {
149
+ contentWidth = w;
150
+ }
151
+ }
152
+ let boxWidth;
153
+ if (fixedWidth) {
154
+ boxWidth = fixedWidth;
155
+ contentWidth = fixedWidth - horizontalOverhead;
156
+ } else {
157
+ boxWidth = horizontalOverhead + contentWidth;
158
+ if (title && borders.top) {
159
+ const minBoxWidthForTitle = getStringWidth(title) + 4 + (borders.left ? 1 : 0) + (borders.right ? 1 : 0);
160
+ if (boxWidth < minBoxWidthForTitle) {
161
+ boxWidth = minBoxWidthForTitle;
162
+ contentWidth = boxWidth - horizontalOverhead;
163
+ }
164
+ }
165
+ }
166
+ const output = [];
167
+ const leftPaddingStr = " ".repeat(pad.left);
168
+ const rightPaddingStr = " ".repeat(pad.right);
169
+ const marginLeftStr = " ".repeat(margin.left);
170
+ const marginRightStr = " ".repeat(margin.right);
171
+ const buildContentLine = (lineContent) => {
172
+ const aligned = alignLine(lineContent, contentWidth, align);
173
+ const leftBorder = borders.left ? chars.vertical : "";
174
+ const rightBorder = borders.right ? chars.vertical : "";
175
+ return marginLeftStr + leftBorder + leftPaddingStr + aligned + rightPaddingStr + rightBorder + marginRightStr;
176
+ };
177
+ const innerWidth = boxWidth - (borders.left ? 1 : 0) - (borders.right ? 1 : 0);
178
+ for (let i = 0;i < margin.top; i++) {
179
+ output.push("");
180
+ }
181
+ if (borders.top) {
182
+ let topBorder;
183
+ if (title) {
184
+ const maxTitleWidth = Math.max(0, innerWidth - 4);
185
+ let displayTitle = title;
186
+ if (maxTitleWidth === 0) {
187
+ topBorder = marginLeftStr + (borders.left ? chars.topLeft : "") + chars.horizontal.repeat(Math.max(0, innerWidth)) + (borders.right ? chars.topRight : "") + marginRightStr;
188
+ } else {
189
+ if (getStringWidth(title) > maxTitleWidth) {
190
+ displayTitle = truncateText(title, maxTitleWidth);
191
+ }
192
+ const titlePart = `${chars.horizontal} ${displayTitle} `;
193
+ const remainingWidth = Math.max(0, innerWidth - getStringWidth(titlePart));
194
+ topBorder = marginLeftStr + (borders.left ? chars.topLeft : "") + titlePart + chars.horizontal.repeat(remainingWidth) + (borders.right ? chars.topRight : "") + marginRightStr;
195
+ }
196
+ } else {
197
+ topBorder = marginLeftStr + (borders.left ? chars.topLeft : "") + chars.horizontal.repeat(innerWidth) + (borders.right ? chars.topRight : "") + marginRightStr;
198
+ }
199
+ output.push(topBorder);
200
+ }
201
+ for (let i = 0;i < pad.top; i++) {
202
+ output.push(buildContentLine(""));
203
+ }
204
+ let boundaryIdx = 0;
205
+ for (const [idx, line] of lines.entries()) {
206
+ output.push(buildContentLine(line));
207
+ const boundary = sectionBoundaries[boundaryIdx];
208
+ if (boundary !== undefined && idx + 1 === boundary) {
209
+ const divider = marginLeftStr + (borders.left ? chars.leftT : "") + chars.horizontal.repeat(innerWidth) + (borders.right ? chars.rightT : "") + marginRightStr;
210
+ output.push(divider);
211
+ boundaryIdx++;
212
+ }
213
+ }
214
+ for (let i = 0;i < pad.bottom; i++) {
215
+ output.push(buildContentLine(""));
216
+ }
217
+ if (borders.bottom) {
218
+ const bottomBorder = marginLeftStr + (borders.left ? chars.bottomLeft : "") + chars.horizontal.repeat(innerWidth) + (borders.right ? chars.bottomRight : "") + marginRightStr;
219
+ output.push(bottomBorder);
220
+ }
221
+ for (let i = 0;i < margin.bottom; i++) {
222
+ output.push("");
223
+ }
224
+ return output.join(`
225
+ `);
226
+ }
227
+ function isBox(value) {
228
+ return typeof value === "object" && value !== null && "output" in value && "width" in value && "height" in value && typeof value.output === "string" && typeof value.width === "number" && typeof value.height === "number";
229
+ }
230
+ function contentToLines(content) {
231
+ if (Array.isArray(content)) {
232
+ const lines = [];
233
+ for (const item of content) {
234
+ if (isBox(item)) {
235
+ lines.push(...item.output.split(`
236
+ `));
237
+ } else if (Array.isArray(item)) {
238
+ lines.push(...item);
239
+ } else {
240
+ lines.push(...item.split(`
241
+ `));
242
+ }
243
+ }
244
+ return lines;
245
+ }
246
+ if (isBox(content)) {
247
+ return content.output.split(`
248
+ `);
249
+ }
250
+ if (typeof content === "string") {
251
+ return content.split(`
252
+ `);
253
+ }
254
+ return content;
255
+ }
256
+ function createBox(content, options) {
257
+ const lines = contentToLines(content);
258
+ const output = renderBox(lines, options);
259
+ const outputLines = output.split(`
260
+ `);
261
+ let maxWidth = 0;
262
+ for (const line of outputLines) {
263
+ const lineWidth = getStringWidth(line);
264
+ if (lineWidth > maxWidth) {
265
+ maxWidth = lineWidth;
266
+ }
267
+ }
268
+ return {
269
+ output,
270
+ width: maxWidth,
271
+ height: outputLines.length
272
+ };
273
+ }
274
+ var init_box = __esm(() => {
275
+ init_borders();
276
+ init_text();
277
+ });
278
+
279
+ export { normalizePadding, normalizeMargin, normalizeBorders, renderBox, createBox, exports_box, init_box };
@@ -0,0 +1,74 @@
1
+ /**
2
+ * Validator factories for prompt input validation.
3
+ *
4
+ * @packageDocumentation
5
+ */
6
+ /**
7
+ * A validator function that returns an error message or undefined.
8
+ */
9
+ type Validator = (value: string) => string | undefined;
10
+ /**
11
+ * Collection of validator factory functions.
12
+ *
13
+ * @example
14
+ * ```typescript
15
+ * import { validators } from "@outfitter/cli/prompt";
16
+ *
17
+ * const validate = validators.compose(
18
+ * validators.required(),
19
+ * validators.minLength(3),
20
+ * validators.email()
21
+ * );
22
+ *
23
+ * const error = validate("ab");
24
+ * // "Minimum 3 characters"
25
+ * ```
26
+ */
27
+ declare const validators: {
28
+ /**
29
+ * Requires a non-empty value.
30
+ *
31
+ * @param message - Custom error message
32
+ * @returns Validator function
33
+ */
34
+ required: (message?: string) => Validator;
35
+ /**
36
+ * Requires minimum character length.
37
+ *
38
+ * @param length - Minimum length
39
+ * @param message - Custom error message
40
+ * @returns Validator function
41
+ */
42
+ minLength: (length: number, message?: string) => Validator;
43
+ /**
44
+ * Requires maximum character length.
45
+ *
46
+ * @param length - Maximum length
47
+ * @param message - Custom error message
48
+ * @returns Validator function
49
+ */
50
+ maxLength: (length: number, message?: string) => Validator;
51
+ /**
52
+ * Requires value to match a regex pattern.
53
+ *
54
+ * @param regex - Pattern to match
55
+ * @param message - Error message when pattern doesn't match
56
+ * @returns Validator function
57
+ */
58
+ pattern: (regex: RegExp, message: string) => Validator;
59
+ /**
60
+ * Validates email format.
61
+ *
62
+ * @param message - Custom error message
63
+ * @returns Validator function
64
+ */
65
+ email: (message?: string) => Validator;
66
+ /**
67
+ * Composes multiple validators, returning the first error.
68
+ *
69
+ * @param fns - Validators to compose
70
+ * @returns Combined validator function
71
+ */
72
+ compose: (...fns: Validator[]) => Validator;
73
+ };
74
+ export { Validator, validators };