@gunshi/plugin 0.26.3 → 0.27.0-alpha.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/index.d.ts +546 -240
- package/lib/index.js +122 -2
- package/package.json +5 -5
package/lib/index.d.ts
CHANGED
|
@@ -1,161 +1,395 @@
|
|
|
1
|
-
//#region ../../node_modules/.pnpm/args-tokens@0.
|
|
1
|
+
//#region ../../node_modules/.pnpm/args-tokens@0.22.0/node_modules/args-tokens/lib/parser-Cbxholql.d.ts
|
|
2
2
|
//#region src/parser.d.ts
|
|
3
3
|
/**
|
|
4
|
-
* Entry point of argument parser.
|
|
5
|
-
* @module
|
|
6
|
-
*/
|
|
7
|
-
/**
|
|
8
|
-
* forked from `nodejs/node` (`pkgjs/parseargs`)
|
|
9
|
-
* repository url: https://github.com/nodejs/node (https://github.com/pkgjs/parseargs)
|
|
10
|
-
* code url: https://github.com/nodejs/node/blob/main/lib/internal/util/parse_args/parse_args.js
|
|
11
|
-
*
|
|
12
|
-
* @author kazuya kawaguchi (a.k.a. kazupon)
|
|
13
|
-
* @license MIT
|
|
14
|
-
*/
|
|
15
|
-
/**
|
|
16
|
-
* Argument token Kind.
|
|
17
|
-
* - `option`: option token, support short option (e.g. `-x`) and long option (e.g. `--foo`)
|
|
18
|
-
* - `option-terminator`: option terminator (`--`) token, see guideline 10 in https://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap12.html
|
|
19
|
-
* - `positional`: positional token
|
|
20
|
-
*/
|
|
21
|
-
type ArgTokenKind =
|
|
22
|
-
/**
|
|
23
|
-
* Argument token.
|
|
24
|
-
*/
|
|
4
|
+
* Entry point of argument parser.
|
|
5
|
+
* @module
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* forked from `nodejs/node` (`pkgjs/parseargs`)
|
|
9
|
+
* repository url: https://github.com/nodejs/node (https://github.com/pkgjs/parseargs)
|
|
10
|
+
* code url: https://github.com/nodejs/node/blob/main/lib/internal/util/parse_args/parse_args.js
|
|
11
|
+
*
|
|
12
|
+
* @author kazuya kawaguchi (a.k.a. kazupon)
|
|
13
|
+
* @license MIT
|
|
14
|
+
*/
|
|
15
|
+
/**
|
|
16
|
+
* Argument token Kind.
|
|
17
|
+
* - `option`: option token, support short option (e.g. `-x`) and long option (e.g. `--foo`)
|
|
18
|
+
* - `option-terminator`: option terminator (`--`) token, see guideline 10 in https://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap12.html
|
|
19
|
+
* - `positional`: positional token
|
|
20
|
+
*/
|
|
21
|
+
type ArgTokenKind = 'option' | 'option-terminator' | 'positional';
|
|
22
|
+
/**
|
|
23
|
+
* Argument token.
|
|
24
|
+
*/
|
|
25
25
|
interface ArgToken {
|
|
26
26
|
/**
|
|
27
|
-
|
|
28
|
-
|
|
27
|
+
* Argument token kind.
|
|
28
|
+
*/
|
|
29
29
|
kind: ArgTokenKind;
|
|
30
30
|
/**
|
|
31
|
-
|
|
32
|
-
|
|
31
|
+
* Argument token index, e.g `--foo bar` => `--foo` index is 0, `bar` index is 1.
|
|
32
|
+
*/
|
|
33
33
|
index: number;
|
|
34
34
|
/**
|
|
35
|
-
|
|
36
|
-
|
|
35
|
+
* Option name, e.g. `--foo` => `foo`, `-x` => `x`.
|
|
36
|
+
*/
|
|
37
37
|
name?: string;
|
|
38
38
|
/**
|
|
39
|
-
|
|
40
|
-
|
|
39
|
+
* Raw option name, e.g. `--foo` => `--foo`, `-x` => `-x`.
|
|
40
|
+
*/
|
|
41
41
|
rawName?: string;
|
|
42
42
|
/**
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
43
|
+
* Option value, e.g. `--foo=bar` => `bar`, `-x=bar` => `bar`.
|
|
44
|
+
* If the `allowCompatible` option is `true`, short option value will be same as Node.js `parseArgs` behavior.
|
|
45
|
+
*/
|
|
46
46
|
value?: string;
|
|
47
47
|
/**
|
|
48
|
-
|
|
49
|
-
|
|
48
|
+
* Inline value, e.g. `--foo=bar` => `true`, `-x=bar` => `true`.
|
|
49
|
+
*/
|
|
50
50
|
inlineValue?: boolean;
|
|
51
|
-
}
|
|
52
|
-
//#region ../../node_modules/.pnpm/args-tokens@0.20.1/node_modules/args-tokens/lib/resolver-U72Jg6Ll.d.ts
|
|
53
|
-
|
|
51
|
+
}
|
|
54
52
|
/**
|
|
55
|
-
* Parser Options.
|
|
56
|
-
*/
|
|
53
|
+
* Parser Options.
|
|
54
|
+
*/
|
|
55
|
+
//#endregion
|
|
56
|
+
//#region ../../node_modules/.pnpm/args-tokens@0.22.0/node_modules/args-tokens/lib/resolver-BoS-UnqX.d.ts
|
|
57
57
|
//#region src/resolver.d.ts
|
|
58
|
+
|
|
58
59
|
/**
|
|
59
|
-
* An argument schema
|
|
60
|
-
* This schema is similar to the schema of the `node:utils`.
|
|
61
|
-
* difference is that:
|
|
62
|
-
* - `required` property and `description` property are added
|
|
63
|
-
* - `type` is not only 'string' and 'boolean', but also 'number', 'enum', 'positional', 'custom' too.
|
|
64
|
-
* - `default` property type, not support multiple types
|
|
65
|
-
*/
|
|
60
|
+
* An argument schema
|
|
61
|
+
* This schema is similar to the schema of the `node:utils`.
|
|
62
|
+
* difference is that:
|
|
63
|
+
* - `required` property and `description` property are added
|
|
64
|
+
* - `type` is not only 'string' and 'boolean', but also 'number', 'enum', 'positional', 'custom' too.
|
|
65
|
+
* - `default` property type, not support multiple types
|
|
66
|
+
*/
|
|
66
67
|
interface ArgSchema {
|
|
67
68
|
/**
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
type:
|
|
69
|
+
* Type of argument.
|
|
70
|
+
*/
|
|
71
|
+
type: 'string' | 'boolean' | 'number' | 'enum' | 'positional' | 'custom';
|
|
71
72
|
/**
|
|
72
|
-
|
|
73
|
-
|
|
73
|
+
* A single character alias for the argument.
|
|
74
|
+
*/
|
|
74
75
|
short?: string;
|
|
75
76
|
/**
|
|
76
|
-
|
|
77
|
-
|
|
77
|
+
* A description of the argument.
|
|
78
|
+
*/
|
|
78
79
|
description?: string;
|
|
79
80
|
/**
|
|
80
|
-
|
|
81
|
-
|
|
81
|
+
* Whether the argument is required or not.
|
|
82
|
+
*/
|
|
82
83
|
required?: true;
|
|
83
84
|
/**
|
|
84
|
-
|
|
85
|
-
|
|
85
|
+
* Whether the argument allow multiple values or not.
|
|
86
|
+
*/
|
|
86
87
|
multiple?: true;
|
|
87
88
|
/**
|
|
88
|
-
|
|
89
|
-
|
|
89
|
+
* Whether the negatable option for `boolean` type
|
|
90
|
+
*/
|
|
90
91
|
negatable?: boolean;
|
|
91
92
|
/**
|
|
92
|
-
|
|
93
|
-
|
|
93
|
+
* The allowed values of the argument, and string only. This property is only used when the type is 'enum'.
|
|
94
|
+
*/
|
|
94
95
|
choices?: string[] | readonly string[];
|
|
95
96
|
/**
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
97
|
+
* The default value of the argument.
|
|
98
|
+
* if the type is 'enum', the default value must be one of the allowed values.
|
|
99
|
+
*/
|
|
99
100
|
default?: string | boolean | number;
|
|
100
101
|
/**
|
|
101
|
-
|
|
102
|
-
|
|
102
|
+
* Whether to convert the argument name to kebab-case.
|
|
103
|
+
*/
|
|
103
104
|
toKebab?: true;
|
|
104
105
|
/**
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
106
|
+
* A function to parse the value of the argument. if the type is 'custom', this function is required.
|
|
107
|
+
* If argument value will be invalid, this function have to throw an error.
|
|
108
|
+
* @param value
|
|
109
|
+
* @returns Parsed value
|
|
110
|
+
* @throws An Error, If the value is invalid. Error type should be `Error` or extends it
|
|
111
|
+
*/
|
|
112
112
|
parse?: (value: string) => any;
|
|
113
113
|
}
|
|
114
114
|
/**
|
|
115
|
-
* An object that contains {@link ArgSchema | argument schema}.
|
|
116
|
-
*/
|
|
115
|
+
* An object that contains {@link ArgSchema | argument schema}.
|
|
116
|
+
*/
|
|
117
117
|
interface Args {
|
|
118
118
|
[option: string]: ArgSchema;
|
|
119
119
|
}
|
|
120
120
|
/**
|
|
121
|
-
* An object that contains the values of the arguments.
|
|
122
|
-
*/
|
|
121
|
+
* An object that contains the values of the arguments.
|
|
122
|
+
*/
|
|
123
123
|
type ArgValues<T> = T extends Args ? ResolveArgValues<T, { [Arg in keyof T]: ExtractOptionValue<T[Arg]> }> : {
|
|
124
124
|
[option: string]: string | boolean | number | (string | boolean | number)[] | undefined;
|
|
125
125
|
};
|
|
126
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
127
126
|
type IsFunction<T> = T extends ((...args: any[]) => any) ? true : false;
|
|
128
127
|
/**
|
|
129
|
-
* @internal
|
|
130
|
-
*/
|
|
131
|
-
type ExtractOptionValue<A extends ArgSchema> = A[
|
|
132
|
-
type ResolveOptionValue<A extends ArgSchema, T> = A[
|
|
128
|
+
* @internal
|
|
129
|
+
*/
|
|
130
|
+
type ExtractOptionValue<A extends ArgSchema> = A['type'] extends 'string' ? ResolveOptionValue<A, string> : A['type'] extends 'boolean' ? ResolveOptionValue<A, boolean> : A['type'] extends 'number' ? ResolveOptionValue<A, number> : A['type'] extends 'positional' ? ResolveOptionValue<A, string> : A['type'] extends 'enum' ? A['choices'] extends string[] | readonly string[] ? ResolveOptionValue<A, A['choices'][number]> : never : A['type'] extends 'custom' ? IsFunction<A['parse']> extends true ? ResolveOptionValue<A, ReturnType<NonNullable<A['parse']>>> : never : ResolveOptionValue<A, string | boolean | number>;
|
|
131
|
+
type ResolveOptionValue<A extends ArgSchema, T> = A['multiple'] extends true ? T[] : T;
|
|
133
132
|
/**
|
|
134
|
-
* @internal
|
|
135
|
-
*/
|
|
136
|
-
type ResolveArgValues<A extends Args, V extends Record<keyof A, unknown>> = { -readonly [Arg in keyof A]?: V[Arg] } & FilterArgs<A, V,
|
|
133
|
+
* @internal
|
|
134
|
+
*/
|
|
135
|
+
type ResolveArgValues<A extends Args, V extends Record<keyof A, unknown>> = { -readonly [Arg in keyof A]?: V[Arg] } & FilterArgs<A, V, 'default'> & FilterArgs<A, V, 'required'> & FilterPositionalArgs<A, V> extends infer P ? { [K in keyof P]: P[K] } : never;
|
|
137
136
|
/**
|
|
138
|
-
* @internal
|
|
139
|
-
*/
|
|
137
|
+
* @internal
|
|
138
|
+
*/
|
|
140
139
|
type FilterArgs<A extends Args, V extends Record<keyof A, unknown>, K extends keyof ArgSchema> = { [Arg in keyof A as A[Arg][K] extends {} ? Arg : never]: V[Arg] };
|
|
141
140
|
/**
|
|
142
|
-
* @internal
|
|
143
|
-
*/
|
|
144
|
-
type FilterPositionalArgs<A extends Args, V extends Record<keyof A, unknown>> = { [Arg in keyof A as A[Arg][
|
|
141
|
+
* @internal
|
|
142
|
+
*/
|
|
143
|
+
type FilterPositionalArgs<A extends Args, V extends Record<keyof A, unknown>> = { [Arg in keyof A as A[Arg]['type'] extends 'positional' ? Arg : never]: V[Arg] };
|
|
144
|
+
/**
|
|
145
|
+
* An arguments for {@link resolveArgs | resolve arguments}.
|
|
146
|
+
*/
|
|
145
147
|
|
|
148
|
+
/**
|
|
149
|
+
* Tracks which arguments were explicitly provided by the user.
|
|
150
|
+
*
|
|
151
|
+
* Each property indicates whether the corresponding argument was explicitly
|
|
152
|
+
* provided (true) or is using a default value or not provided (false).
|
|
153
|
+
*/
|
|
154
|
+
type ArgExplicitlyProvided<A extends Args> = { [K in keyof A]: boolean };
|
|
155
|
+
/**
|
|
156
|
+
* Resolve command line arguments.
|
|
157
|
+
* @param args - An arguments that contains {@link ArgSchema | arguments schema}.
|
|
158
|
+
* @param tokens - An array of {@link ArgToken | tokens}.
|
|
159
|
+
* @param resolveArgs - An arguments that contains {@link ResolveArgs | resolve arguments}.
|
|
160
|
+
* @returns An object that contains the values of the arguments, positional arguments, rest arguments, {@link AggregateError | validation errors}, and explicit provision status.
|
|
161
|
+
*
|
|
162
|
+
* @example
|
|
163
|
+
* ```typescript
|
|
164
|
+
* // passed tokens: --port 3000
|
|
165
|
+
*
|
|
166
|
+
* const { values, explicit } = resolveArgs({
|
|
167
|
+
* port: {
|
|
168
|
+
* type: 'number',
|
|
169
|
+
* default: 8080
|
|
170
|
+
* },
|
|
171
|
+
* host: {
|
|
172
|
+
* type: 'string',
|
|
173
|
+
* default: 'localhost'
|
|
174
|
+
* }
|
|
175
|
+
* }, parsedTokens)
|
|
176
|
+
*
|
|
177
|
+
* values.port // 3000
|
|
178
|
+
* values.host // 'localhost'
|
|
179
|
+
*
|
|
180
|
+
* explicit.port // true (explicitly provided)
|
|
181
|
+
* explicit.host // false (not provided, fallback to default)
|
|
182
|
+
* ```
|
|
183
|
+
*/
|
|
146
184
|
//#endregion
|
|
147
|
-
//#region ../gunshi/src/
|
|
185
|
+
//#region ../gunshi/src/plugin/context.d.ts
|
|
186
|
+
/**
|
|
187
|
+
* Type helper to create GunshiParams from extracted args and extensions
|
|
188
|
+
* @internal
|
|
189
|
+
*/
|
|
190
|
+
type ExtractedParams<G extends GunshiParamsConstraint, L extends Record<string, unknown> = {}> = {
|
|
191
|
+
args: ExtractArgs<G>;
|
|
192
|
+
extensions: ExtractExtensions$1<G> & L;
|
|
193
|
+
};
|
|
194
|
+
/**
|
|
195
|
+
* Gunshi plugin context interface.
|
|
196
|
+
* @since v0.27.0
|
|
197
|
+
*/
|
|
198
|
+
interface PluginContext<G extends GunshiParamsConstraint = DefaultGunshiParams> {
|
|
199
|
+
/**
|
|
200
|
+
* Get the global options
|
|
201
|
+
* @returns A map of global options.
|
|
202
|
+
*/
|
|
203
|
+
readonly globalOptions: Map<string, ArgSchema>;
|
|
204
|
+
/**
|
|
205
|
+
* Get the registered sub commands
|
|
206
|
+
* @returns A map of sub commands.
|
|
207
|
+
*/
|
|
208
|
+
readonly subCommands: ReadonlyMap<string, Command<G> | LazyCommand<G>>;
|
|
209
|
+
/**
|
|
210
|
+
* Add a global option.
|
|
211
|
+
* @param name An option name
|
|
212
|
+
* @param schema An {@link ArgSchema} for the option
|
|
213
|
+
*/
|
|
214
|
+
addGlobalOption(name: string, schema: ArgSchema): void;
|
|
215
|
+
/**
|
|
216
|
+
* Add a sub command.
|
|
217
|
+
* @param name Command name
|
|
218
|
+
* @param command Command definition
|
|
219
|
+
*/
|
|
220
|
+
addCommand(name: string, command: Command<G> | LazyCommand<G>): void;
|
|
221
|
+
/**
|
|
222
|
+
* Check if a command exists.
|
|
223
|
+
* @param name Command name
|
|
224
|
+
* @returns True if the command exists, false otherwise
|
|
225
|
+
*/
|
|
226
|
+
hasCommand(name: string): boolean;
|
|
227
|
+
/**
|
|
228
|
+
* Decorate the header renderer.
|
|
229
|
+
* @param decorator - A decorator function that wraps the base header renderer.
|
|
230
|
+
*/
|
|
231
|
+
decorateHeaderRenderer<L extends Record<string, unknown> = DefaultGunshiParams['extensions']>(decorator: (baseRenderer: (ctx: Readonly<CommandContext<ExtractedParams<G, L>>>) => Promise<string>, ctx: Readonly<CommandContext<ExtractedParams<G, L>>>) => Promise<string>): void;
|
|
232
|
+
/**
|
|
233
|
+
* Decorate the usage renderer.
|
|
234
|
+
* @param decorator - A decorator function that wraps the base usage renderer.
|
|
235
|
+
*/
|
|
236
|
+
decorateUsageRenderer<L extends Record<string, unknown> = DefaultGunshiParams['extensions']>(decorator: (baseRenderer: (ctx: Readonly<CommandContext<ExtractedParams<G, L>>>) => Promise<string>, ctx: Readonly<CommandContext<ExtractedParams<G, L>>>) => Promise<string>): void;
|
|
237
|
+
/**
|
|
238
|
+
* Decorate the validation errors renderer.
|
|
239
|
+
* @param decorator - A decorator function that wraps the base validation errors renderer.
|
|
240
|
+
*/
|
|
241
|
+
decorateValidationErrorsRenderer<L extends Record<string, unknown> = DefaultGunshiParams['extensions']>(decorator: (baseRenderer: (ctx: Readonly<CommandContext<ExtractedParams<G, L>>>, error: AggregateError) => Promise<string>, ctx: Readonly<CommandContext<ExtractedParams<G, L>>>, error: AggregateError) => Promise<string>): void;
|
|
242
|
+
/**
|
|
243
|
+
* Decorate the command execution.
|
|
244
|
+
* Decorators are applied in reverse order (last registered is executed first).
|
|
245
|
+
* @param decorator - A decorator function that wraps the command runner
|
|
246
|
+
*/
|
|
247
|
+
decorateCommand<L extends Record<string, unknown> = DefaultGunshiParams['extensions']>(decorator: (baseRunner: (ctx: Readonly<CommandContext<ExtractedParams<G, L>>>) => Awaitable<void | string>) => (ctx: Readonly<CommandContext<ExtractedParams<G, L>>>) => Awaitable<void | string>): void;
|
|
248
|
+
}
|
|
249
|
+
/**
|
|
250
|
+
* Factory function for creating a plugin context.
|
|
251
|
+
* @param decorators - A {@link Decorators} instance.
|
|
252
|
+
* @param initialSubCommands - Initial sub commands map.
|
|
253
|
+
* @returns A new {@link PluginContext} instance.
|
|
254
|
+
*/
|
|
255
|
+
//#endregion
|
|
256
|
+
//#region ../gunshi/src/plugin/core.d.ts
|
|
257
|
+
/**
|
|
258
|
+
* Plugin dependency definition
|
|
259
|
+
* @since v0.27.0
|
|
260
|
+
*/
|
|
261
|
+
interface PluginDependency {
|
|
262
|
+
/**
|
|
263
|
+
* Dependency plugin id
|
|
264
|
+
*/
|
|
265
|
+
id: string;
|
|
266
|
+
/**
|
|
267
|
+
* Optional dependency flag.
|
|
268
|
+
* If true, the plugin will not throw an error if the dependency is not found.
|
|
269
|
+
*/
|
|
270
|
+
optional?: boolean;
|
|
271
|
+
}
|
|
272
|
+
/**
|
|
273
|
+
* Plugin function type
|
|
274
|
+
* @since v0.27.0
|
|
275
|
+
*/
|
|
276
|
+
type PluginFunction<G extends GunshiParams = DefaultGunshiParams> = (ctx: Readonly<PluginContext<G>>) => Awaitable<void>;
|
|
277
|
+
/**
|
|
278
|
+
* Plugin extension for CommandContext
|
|
279
|
+
* @since v0.27.0
|
|
280
|
+
*/
|
|
281
|
+
type PluginExtension<T = Record<string, unknown>, G extends GunshiParams = DefaultGunshiParams> = (ctx: CommandContextCore<G>, cmd: Command<G>) => Awaitable<T>;
|
|
282
|
+
/**
|
|
283
|
+
* Plugin extension callback type
|
|
284
|
+
* @since v0.27.0
|
|
285
|
+
*/
|
|
286
|
+
type OnPluginExtension<G extends GunshiParams = DefaultGunshiParams> = (ctx: Readonly<CommandContext<G>>, cmd: Readonly<Command<G>>) => Awaitable<void>;
|
|
287
|
+
/**
|
|
288
|
+
* Plugin definition options
|
|
289
|
+
* @since v0.27.0
|
|
290
|
+
*/
|
|
291
|
+
interface PluginOptions<T extends Record<string, unknown> = Record<never, never>, G extends GunshiParams = DefaultGunshiParams> {
|
|
292
|
+
/**
|
|
293
|
+
* Plugin unique identifier
|
|
294
|
+
*/
|
|
295
|
+
id: string;
|
|
296
|
+
/**
|
|
297
|
+
* Plugin name
|
|
298
|
+
*/
|
|
299
|
+
name?: string;
|
|
300
|
+
/**
|
|
301
|
+
* Plugin dependencies
|
|
302
|
+
*/
|
|
303
|
+
dependencies?: (PluginDependency | string)[];
|
|
304
|
+
/**
|
|
305
|
+
* Plugin setup function
|
|
306
|
+
*/
|
|
307
|
+
setup?: PluginFunction<G>;
|
|
308
|
+
/**
|
|
309
|
+
* Plugin extension
|
|
310
|
+
*/
|
|
311
|
+
extension?: PluginExtension<T, G>;
|
|
312
|
+
/**
|
|
313
|
+
* Callback for when the plugin is extended with `extension` option.
|
|
314
|
+
*/
|
|
315
|
+
onExtension?: OnPluginExtension<G>;
|
|
316
|
+
}
|
|
148
317
|
/**
|
|
149
|
-
*
|
|
150
|
-
|
|
318
|
+
* Gunshi plugin, which is a function that receives a PluginContext.
|
|
319
|
+
* @param ctx - A {@link PluginContext}.
|
|
320
|
+
* @returns An {@link Awaitable} that resolves when the plugin is loaded.
|
|
321
|
+
* @since v0.27.0
|
|
322
|
+
*/
|
|
323
|
+
type Plugin<E extends GunshiParams['extensions'] = DefaultGunshiParams['extensions']> = PluginFunction & {
|
|
324
|
+
id: string;
|
|
325
|
+
name?: string;
|
|
326
|
+
dependencies?: (PluginDependency | string)[];
|
|
327
|
+
extension?: CommandContextExtension<E>;
|
|
328
|
+
};
|
|
329
|
+
/**
|
|
330
|
+
* Plugin return type with extension
|
|
331
|
+
* @internal
|
|
332
|
+
*/
|
|
333
|
+
interface PluginWithExtension<E extends GunshiParams['extensions'] = DefaultGunshiParams['extensions']> extends Plugin<E> {
|
|
334
|
+
id: string;
|
|
335
|
+
name: string;
|
|
336
|
+
dependencies?: (PluginDependency | string)[];
|
|
337
|
+
extension: CommandContextExtension<E>;
|
|
338
|
+
}
|
|
339
|
+
/**
|
|
340
|
+
* Plugin return type without extension
|
|
341
|
+
* @internal
|
|
342
|
+
*/
|
|
343
|
+
interface PluginWithoutExtension<E extends GunshiParams['extensions'] = DefaultGunshiParams['extensions']> extends Plugin<E> {
|
|
344
|
+
id: string;
|
|
345
|
+
name: string;
|
|
346
|
+
dependencies?: (PluginDependency | string)[];
|
|
347
|
+
}
|
|
348
|
+
/**
|
|
349
|
+
* Define a plugin with extension capabilities
|
|
350
|
+
* @param options - {@link PluginOptions | plugin options}
|
|
351
|
+
* @return A defined plugin with extension capabilities.
|
|
352
|
+
* @since v0.27.0
|
|
353
|
+
*/
|
|
354
|
+
declare function plugin<I extends string, P extends PluginExtension<any, DefaultGunshiParams>>(options: {
|
|
355
|
+
id: I;
|
|
356
|
+
name?: string;
|
|
357
|
+
dependencies?: (PluginDependency | string)[];
|
|
358
|
+
setup?: (ctx: Readonly<PluginContext<GunshiParams<{
|
|
359
|
+
args: Args;
|
|
360
|
+
extensions: { [K in I]: Awaited<ReturnType<P>> };
|
|
361
|
+
}>>>) => Awaitable<void>;
|
|
362
|
+
extension: P;
|
|
363
|
+
onExtension?: OnPluginExtension<{
|
|
364
|
+
args: Args;
|
|
365
|
+
extensions: { [K in I]: Awaited<ReturnType<P>> };
|
|
366
|
+
}>;
|
|
367
|
+
}): PluginWithExtension<Awaited<ReturnType<P>>>;
|
|
368
|
+
/**
|
|
369
|
+
* Define a plugin without extension capabilities
|
|
370
|
+
* @param options - {@link PluginOptions | plugin options} without extension
|
|
371
|
+
* @returns A defined plugin without extension capabilities.
|
|
372
|
+
* @since v0.27.0
|
|
373
|
+
*/
|
|
374
|
+
declare function plugin(options: {
|
|
375
|
+
id: string;
|
|
376
|
+
name?: string;
|
|
377
|
+
dependencies?: (PluginDependency | string)[];
|
|
378
|
+
setup?: (ctx: Readonly<PluginContext<DefaultGunshiParams>>) => Awaitable<void>;
|
|
379
|
+
onExtension?: OnPluginExtension<DefaultGunshiParams>;
|
|
380
|
+
}): PluginWithoutExtension<DefaultGunshiParams['extensions']>;
|
|
381
|
+
//#endregion
|
|
382
|
+
//#region ../gunshi/src/types.d.ts
|
|
151
383
|
type Awaitable<T> = T | Promise<T>;
|
|
152
384
|
/**
|
|
153
385
|
* Extend command context type. This type is used to extend the command context with additional properties at {@link CommandContext.extensions}.
|
|
386
|
+
* @since v0.27.0
|
|
154
387
|
*/
|
|
155
388
|
type ExtendContext = Record<string, unknown>;
|
|
156
389
|
/**
|
|
157
390
|
* Gunshi unified parameter type.
|
|
158
391
|
* This type combines both argument definitions and command context extensions.
|
|
392
|
+
* @since v0.27.0
|
|
159
393
|
*/
|
|
160
394
|
interface GunshiParams<P extends {
|
|
161
395
|
args?: Args;
|
|
@@ -179,11 +413,13 @@ interface GunshiParams<P extends {
|
|
|
179
413
|
}
|
|
180
414
|
/**
|
|
181
415
|
* Default Gunshi parameters
|
|
416
|
+
* @since v0.27.0
|
|
182
417
|
*/
|
|
183
418
|
type DefaultGunshiParams = GunshiParams;
|
|
184
419
|
/**
|
|
185
420
|
* Generic constraint for command-related types.
|
|
186
421
|
* This type constraint allows both GunshiParams and objects with extensions.
|
|
422
|
+
* @since v0.27.0
|
|
187
423
|
*/
|
|
188
424
|
type GunshiParamsConstraint = GunshiParams<any> | {
|
|
189
425
|
extensions: ExtendContext;
|
|
@@ -193,11 +429,16 @@ type GunshiParamsConstraint = GunshiParams<any> | {
|
|
|
193
429
|
* @internal
|
|
194
430
|
*/
|
|
195
431
|
type ExtractArgs<G> = G extends GunshiParams<any> ? G['args'] : Args;
|
|
432
|
+
/**
|
|
433
|
+
* Type helper to extract explicitly provided argument flags from G
|
|
434
|
+
* @internal
|
|
435
|
+
*/
|
|
436
|
+
type ExtractArgExplicitlyProvided<G> = ArgExplicitlyProvided<ExtractArgs<G>>;
|
|
196
437
|
/**
|
|
197
438
|
* Type helper to extract extensions from G
|
|
198
439
|
* @internal
|
|
199
440
|
*/
|
|
200
|
-
type ExtractExtensions<G> = G extends GunshiParams<any> ? G['extensions'] : G extends {
|
|
441
|
+
type ExtractExtensions$1<G> = G extends GunshiParams<any> ? G['extensions'] : G extends {
|
|
201
442
|
extensions: infer E;
|
|
202
443
|
} ? E : {};
|
|
203
444
|
/**
|
|
@@ -285,23 +526,105 @@ interface CommandEnvironment<G extends GunshiParamsConstraint = DefaultGunshiPar
|
|
|
285
526
|
/**
|
|
286
527
|
* Hook that runs before any command execution
|
|
287
528
|
* @see {@link CliOptions.onBeforeCommand}
|
|
529
|
+
* @since v0.27.0
|
|
288
530
|
*/
|
|
289
531
|
onBeforeCommand: ((ctx: Readonly<CommandContext<G>>) => Awaitable<void>) | undefined;
|
|
290
532
|
/**
|
|
291
533
|
* Hook that runs after successful command execution
|
|
292
534
|
* @see {@link CliOptions.onAfterCommand}
|
|
535
|
+
* @since v0.27.0
|
|
293
536
|
*/
|
|
294
|
-
onAfterCommand: ((ctx: Readonly<CommandContext<G>>, result: string |
|
|
537
|
+
onAfterCommand: ((ctx: Readonly<CommandContext<G>>, result: string | undefined) => Awaitable<void>) | undefined;
|
|
295
538
|
/**
|
|
296
539
|
* Hook that runs when a command throws an error
|
|
297
540
|
* @see {@link CliOptions.onErrorCommand}
|
|
541
|
+
* @since v0.27.0
|
|
298
542
|
*/
|
|
299
543
|
onErrorCommand: ((ctx: Readonly<CommandContext<G>>, error: Error) => Awaitable<void>) | undefined;
|
|
300
544
|
}
|
|
301
545
|
/**
|
|
302
546
|
* CLI options of `cli` function.
|
|
303
547
|
*/
|
|
304
|
-
|
|
548
|
+
interface CliOptions<G extends GunshiParamsConstraint = DefaultGunshiParams> {
|
|
549
|
+
/**
|
|
550
|
+
* Current working directory.
|
|
551
|
+
*/
|
|
552
|
+
cwd?: string;
|
|
553
|
+
/**
|
|
554
|
+
* Command program name.
|
|
555
|
+
*/
|
|
556
|
+
name?: string;
|
|
557
|
+
/**
|
|
558
|
+
* Command program description.
|
|
559
|
+
*
|
|
560
|
+
*/
|
|
561
|
+
description?: string;
|
|
562
|
+
/**
|
|
563
|
+
* Command program version.
|
|
564
|
+
*/
|
|
565
|
+
version?: string;
|
|
566
|
+
/**
|
|
567
|
+
* Sub commands.
|
|
568
|
+
*/
|
|
569
|
+
subCommands?: Map<string, Command<any> | LazyCommand<any>>;
|
|
570
|
+
/**
|
|
571
|
+
* Left margin of the command output.
|
|
572
|
+
*/
|
|
573
|
+
leftMargin?: number;
|
|
574
|
+
/**
|
|
575
|
+
* Middle margin of the command output.
|
|
576
|
+
*/
|
|
577
|
+
middleMargin?: number;
|
|
578
|
+
/**
|
|
579
|
+
* Whether to display the usage optional argument type.
|
|
580
|
+
*/
|
|
581
|
+
usageOptionType?: boolean;
|
|
582
|
+
/**
|
|
583
|
+
* Whether to display the optional argument value.
|
|
584
|
+
*/
|
|
585
|
+
usageOptionValue?: boolean;
|
|
586
|
+
/**
|
|
587
|
+
* Whether to display the command usage.
|
|
588
|
+
*/
|
|
589
|
+
usageSilent?: boolean;
|
|
590
|
+
/**
|
|
591
|
+
* Render function the command usage.
|
|
592
|
+
*/
|
|
593
|
+
renderUsage?: ((ctx: Readonly<CommandContext<G>>) => Promise<string>) | null;
|
|
594
|
+
/**
|
|
595
|
+
* Render function the header section in the command usage.
|
|
596
|
+
*/
|
|
597
|
+
renderHeader?: ((ctx: Readonly<CommandContext<G>>) => Promise<string>) | null;
|
|
598
|
+
/**
|
|
599
|
+
* Render function the validation errors.
|
|
600
|
+
*/
|
|
601
|
+
renderValidationErrors?: ((ctx: Readonly<CommandContext<G>>, error: AggregateError) => Promise<string>) | null;
|
|
602
|
+
/**
|
|
603
|
+
* User plugins.
|
|
604
|
+
* @since v0.27.0
|
|
605
|
+
*/
|
|
606
|
+
plugins?: Plugin[];
|
|
607
|
+
/**
|
|
608
|
+
* Hook that runs before any command execution
|
|
609
|
+
* @param ctx - The command context
|
|
610
|
+
* @since v0.27.0
|
|
611
|
+
*/
|
|
612
|
+
onBeforeCommand?: (ctx: Readonly<CommandContext<G>>) => Awaitable<void>;
|
|
613
|
+
/**
|
|
614
|
+
* Hook that runs after successful command execution
|
|
615
|
+
* @param ctx - The command context
|
|
616
|
+
* @param result - The command execution result
|
|
617
|
+
* @since v0.27.0
|
|
618
|
+
*/
|
|
619
|
+
onAfterCommand?: (ctx: Readonly<CommandContext<G>>, result: string | undefined) => Awaitable<void>;
|
|
620
|
+
/**
|
|
621
|
+
* Hook that runs when a command throws an error
|
|
622
|
+
* @param ctx - The command context
|
|
623
|
+
* @param error - The error thrown during execution
|
|
624
|
+
* @since v0.27.0
|
|
625
|
+
*/
|
|
626
|
+
onErrorCommand?: (ctx: Readonly<CommandContext<G>>, error: Error) => Awaitable<void>;
|
|
627
|
+
}
|
|
305
628
|
/**
|
|
306
629
|
* Command call mode.
|
|
307
630
|
*/
|
|
@@ -331,6 +654,15 @@ interface CommandContext<G extends GunshiParamsConstraint = DefaultGunshiParams>
|
|
|
331
654
|
* The command arguments is same {@link Command.args}.
|
|
332
655
|
*/
|
|
333
656
|
args: ExtractArgs<G>;
|
|
657
|
+
/**
|
|
658
|
+
* Whether arguments were explicitly provided by the user.
|
|
659
|
+
*
|
|
660
|
+
* - `true`: The argument was explicitly provided via command line
|
|
661
|
+
* - `false`: The argument was not explicitly provided. This means either:
|
|
662
|
+
* - The value comes from a default value defined in the argument schema
|
|
663
|
+
* - The value is `undefined` (no explicit input and no default value)
|
|
664
|
+
*/
|
|
665
|
+
explicit: ExtractArgExplicitlyProvided<G>;
|
|
334
666
|
/**
|
|
335
667
|
* Command values, that is the values of the command that is executed.
|
|
336
668
|
* Resolve values with `resolveArgs` from command arguments and {@link Command.args}.
|
|
@@ -377,9 +709,10 @@ interface CommandContext<G extends GunshiParamsConstraint = DefaultGunshiParams>
|
|
|
377
709
|
*/
|
|
378
710
|
log: (message?: any, ...optionalParams: any[]) => void;
|
|
379
711
|
/**
|
|
380
|
-
*
|
|
712
|
+
* Command context extensions.
|
|
713
|
+
* @since v0.27.0
|
|
381
714
|
*/
|
|
382
|
-
extensions: keyof ExtractExtensions<G> extends never ? undefined : ExtractExtensions<G>;
|
|
715
|
+
extensions: keyof ExtractExtensions$1<G> extends never ? undefined : ExtractExtensions$1<G>;
|
|
383
716
|
/**
|
|
384
717
|
* Validation error from argument parsing.
|
|
385
718
|
* This will be set if argument validation fails during CLI execution.
|
|
@@ -388,16 +721,45 @@ interface CommandContext<G extends GunshiParamsConstraint = DefaultGunshiParams>
|
|
|
388
721
|
}
|
|
389
722
|
/**
|
|
390
723
|
* CommandContextCore type (base type without extensions)
|
|
724
|
+
* @since v0.27.0
|
|
391
725
|
*/
|
|
392
726
|
type CommandContextCore<G extends GunshiParamsConstraint = DefaultGunshiParams> = Readonly<CommandContext<G>>;
|
|
393
727
|
/**
|
|
394
728
|
* Command context extension
|
|
729
|
+
* @since v0.27.0
|
|
395
730
|
*/
|
|
396
731
|
interface CommandContextExtension<E extends GunshiParams['extensions'] = DefaultGunshiParams['extensions']> {
|
|
397
732
|
readonly key: symbol;
|
|
398
733
|
readonly factory: (ctx: CommandContextCore, cmd: Command) => Awaitable<E>;
|
|
399
734
|
readonly onFactory?: (ctx: Readonly<CommandContext>, cmd: Readonly<Command>) => Awaitable<void>;
|
|
400
735
|
}
|
|
736
|
+
/**
|
|
737
|
+
* Rendering control options
|
|
738
|
+
* @since v0.27.0
|
|
739
|
+
*/
|
|
740
|
+
interface RenderingOptions<G extends GunshiParamsConstraint = DefaultGunshiParams> {
|
|
741
|
+
/**
|
|
742
|
+
* Header rendering configuration
|
|
743
|
+
* - `null`: Disable rendering
|
|
744
|
+
* - `function`: Use custom renderer
|
|
745
|
+
* - `undefined` (when omitted): Use default renderer
|
|
746
|
+
*/
|
|
747
|
+
header?: ((ctx: Readonly<CommandContext<G>>) => Promise<string>) | null;
|
|
748
|
+
/**
|
|
749
|
+
* Usage rendering configuration
|
|
750
|
+
* - `null`: Disable rendering
|
|
751
|
+
* - `function`: Use custom renderer
|
|
752
|
+
* - `undefined` (when omitted): Use default renderer
|
|
753
|
+
*/
|
|
754
|
+
usage?: ((ctx: Readonly<CommandContext<G>>) => Promise<string>) | null;
|
|
755
|
+
/**
|
|
756
|
+
* Validation errors rendering configuration
|
|
757
|
+
* - `null`: Disable rendering
|
|
758
|
+
* - `function`: Use custom renderer
|
|
759
|
+
* - `undefined` (when omitted): Use default renderer
|
|
760
|
+
*/
|
|
761
|
+
validationErrors?: ((ctx: Readonly<CommandContext<G>>, error: AggregateError) => Promise<string>) | null;
|
|
762
|
+
}
|
|
401
763
|
/**
|
|
402
764
|
* Command interface.
|
|
403
765
|
*/
|
|
@@ -431,6 +793,24 @@ interface Command<G extends GunshiParamsConstraint = DefaultGunshiParams> {
|
|
|
431
793
|
* If you will set to `true`, All {@link Command.args} names will be converted to kebab-case.
|
|
432
794
|
*/
|
|
433
795
|
toKebab?: boolean;
|
|
796
|
+
/**
|
|
797
|
+
* Whether this is an internal command.
|
|
798
|
+
* Internal commands are not shown in help usage.
|
|
799
|
+
* @default false
|
|
800
|
+
* @since v0.27.0
|
|
801
|
+
*/
|
|
802
|
+
internal?: boolean;
|
|
803
|
+
/**
|
|
804
|
+
* Whether this command is an entry command.
|
|
805
|
+
* @default undefined
|
|
806
|
+
* @since v0.27.0
|
|
807
|
+
*/
|
|
808
|
+
entry?: boolean;
|
|
809
|
+
/**
|
|
810
|
+
* Rendering control options
|
|
811
|
+
* @since v0.27.0
|
|
812
|
+
*/
|
|
813
|
+
rendering?: RenderingOptions<G>;
|
|
434
814
|
}
|
|
435
815
|
/**
|
|
436
816
|
* Lazy command interface.
|
|
@@ -461,7 +841,7 @@ type CommandExamplesFetcher<G extends GunshiParamsConstraint = DefaultGunshiPara
|
|
|
461
841
|
* @param ctx A {@link CommandContext | command context}
|
|
462
842
|
* @returns void or string (for CLI output)
|
|
463
843
|
*/
|
|
464
|
-
type CommandRunner<G extends GunshiParamsConstraint = DefaultGunshiParams> = (ctx: Readonly<CommandContext<G>>) => Awaitable<
|
|
844
|
+
type CommandRunner<G extends GunshiParamsConstraint = DefaultGunshiParams> = (ctx: Readonly<CommandContext<G>>) => Awaitable<string | void>;
|
|
465
845
|
/**
|
|
466
846
|
* Command loader.
|
|
467
847
|
* A function that returns a command or command runner.
|
|
@@ -474,14 +854,16 @@ type CommandRunner<G extends GunshiParamsConstraint = DefaultGunshiParams> = (ct
|
|
|
474
854
|
* A function that wraps a command runner to add or modify its behavior.
|
|
475
855
|
* @param baseRunner The base command runner to decorate
|
|
476
856
|
* @returns The decorated command runner
|
|
857
|
+
* @since v0.27.0
|
|
477
858
|
*/
|
|
478
|
-
type CommandDecorator<G extends GunshiParamsConstraint = DefaultGunshiParams> = (baseRunner: (ctx: Readonly<CommandContext<G>>) => Awaitable<
|
|
859
|
+
type CommandDecorator<G extends GunshiParamsConstraint = DefaultGunshiParams> = (baseRunner: (ctx: Readonly<CommandContext<G>>) => Awaitable<string | void>) => (ctx: Readonly<CommandContext<G>>) => Awaitable<string | void>;
|
|
479
860
|
/**
|
|
480
861
|
* Renderer decorator type.
|
|
481
862
|
* A function that wraps a base renderer to add or modify its behavior.
|
|
482
863
|
* @param baseRenderer The base renderer function to decorate
|
|
483
864
|
* @param ctx The command context
|
|
484
865
|
* @returns The decorated result
|
|
866
|
+
* @since v0.27.0
|
|
485
867
|
*/
|
|
486
868
|
type RendererDecorator<T, G extends GunshiParamsConstraint = DefaultGunshiParams> = (baseRenderer: (ctx: Readonly<CommandContext<G>>) => Promise<T>, ctx: Readonly<CommandContext<G>>) => Promise<T>;
|
|
487
869
|
/**
|
|
@@ -491,177 +873,101 @@ type RendererDecorator<T, G extends GunshiParamsConstraint = DefaultGunshiParams
|
|
|
491
873
|
* @param ctx The command context
|
|
492
874
|
* @param error The aggregate error containing validation errors
|
|
493
875
|
* @returns The decorated result
|
|
876
|
+
* @since v0.27.0
|
|
494
877
|
*/
|
|
495
|
-
type ValidationErrorsDecorator<G extends GunshiParamsConstraint = DefaultGunshiParams> = (baseRenderer: (ctx: Readonly<CommandContext<G>>, error: AggregateError) => Promise<string>, ctx: Readonly<CommandContext<G>>, error: AggregateError) => Promise<string>;
|
|
496
|
-
//#
|
|
878
|
+
type ValidationErrorsDecorator<G extends GunshiParamsConstraint = DefaultGunshiParams> = (baseRenderer: (ctx: Readonly<CommandContext<G>>, error: AggregateError) => Promise<string>, ctx: Readonly<CommandContext<G>>, error: AggregateError) => Promise<string>;
|
|
879
|
+
//#endregion
|
|
880
|
+
//#region ../gunshi/src/constants.d.ts
|
|
881
|
+
declare const ANONYMOUS_COMMAND_NAME = "(anonymous)";
|
|
882
|
+
declare const CLI_OPTIONS_DEFAULT: CliOptions<DefaultGunshiParams>;
|
|
883
|
+
//#endregion
|
|
884
|
+
//#region ../gunshi/src/context.d.ts
|
|
497
885
|
/**
|
|
498
|
-
*
|
|
886
|
+
* Extract extension return types from extensions record
|
|
499
887
|
* @internal
|
|
500
888
|
*/
|
|
501
|
-
type
|
|
502
|
-
args: ExtractArgs<G>;
|
|
503
|
-
extensions: ExtractExtensions<G> & L;
|
|
504
|
-
};
|
|
889
|
+
type ExtractExtensions<E extends Record<string, CommandContextExtension>> = { [K in keyof E]: E[K] extends CommandContextExtension<infer T> ? T : never };
|
|
505
890
|
/**
|
|
506
|
-
*
|
|
891
|
+
* Parameters of {@link createCommandContext}
|
|
507
892
|
*/
|
|
508
|
-
interface
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
* @returns A map of global options.
|
|
512
|
-
*/
|
|
513
|
-
readonly globalOptions: Map<string, ArgSchema>;
|
|
893
|
+
interface CommandContextParams<G extends GunshiParams | {
|
|
894
|
+
extensions: ExtendContext;
|
|
895
|
+
}, V extends ArgValues<ExtractArgs<G>>, C extends Command<G> | LazyCommand<G> = Command<G>, E extends Record<string, CommandContextExtension> = Record<string, CommandContextExtension>> {
|
|
514
896
|
/**
|
|
515
|
-
*
|
|
516
|
-
* @param name An option name
|
|
517
|
-
* @param schema An {@link ArgSchema} for the option
|
|
897
|
+
* An arguments of target command
|
|
518
898
|
*/
|
|
519
|
-
|
|
899
|
+
args: ExtractArgs<G>;
|
|
520
900
|
/**
|
|
521
|
-
*
|
|
522
|
-
* @param decorator - A decorator function that wraps the base header renderer.
|
|
901
|
+
* Explicitly provided arguments
|
|
523
902
|
*/
|
|
524
|
-
|
|
903
|
+
explicit: ExtractArgExplicitlyProvided<G>;
|
|
525
904
|
/**
|
|
526
|
-
*
|
|
527
|
-
* @param decorator - A decorator function that wraps the base usage renderer.
|
|
905
|
+
* A values of target command
|
|
528
906
|
*/
|
|
529
|
-
|
|
907
|
+
values: V;
|
|
530
908
|
/**
|
|
531
|
-
*
|
|
532
|
-
* @param decorator - A decorator function that wraps the base validation errors renderer.
|
|
909
|
+
* A positionals arguments, which passed to the target command
|
|
533
910
|
*/
|
|
534
|
-
|
|
911
|
+
positionals: string[];
|
|
535
912
|
/**
|
|
536
|
-
*
|
|
537
|
-
* Decorators are applied in reverse order (last registered is executed first).
|
|
538
|
-
* @param decorator - A decorator function that wraps the command runner
|
|
913
|
+
* A rest arguments, which passed to the target command
|
|
539
914
|
*/
|
|
540
|
-
|
|
541
|
-
}
|
|
542
|
-
|
|
543
|
-
//#endregion
|
|
544
|
-
//#region ../gunshi/src/plugin/core.d.ts
|
|
545
|
-
/**
|
|
546
|
-
* Factory function for creating a plugin context.
|
|
547
|
-
* @param decorators - A {@link Decorators} instance.
|
|
548
|
-
* @returns A new {@link PluginContext} instance.
|
|
549
|
-
*/
|
|
550
|
-
/**
|
|
551
|
-
* Plugin dependency definition
|
|
552
|
-
*/
|
|
553
|
-
interface PluginDependency {
|
|
915
|
+
rest: string[];
|
|
554
916
|
/**
|
|
555
|
-
*
|
|
917
|
+
* Original command line arguments
|
|
556
918
|
*/
|
|
557
|
-
|
|
919
|
+
argv: string[];
|
|
558
920
|
/**
|
|
559
|
-
*
|
|
560
|
-
* If true, the plugin will not throw an error if the dependency is not found.
|
|
921
|
+
* Argument tokens that are parsed by the `parseArgs` function
|
|
561
922
|
*/
|
|
562
|
-
|
|
563
|
-
}
|
|
564
|
-
/**
|
|
565
|
-
* Plugin function type
|
|
566
|
-
*/
|
|
567
|
-
type PluginFunction<G extends GunshiParams = DefaultGunshiParams> = (ctx: Readonly<PluginContext<G>>) => Awaitable<void>;
|
|
568
|
-
/**
|
|
569
|
-
* Plugin extension for CommandContext
|
|
570
|
-
*/
|
|
571
|
-
type PluginExtension<T = Record<string, unknown>, G extends GunshiParams = DefaultGunshiParams> = (ctx: CommandContextCore<G>, cmd: Command<G>) => T;
|
|
572
|
-
/**
|
|
573
|
-
* Plugin extension callback type
|
|
574
|
-
*/
|
|
575
|
-
type OnPluginExtension<G extends GunshiParams = DefaultGunshiParams> = (ctx: Readonly<CommandContext<G>>, cmd: Readonly<Command<G>>) => void;
|
|
576
|
-
/**
|
|
577
|
-
* Plugin definition options
|
|
578
|
-
*/
|
|
579
|
-
interface PluginOptions<T extends Record<string, unknown> = Record<never, never>, G extends GunshiParams = DefaultGunshiParams> {
|
|
923
|
+
tokens: ArgToken[];
|
|
580
924
|
/**
|
|
581
|
-
*
|
|
925
|
+
* Whether the command is omitted
|
|
582
926
|
*/
|
|
583
|
-
|
|
927
|
+
omitted: boolean;
|
|
584
928
|
/**
|
|
585
|
-
*
|
|
929
|
+
* Command call mode.
|
|
586
930
|
*/
|
|
587
|
-
|
|
931
|
+
callMode: CommandCallMode;
|
|
588
932
|
/**
|
|
589
|
-
*
|
|
933
|
+
* A target command
|
|
590
934
|
*/
|
|
591
|
-
|
|
935
|
+
command: C;
|
|
592
936
|
/**
|
|
593
|
-
* Plugin
|
|
937
|
+
* Plugin extensions to apply as the command context extension.
|
|
594
938
|
*/
|
|
595
|
-
|
|
939
|
+
extensions?: E;
|
|
596
940
|
/**
|
|
597
|
-
*
|
|
941
|
+
* A command options, which is spicialized from `cli` function
|
|
598
942
|
*/
|
|
599
|
-
|
|
943
|
+
cliOptions: CliOptions<G>;
|
|
600
944
|
/**
|
|
601
|
-
*
|
|
945
|
+
* Validation error from argument parsing.
|
|
602
946
|
*/
|
|
603
|
-
|
|
604
|
-
}
|
|
605
|
-
/**
|
|
606
|
-
* Gunshi plugin, which is a function that receives a PluginContext.
|
|
607
|
-
* @param ctx - A {@link PluginContext}.
|
|
608
|
-
* @returns An {@link Awaitable} that resolves when the plugin is loaded.
|
|
609
|
-
*/
|
|
610
|
-
type Plugin<E extends GunshiParams['extensions'] = DefaultGunshiParams['extensions']> = PluginFunction & {
|
|
611
|
-
id: string;
|
|
612
|
-
name?: string;
|
|
613
|
-
dependencies?: (PluginDependency | string)[];
|
|
614
|
-
extension?: CommandContextExtension<E>;
|
|
615
|
-
};
|
|
616
|
-
/**
|
|
617
|
-
* Plugin return type with extension
|
|
618
|
-
* @internal
|
|
619
|
-
*/
|
|
620
|
-
interface PluginWithExtension<E extends GunshiParams['extensions'] = DefaultGunshiParams['extensions']> extends Plugin<E> {
|
|
621
|
-
id: string;
|
|
622
|
-
name: string;
|
|
623
|
-
dependencies?: (PluginDependency | string)[];
|
|
624
|
-
extension: CommandContextExtension<E>;
|
|
625
|
-
}
|
|
626
|
-
/**
|
|
627
|
-
* Plugin return type without extension
|
|
628
|
-
* @internal
|
|
629
|
-
*/
|
|
630
|
-
interface PluginWithoutExtension<E extends GunshiParams['extensions'] = DefaultGunshiParams['extensions']> extends Plugin<E> {
|
|
631
|
-
id: string;
|
|
632
|
-
name: string;
|
|
633
|
-
dependencies?: (PluginDependency | string)[];
|
|
947
|
+
validationError?: AggregateError;
|
|
634
948
|
}
|
|
635
949
|
/**
|
|
636
|
-
*
|
|
637
|
-
* @param
|
|
638
|
-
* @
|
|
639
|
-
*/
|
|
640
|
-
declare function
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
*/
|
|
659
|
-
declare function plugin(options: {
|
|
660
|
-
id: string;
|
|
661
|
-
name?: string;
|
|
662
|
-
dependencies?: (PluginDependency | string)[];
|
|
663
|
-
setup?: (ctx: Readonly<PluginContext<DefaultGunshiParams>>) => Awaitable<void>;
|
|
664
|
-
}): PluginWithoutExtension<DefaultGunshiParams['extensions']>;
|
|
665
|
-
|
|
950
|
+
* Create a {@link CommandContext | command context}
|
|
951
|
+
* @param param A {@link CommandContextParams | parameters} to create a {@link CommandContext | command context}
|
|
952
|
+
* @returns A {@link CommandContext | command context}, which is readonly
|
|
953
|
+
*/
|
|
954
|
+
declare function createCommandContext<G extends GunshiParamsConstraint = DefaultGunshiParams, V extends ArgValues<ExtractArgs<G>> = ArgValues<ExtractArgs<G>>, C extends Command<G> | LazyCommand<G> = Command<G>, E extends Record<string, CommandContextExtension> = {}>({
|
|
955
|
+
args,
|
|
956
|
+
explicit,
|
|
957
|
+
values,
|
|
958
|
+
positionals,
|
|
959
|
+
rest,
|
|
960
|
+
argv,
|
|
961
|
+
tokens,
|
|
962
|
+
command,
|
|
963
|
+
extensions,
|
|
964
|
+
cliOptions,
|
|
965
|
+
callMode,
|
|
966
|
+
omitted,
|
|
967
|
+
validationError
|
|
968
|
+
}: CommandContextParams<G, V, C, E>): Promise<{} extends ExtractExtensions<E> ? Readonly<CommandContext<G>> : Readonly<CommandContext<GunshiParams<{
|
|
969
|
+
args: ExtractArgs<G>;
|
|
970
|
+
extensions: ExtractExtensions<E>;
|
|
971
|
+
}>>>>;
|
|
666
972
|
//#endregion
|
|
667
|
-
export { ArgSchema, ArgToken, ArgValues, Args, Awaitable, Command, CommandContext, CommandContextCore, CommandDecorator, CommandExamplesFetcher, CommandRunner, DefaultGunshiParams, ExtendContext, ExtractArgs, GunshiParams, GunshiParamsConstraint, LazyCommand, NormalizeToGunshiParams, OnPluginExtension, Plugin, PluginContext, PluginDependency, PluginExtension, PluginFunction, PluginOptions, PluginWithExtension, PluginWithoutExtension, RendererDecorator, ValidationErrorsDecorator, plugin };
|
|
973
|
+
export { ANONYMOUS_COMMAND_NAME, type ArgSchema, type ArgToken, type ArgValues, type Args, Awaitable, CLI_OPTIONS_DEFAULT, Command, CommandContext, CommandContextCore, CommandContextExtension, CommandDecorator, CommandExamplesFetcher, CommandRunner, DefaultGunshiParams, ExtendContext, ExtractArgs, GunshiParams, GunshiParamsConstraint, LazyCommand, NormalizeToGunshiParams, OnPluginExtension, Plugin, PluginContext, PluginDependency, PluginExtension, PluginFunction, PluginOptions, PluginWithExtension, PluginWithoutExtension, RendererDecorator, ValidationErrorsDecorator, createCommandContext, plugin };
|
package/lib/index.js
CHANGED
|
@@ -1,11 +1,131 @@
|
|
|
1
|
+
//#region ../gunshi/src/constants.ts
|
|
2
|
+
const ANONYMOUS_COMMAND_NAME = "(anonymous)";
|
|
3
|
+
const NOOP = () => {};
|
|
4
|
+
const CLI_OPTIONS_DEFAULT = {
|
|
5
|
+
name: void 0,
|
|
6
|
+
description: void 0,
|
|
7
|
+
version: void 0,
|
|
8
|
+
cwd: void 0,
|
|
9
|
+
usageSilent: false,
|
|
10
|
+
subCommands: void 0,
|
|
11
|
+
leftMargin: 2,
|
|
12
|
+
middleMargin: 10,
|
|
13
|
+
usageOptionType: false,
|
|
14
|
+
usageOptionValue: true,
|
|
15
|
+
renderHeader: void 0,
|
|
16
|
+
renderUsage: void 0,
|
|
17
|
+
renderValidationErrors: void 0,
|
|
18
|
+
plugins: void 0
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
//#endregion
|
|
22
|
+
//#region ../gunshi/src/utils.ts
|
|
23
|
+
function isLazyCommand(cmd) {
|
|
24
|
+
return typeof cmd === "function" && "commandName" in cmd && !!cmd.commandName;
|
|
25
|
+
}
|
|
26
|
+
function create(obj = null) {
|
|
27
|
+
return Object.create(obj);
|
|
28
|
+
}
|
|
29
|
+
function log(...args) {
|
|
30
|
+
console.log(...args);
|
|
31
|
+
}
|
|
32
|
+
function deepFreeze(obj, ignores = []) {
|
|
33
|
+
if (obj === null || typeof obj !== "object") return obj;
|
|
34
|
+
for (const key of Object.keys(obj)) {
|
|
35
|
+
const value = obj[key];
|
|
36
|
+
if (ignores.includes(key)) continue;
|
|
37
|
+
if (typeof value === "object" && value !== null) deepFreeze(value, ignores);
|
|
38
|
+
}
|
|
39
|
+
return Object.freeze(obj);
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
//#endregion
|
|
43
|
+
//#region ../gunshi/src/context.ts
|
|
44
|
+
/**
|
|
45
|
+
* Create a {@link CommandContext | command context}
|
|
46
|
+
* @param param A {@link CommandContextParams | parameters} to create a {@link CommandContext | command context}
|
|
47
|
+
* @returns A {@link CommandContext | command context}, which is readonly
|
|
48
|
+
*/
|
|
49
|
+
async function createCommandContext({ args, explicit, values, positionals, rest, argv, tokens, command, extensions = {}, cliOptions, callMode = "entry", omitted = false, validationError }) {
|
|
50
|
+
/**
|
|
51
|
+
* normailize the options schema and values, to avoid prototype pollution
|
|
52
|
+
*/
|
|
53
|
+
const _args = Object.entries(args).reduce((acc, [key, value]) => {
|
|
54
|
+
acc[key] = Object.assign(create(), value);
|
|
55
|
+
return acc;
|
|
56
|
+
}, create());
|
|
57
|
+
/**
|
|
58
|
+
* setup the environment
|
|
59
|
+
*/
|
|
60
|
+
const env = Object.assign(create(), CLI_OPTIONS_DEFAULT, cliOptions);
|
|
61
|
+
/**
|
|
62
|
+
* apply Command definition's rendering option with highest priority
|
|
63
|
+
*/
|
|
64
|
+
if (command.rendering) {
|
|
65
|
+
const { header, usage, validationErrors } = command.rendering;
|
|
66
|
+
if (header !== void 0) env.renderHeader = header;
|
|
67
|
+
if (usage !== void 0) env.renderUsage = usage;
|
|
68
|
+
if (validationErrors !== void 0) env.renderValidationErrors = validationErrors;
|
|
69
|
+
}
|
|
70
|
+
/**
|
|
71
|
+
* create the command context
|
|
72
|
+
*/
|
|
73
|
+
const core = Object.assign(create(), {
|
|
74
|
+
name: getCommandName(command),
|
|
75
|
+
description: command.description,
|
|
76
|
+
omitted,
|
|
77
|
+
callMode,
|
|
78
|
+
env,
|
|
79
|
+
args: _args,
|
|
80
|
+
explicit,
|
|
81
|
+
values,
|
|
82
|
+
positionals,
|
|
83
|
+
rest,
|
|
84
|
+
_: argv,
|
|
85
|
+
tokens,
|
|
86
|
+
toKebab: command.toKebab,
|
|
87
|
+
log: cliOptions.usageSilent ? NOOP : log,
|
|
88
|
+
validationError
|
|
89
|
+
});
|
|
90
|
+
/**
|
|
91
|
+
* extend the command context with extensions
|
|
92
|
+
*/
|
|
93
|
+
if (Object.keys(extensions).length > 0) {
|
|
94
|
+
const ext = create(null);
|
|
95
|
+
Object.defineProperty(core, "extensions", {
|
|
96
|
+
value: ext,
|
|
97
|
+
writable: false,
|
|
98
|
+
enumerable: true,
|
|
99
|
+
configurable: true
|
|
100
|
+
});
|
|
101
|
+
for (const [key, extension] of Object.entries(extensions)) {
|
|
102
|
+
ext[key] = await extension.factory(core, command);
|
|
103
|
+
if (extension.onFactory) await extension.onFactory(core, command);
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
const ctx = deepFreeze(core, ["extensions"]);
|
|
107
|
+
return ctx;
|
|
108
|
+
}
|
|
109
|
+
function getCommandName(cmd) {
|
|
110
|
+
if (isLazyCommand(cmd)) return cmd.commandName || cmd.name || ANONYMOUS_COMMAND_NAME;
|
|
111
|
+
else if (typeof cmd === "object") return cmd.name || ANONYMOUS_COMMAND_NAME;
|
|
112
|
+
else return ANONYMOUS_COMMAND_NAME;
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
//#endregion
|
|
1
116
|
//#region ../gunshi/src/plugin/core.ts
|
|
117
|
+
const NOOP_EXTENSION = () => {
|
|
118
|
+
return Object.create(null);
|
|
119
|
+
};
|
|
2
120
|
/**
|
|
3
121
|
* Define a plugin
|
|
4
122
|
* @param options - {@link PluginOptions | plugin options}
|
|
5
123
|
* @returns A defined plugin.
|
|
124
|
+
* @since v0.27.0
|
|
6
125
|
*/
|
|
7
126
|
function plugin(options) {
|
|
8
|
-
const { id, name, setup,
|
|
127
|
+
const { id, name, setup, onExtension, dependencies } = options;
|
|
128
|
+
const extension = options.extension || NOOP_EXTENSION;
|
|
9
129
|
const pluginFn = async (ctx) => {
|
|
10
130
|
if (setup) await setup(ctx);
|
|
11
131
|
};
|
|
@@ -42,4 +162,4 @@ function plugin(options) {
|
|
|
42
162
|
}
|
|
43
163
|
|
|
44
164
|
//#endregion
|
|
45
|
-
export { plugin };
|
|
165
|
+
export { ANONYMOUS_COMMAND_NAME, CLI_OPTIONS_DEFAULT, createCommandContext, plugin };
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@gunshi/plugin",
|
|
3
3
|
"description": "utilities for gunshi plugin",
|
|
4
|
-
"version": "0.
|
|
4
|
+
"version": "0.27.0-alpha.10",
|
|
5
5
|
"author": {
|
|
6
6
|
"name": "kazuya kawaguchi",
|
|
7
7
|
"email": "kawakazu80@gmail.com"
|
|
@@ -51,12 +51,12 @@
|
|
|
51
51
|
}
|
|
52
52
|
},
|
|
53
53
|
"devDependencies": {
|
|
54
|
-
"deno": "^2.
|
|
55
|
-
"jsr": "^0.13.
|
|
54
|
+
"deno": "^2.4.2",
|
|
55
|
+
"jsr": "^0.13.5",
|
|
56
56
|
"jsr-exports-lint": "^0.4.1",
|
|
57
57
|
"publint": "^0.3.12",
|
|
58
|
-
"tsdown": "^0.
|
|
59
|
-
"gunshi": "0.
|
|
58
|
+
"tsdown": "^0.13.0",
|
|
59
|
+
"gunshi": "0.27.0-alpha.10"
|
|
60
60
|
},
|
|
61
61
|
"scripts": {
|
|
62
62
|
"build": "tsdown",
|