@kinotic-ai/kinotic-cli 2.2.0 → 3.0.0

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 (33) hide show
  1. package/README.md +1 -393
  2. package/dist/commands/create/project.d.ts +5 -1
  3. package/dist/commands/create/project.js +17 -11
  4. package/dist/commands/generate.d.ts +2 -2
  5. package/dist/commands/initialize.d.ts +4 -4
  6. package/dist/commands/login.d.ts +9 -0
  7. package/dist/commands/login.js +21 -0
  8. package/dist/commands/spawn/lint.d.ts +13 -0
  9. package/dist/commands/spawn/lint.js +51 -0
  10. package/dist/commands/synchronize.d.ts +5 -6
  11. package/dist/commands/synchronize.js +39 -38
  12. package/dist/internal/CliAuthenticator.d.ts +46 -0
  13. package/dist/internal/CliAuthenticator.js +211 -0
  14. package/dist/internal/Logger.d.ts +1 -1
  15. package/dist/internal/Utils.d.ts +0 -16
  16. package/dist/internal/Utils.js +0 -156
  17. package/dist/internal/spawn/FileSystemSpawnEngine.d.ts +23 -0
  18. package/dist/internal/spawn/FileSystemSpawnEngine.js +33 -0
  19. package/dist/internal/spawn/InquirerPropertyResolver.d.ts +9 -0
  20. package/dist/internal/spawn/InquirerPropertyResolver.js +30 -0
  21. package/dist/templates/entity/BaseRepository.liquid +2 -2
  22. package/dist/templates/spawns/project/package.json.liquid +2 -2
  23. package/dist/templates/spawns/project/spawn.json +10 -1
  24. package/package.json +19 -34
  25. package/bin/dev.cmd +0 -3
  26. package/bin/dev.js +0 -6
  27. package/bin/run.cmd +0 -3
  28. package/bin/run.js +0 -6
  29. package/dist/internal/spawn/SpawnConfig.d.ts +0 -31
  30. package/dist/internal/spawn/SpawnConfig.js +0 -12
  31. package/dist/internal/spawn/SpawnEngine.d.ts +0 -27
  32. package/dist/internal/spawn/SpawnEngine.js +0 -187
  33. package/oclif.manifest.json +0 -213
package/README.md CHANGED
@@ -1,4 +1,4 @@
1
- Structures CLI
1
+ Kinotic CLI
2
2
  =================
3
3
 
4
4
  <!-- toc -->
@@ -21,57 +21,13 @@ USAGE
21
21
  <!-- usagestop -->
22
22
  # Commands
23
23
  <!-- commands -->
24
- * [`kinotic autocomplete [SHELL]`](#kinotic-autocomplete-shell)
25
24
  * [`kinotic create project NAME`](#kinotic-create-project-name)
26
25
  * [`kinotic gen`](#kinotic-gen)
27
26
  * [`kinotic generate`](#kinotic-generate)
28
- * [`kinotic help [COMMAND]`](#kinotic-help-command)
29
27
  * [`kinotic init`](#kinotic-init)
30
28
  * [`kinotic initialize`](#kinotic-initialize)
31
- * [`kinotic plugins`](#kinotic-plugins)
32
- * [`kinotic plugins add PLUGIN`](#kinotic-plugins-add-plugin)
33
- * [`kinotic plugins:inspect PLUGIN...`](#kinotic-pluginsinspect-plugin)
34
- * [`kinotic plugins install PLUGIN`](#kinotic-plugins-install-plugin)
35
- * [`kinotic plugins link PATH`](#kinotic-plugins-link-path)
36
- * [`kinotic plugins remove [PLUGIN]`](#kinotic-plugins-remove-plugin)
37
- * [`kinotic plugins reset`](#kinotic-plugins-reset)
38
- * [`kinotic plugins uninstall [PLUGIN]`](#kinotic-plugins-uninstall-plugin)
39
- * [`kinotic plugins unlink [PLUGIN]`](#kinotic-plugins-unlink-plugin)
40
- * [`kinotic plugins update`](#kinotic-plugins-update)
41
29
  * [`kinotic sync`](#kinotic-sync)
42
30
  * [`kinotic synchronize`](#kinotic-synchronize)
43
- * [`kinotic update [CHANNEL]`](#kinotic-update-channel)
44
-
45
- ## `kinotic autocomplete [SHELL]`
46
-
47
- Display autocomplete installation instructions.
48
-
49
- ```
50
- USAGE
51
- $ kinotic autocomplete [SHELL] [-r]
52
-
53
- ARGUMENTS
54
- [SHELL] (zsh|bash|powershell) Shell type
55
-
56
- FLAGS
57
- -r, --refresh-cache Refresh cache (ignores displaying instructions)
58
-
59
- DESCRIPTION
60
- Display autocomplete installation instructions.
61
-
62
- EXAMPLES
63
- $ kinotic autocomplete
64
-
65
- $ kinotic autocomplete bash
66
-
67
- $ kinotic autocomplete zsh
68
-
69
- $ kinotic autocomplete powershell
70
-
71
- $ kinotic autocomplete --refresh-cache
72
- ```
73
-
74
- _See code: [@oclif/plugin-autocomplete](https://github.com/oclif/plugin-autocomplete/blob/v3.2.41/src/commands/autocomplete/index.ts)_
75
31
 
76
32
  ## `kinotic create project NAME`
77
33
 
@@ -151,26 +107,6 @@ EXAMPLES
151
107
 
152
108
  _See code: [src/commands/generate.ts](https://github.com/kinotic-ai/kinotic/blob/v2.2.0/src/commands/generate.ts)_
153
109
 
154
- ## `kinotic help [COMMAND]`
155
-
156
- Display help for kinotic.
157
-
158
- ```
159
- USAGE
160
- $ kinotic help [COMMAND...] [-n]
161
-
162
- ARGUMENTS
163
- [COMMAND...] Command to show help for.
164
-
165
- FLAGS
166
- -n, --nested-commands Include all nested commands in the output.
167
-
168
- DESCRIPTION
169
- Display help for kinotic.
170
- ```
171
-
172
- _See code: [@oclif/plugin-help](https://github.com/oclif/plugin-help/blob/6.2.38/src/commands/help.ts)_
173
-
174
110
  ## `kinotic init`
175
111
 
176
112
  This will initialize a new Kinotic Project for use with the Kinotic CLI.
@@ -233,296 +169,6 @@ EXAMPLES
233
169
 
234
170
  _See code: [src/commands/initialize.ts](https://github.com/kinotic-ai/kinotic/blob/v2.2.0/src/commands/initialize.ts)_
235
171
 
236
- ## `kinotic plugins`
237
-
238
- List installed plugins.
239
-
240
- ```
241
- USAGE
242
- $ kinotic plugins [--json] [--core]
243
-
244
- FLAGS
245
- --core Show core plugins.
246
-
247
- GLOBAL FLAGS
248
- --json Format output as json.
249
-
250
- DESCRIPTION
251
- List installed plugins.
252
-
253
- EXAMPLES
254
- $ kinotic plugins
255
- ```
256
-
257
- _See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/5.4.58/src/commands/plugins/index.ts)_
258
-
259
- ## `kinotic plugins add PLUGIN`
260
-
261
- Installs a plugin into kinotic.
262
-
263
- ```
264
- USAGE
265
- $ kinotic plugins add PLUGIN... [--json] [-f] [-h] [-s | -v]
266
-
267
- ARGUMENTS
268
- PLUGIN... Plugin to install.
269
-
270
- FLAGS
271
- -f, --force Force npm to fetch remote resources even if a local copy exists on disk.
272
- -h, --help Show CLI help.
273
- -s, --silent Silences npm output.
274
- -v, --verbose Show verbose npm output.
275
-
276
- GLOBAL FLAGS
277
- --json Format output as json.
278
-
279
- DESCRIPTION
280
- Installs a plugin into kinotic.
281
-
282
- Uses npm to install plugins.
283
-
284
- Installation of a user-installed plugin will override a core plugin.
285
-
286
- Use the KINOTIC_NPM_LOG_LEVEL environment variable to set the npm loglevel.
287
- Use the KINOTIC_NPM_REGISTRY environment variable to set the npm registry.
288
-
289
- ALIASES
290
- $ kinotic plugins add
291
-
292
- EXAMPLES
293
- Install a plugin from npm registry.
294
-
295
- $ kinotic plugins add myplugin
296
-
297
- Install a plugin from a github url.
298
-
299
- $ kinotic plugins add https://github.com/someuser/someplugin
300
-
301
- Install a plugin from a github slug.
302
-
303
- $ kinotic plugins add someuser/someplugin
304
- ```
305
-
306
- ## `kinotic plugins:inspect PLUGIN...`
307
-
308
- Displays installation properties of a plugin.
309
-
310
- ```
311
- USAGE
312
- $ kinotic plugins inspect PLUGIN...
313
-
314
- ARGUMENTS
315
- PLUGIN... [default: .] Plugin to inspect.
316
-
317
- FLAGS
318
- -h, --help Show CLI help.
319
- -v, --verbose
320
-
321
- GLOBAL FLAGS
322
- --json Format output as json.
323
-
324
- DESCRIPTION
325
- Displays installation properties of a plugin.
326
-
327
- EXAMPLES
328
- $ kinotic plugins inspect myplugin
329
- ```
330
-
331
- _See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/5.4.58/src/commands/plugins/inspect.ts)_
332
-
333
- ## `kinotic plugins install PLUGIN`
334
-
335
- Installs a plugin into kinotic.
336
-
337
- ```
338
- USAGE
339
- $ kinotic plugins install PLUGIN... [--json] [-f] [-h] [-s | -v]
340
-
341
- ARGUMENTS
342
- PLUGIN... Plugin to install.
343
-
344
- FLAGS
345
- -f, --force Force npm to fetch remote resources even if a local copy exists on disk.
346
- -h, --help Show CLI help.
347
- -s, --silent Silences npm output.
348
- -v, --verbose Show verbose npm output.
349
-
350
- GLOBAL FLAGS
351
- --json Format output as json.
352
-
353
- DESCRIPTION
354
- Installs a plugin into kinotic.
355
-
356
- Uses npm to install plugins.
357
-
358
- Installation of a user-installed plugin will override a core plugin.
359
-
360
- Use the KINOTIC_NPM_LOG_LEVEL environment variable to set the npm loglevel.
361
- Use the KINOTIC_NPM_REGISTRY environment variable to set the npm registry.
362
-
363
- ALIASES
364
- $ kinotic plugins add
365
-
366
- EXAMPLES
367
- Install a plugin from npm registry.
368
-
369
- $ kinotic plugins install myplugin
370
-
371
- Install a plugin from a github url.
372
-
373
- $ kinotic plugins install https://github.com/someuser/someplugin
374
-
375
- Install a plugin from a github slug.
376
-
377
- $ kinotic plugins install someuser/someplugin
378
- ```
379
-
380
- _See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/5.4.58/src/commands/plugins/install.ts)_
381
-
382
- ## `kinotic plugins link PATH`
383
-
384
- Links a plugin into the CLI for development.
385
-
386
- ```
387
- USAGE
388
- $ kinotic plugins link PATH [-h] [--install] [-v]
389
-
390
- ARGUMENTS
391
- PATH [default: .] path to plugin
392
-
393
- FLAGS
394
- -h, --help Show CLI help.
395
- -v, --verbose
396
- --[no-]install Install dependencies after linking the plugin.
397
-
398
- DESCRIPTION
399
- Links a plugin into the CLI for development.
400
-
401
- Installation of a linked plugin will override a user-installed or core plugin.
402
-
403
- e.g. If you have a user-installed or core plugin that has a 'hello' command, installing a linked plugin with a 'hello'
404
- command will override the user-installed or core plugin implementation. This is useful for development work.
405
-
406
-
407
- EXAMPLES
408
- $ kinotic plugins link myplugin
409
- ```
410
-
411
- _See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/5.4.58/src/commands/plugins/link.ts)_
412
-
413
- ## `kinotic plugins remove [PLUGIN]`
414
-
415
- Removes a plugin from the CLI.
416
-
417
- ```
418
- USAGE
419
- $ kinotic plugins remove [PLUGIN...] [-h] [-v]
420
-
421
- ARGUMENTS
422
- [PLUGIN...] plugin to uninstall
423
-
424
- FLAGS
425
- -h, --help Show CLI help.
426
- -v, --verbose
427
-
428
- DESCRIPTION
429
- Removes a plugin from the CLI.
430
-
431
- ALIASES
432
- $ kinotic plugins unlink
433
- $ kinotic plugins remove
434
-
435
- EXAMPLES
436
- $ kinotic plugins remove myplugin
437
- ```
438
-
439
- ## `kinotic plugins reset`
440
-
441
- Remove all user-installed and linked plugins.
442
-
443
- ```
444
- USAGE
445
- $ kinotic plugins reset [--hard] [--reinstall]
446
-
447
- FLAGS
448
- --hard Delete node_modules and package manager related files in addition to uninstalling plugins.
449
- --reinstall Reinstall all plugins after uninstalling.
450
- ```
451
-
452
- _See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/5.4.58/src/commands/plugins/reset.ts)_
453
-
454
- ## `kinotic plugins uninstall [PLUGIN]`
455
-
456
- Removes a plugin from the CLI.
457
-
458
- ```
459
- USAGE
460
- $ kinotic plugins uninstall [PLUGIN...] [-h] [-v]
461
-
462
- ARGUMENTS
463
- [PLUGIN...] plugin to uninstall
464
-
465
- FLAGS
466
- -h, --help Show CLI help.
467
- -v, --verbose
468
-
469
- DESCRIPTION
470
- Removes a plugin from the CLI.
471
-
472
- ALIASES
473
- $ kinotic plugins unlink
474
- $ kinotic plugins remove
475
-
476
- EXAMPLES
477
- $ kinotic plugins uninstall myplugin
478
- ```
479
-
480
- _See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/5.4.58/src/commands/plugins/uninstall.ts)_
481
-
482
- ## `kinotic plugins unlink [PLUGIN]`
483
-
484
- Removes a plugin from the CLI.
485
-
486
- ```
487
- USAGE
488
- $ kinotic plugins unlink [PLUGIN...] [-h] [-v]
489
-
490
- ARGUMENTS
491
- [PLUGIN...] plugin to uninstall
492
-
493
- FLAGS
494
- -h, --help Show CLI help.
495
- -v, --verbose
496
-
497
- DESCRIPTION
498
- Removes a plugin from the CLI.
499
-
500
- ALIASES
501
- $ kinotic plugins unlink
502
- $ kinotic plugins remove
503
-
504
- EXAMPLES
505
- $ kinotic plugins unlink myplugin
506
- ```
507
-
508
- ## `kinotic plugins update`
509
-
510
- Update installed plugins.
511
-
512
- ```
513
- USAGE
514
- $ kinotic plugins update [-h] [-v]
515
-
516
- FLAGS
517
- -h, --help Show CLI help.
518
- -v, --verbose
519
-
520
- DESCRIPTION
521
- Update installed plugins.
522
- ```
523
-
524
- _See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/5.4.58/src/commands/plugins/update.ts)_
525
-
526
172
  ## `kinotic sync`
527
173
 
528
174
  Synchronize the local Entity definitions with the Kinotic Server
@@ -588,42 +234,4 @@ EXAMPLES
588
234
  ```
589
235
 
590
236
  _See code: [src/commands/synchronize.ts](https://github.com/kinotic-ai/kinotic/blob/v2.2.0/src/commands/synchronize.ts)_
591
-
592
- ## `kinotic update [CHANNEL]`
593
-
594
- update the kinotic CLI
595
-
596
- ```
597
- USAGE
598
- $ kinotic update [CHANNEL] [--force | | [-a | -v <value> | -i]] [-b ]
599
-
600
- FLAGS
601
- -a, --available See available versions.
602
- -b, --verbose Show more details about the available versions.
603
- -i, --interactive Interactively select version to install. This is ignored if a channel is provided.
604
- -v, --version=<value> Install a specific version.
605
- --force Force a re-download of the requested version.
606
-
607
- DESCRIPTION
608
- update the kinotic CLI
609
-
610
- EXAMPLES
611
- Update to the stable channel:
612
-
613
- $ kinotic update stable
614
-
615
- Update to a specific version:
616
-
617
- $ kinotic update --version 1.0.0
618
-
619
- Interactively select version:
620
-
621
- $ kinotic update --interactive
622
-
623
- See available versions:
624
-
625
- $ kinotic update --available
626
- ```
627
-
628
- _See code: [@oclif/plugin-update](https://github.com/oclif/plugin-update/blob/4.7.23/src/commands/update.ts)_
629
237
  <!-- commandsstop -->
@@ -3,7 +3,11 @@ export declare class Project extends Command {
3
3
  static description: string;
4
4
  static examples: string[];
5
5
  static args: {
6
- name: import("@oclif/core/lib/interfaces").Arg<string, Record<string, unknown>>;
6
+ name: import("@oclif/core/interfaces").Arg<string, Record<string, unknown>>;
7
+ };
8
+ static flags: {
9
+ organization: import("@oclif/core/interfaces").OptionFlag<string, import("@oclif/core/interfaces").CustomOptions>;
10
+ application: import("@oclif/core/interfaces").OptionFlag<string, import("@oclif/core/interfaces").CustomOptions>;
7
11
  };
8
12
  run(): Promise<void>;
9
13
  private renderProjectModule;
@@ -1,27 +1,36 @@
1
- import { Args, Command } from '@oclif/core';
1
+ import { Args, Command, Flags } from '@oclif/core';
2
2
  import { input, select } from '@inquirer/prompts';
3
3
  import chalk from 'chalk';
4
4
  import ora from 'ora';
5
5
  import path from 'node:path';
6
6
  import process from 'node:process';
7
- import { spawnEngine } from '../../internal/spawn/SpawnEngine.js';
7
+ import { assertPathWithin } from '@kinotic-ai/spawn/node';
8
+ import { fileSystemSpawnEngine } from '../../internal/spawn/FileSystemSpawnEngine.js';
8
9
  import { createFrontEnd } from '../../internal/CommandHelper.js';
9
10
  export class Project extends Command {
10
11
  static description = 'Creates a Kinotic Project';
11
12
  static examples = [
12
- '$ kinotic create project MyProjectName',
13
+ '$ kinotic create project MyProjectName --organization acme --application acme-app',
13
14
  ];
14
15
  static args = {
15
16
  name: Args.string({ description: 'The name for the project', required: true })
16
17
  };
18
+ static flags = {
19
+ organization: Flags.string({ char: 'o', description: 'The organization that owns the project', required: true }),
20
+ application: Flags.string({ char: 'a', description: 'The application the project belongs to', required: true })
21
+ };
17
22
  async run() {
18
- const { args } = await this.parse(Project);
23
+ const { args, flags } = await this.parse(Project);
19
24
  const projectDir = path.resolve(args.name);
20
- let context = { projectName: args.name };
25
+ let context = {
26
+ projectName: args.name,
27
+ organization: flags.organization,
28
+ application: flags.application
29
+ };
21
30
  this.log(chalk.cyan('Creating Kinotic Project'));
22
31
  const spinner = ora('Generating project...').start();
23
32
  try {
24
- context = (await spawnEngine.renderSpawn('project', projectDir, context)) ?? context;
33
+ context = await fileSystemSpawnEngine.renderSpawn('project', projectDir, context);
25
34
  spinner.succeed(chalk.green('Project generated'));
26
35
  }
27
36
  catch (err) {
@@ -53,10 +62,7 @@ export class Project extends Command {
53
62
  } while (choice !== 'Quit');
54
63
  }
55
64
  async renderProjectModule(spawn, name, projectDir, context) {
56
- const dir = path.resolve(name);
57
- if (!dir.startsWith(projectDir)) {
58
- throw new Error(`Module dir ${dir} must be within ${projectDir}`);
59
- }
60
- await spawnEngine.renderSpawn(spawn, dir, context);
65
+ const dir = assertPathWithin(projectDir, name);
66
+ await fileSystemSpawnEngine.renderSpawn(spawn, dir, context);
61
67
  }
62
68
  }
@@ -4,8 +4,8 @@ export declare class Generate extends Command {
4
4
  static description: string;
5
5
  static examples: string[];
6
6
  static flags: {
7
- verbose: import("@oclif/core/lib/interfaces").BooleanFlag<boolean>;
8
- force: import("@oclif/core/lib/interfaces").BooleanFlag<boolean>;
7
+ verbose: import("@oclif/core/interfaces").BooleanFlag<boolean>;
8
+ force: import("@oclif/core/interfaces").BooleanFlag<boolean>;
9
9
  };
10
10
  run(): Promise<void>;
11
11
  logVerbose(message: string | (() => string), verbose: boolean): void;
@@ -4,10 +4,10 @@ export declare class Initialize extends Command {
4
4
  static description: string;
5
5
  static examples: string[];
6
6
  static flags: {
7
- application: import("@oclif/core/lib/interfaces").OptionFlag<string | undefined, import("@oclif/core/lib/interfaces").CustomOptions>;
8
- entities: import("@oclif/core/lib/interfaces").OptionFlag<string | undefined, import("@oclif/core/lib/interfaces").CustomOptions>;
9
- repository: import("@oclif/core/lib/interfaces").OptionFlag<string | undefined, import("@oclif/core/lib/interfaces").CustomOptions>;
10
- mirror: import("@oclif/core/lib/interfaces").BooleanFlag<boolean>;
7
+ application: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
8
+ entities: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
9
+ repository: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
10
+ mirror: import("@oclif/core/interfaces").BooleanFlag<boolean>;
11
11
  };
12
12
  run(): Promise<void>;
13
13
  }
@@ -0,0 +1,9 @@
1
+ import { Command } from '@oclif/core';
2
+ export declare class Login extends Command {
3
+ static description: string;
4
+ static examples: string[];
5
+ static flags: {
6
+ server: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
7
+ };
8
+ run(): Promise<void>;
9
+ }
@@ -0,0 +1,21 @@
1
+ import { Command, Flags } from '@oclif/core';
2
+ import { resolveServer } from '../internal/state/Environment.js';
3
+ import { CliAuthenticator } from '../internal/CliAuthenticator.js';
4
+ export class Login extends Command {
5
+ static description = 'Log in to a Kinotic Server and store credentials for subsequent commands';
6
+ static examples = [
7
+ '$ kinotic login',
8
+ '$ kinotic login --server http://localhost:9090'
9
+ ];
10
+ static flags = {
11
+ server: Flags.string({ char: 's', description: 'The Kinotic server to log in to' })
12
+ };
13
+ async run() {
14
+ const { flags } = await this.parse(Login);
15
+ const serverConfig = await resolveServer(this.config.configDir, flags.server);
16
+ if (!(await new CliAuthenticator(serverConfig.url, this.config.configDir, this).login())) {
17
+ this.error('Login failed');
18
+ }
19
+ this.log(`Logged in to ${serverConfig.url}`);
20
+ }
21
+ }
@@ -0,0 +1,13 @@
1
+ import { Command } from '@oclif/core';
2
+ export declare class Lint extends Command {
3
+ static description: string;
4
+ static examples: string[];
5
+ static args: {
6
+ dir: import("@oclif/core/interfaces").Arg<string, Record<string, unknown>>;
7
+ };
8
+ static flags: {
9
+ fix: import("@oclif/core/interfaces").BooleanFlag<boolean>;
10
+ };
11
+ run(): Promise<void>;
12
+ private applyFix;
13
+ }
@@ -0,0 +1,51 @@
1
+ import { Args, Command, Flags } from '@oclif/core';
2
+ import chalk from 'chalk';
3
+ import fs from 'node:fs';
4
+ import path from 'node:path';
5
+ import { lintSpawnDir } from '@kinotic-ai/spawn/node';
6
+ export class Lint extends Command {
7
+ static description = 'Reports variables used in a spawn template that are not declared in its spawn.json';
8
+ static examples = [
9
+ '$ kinotic spawn lint',
10
+ '$ kinotic spawn lint ./my-template --fix',
11
+ ];
12
+ static args = {
13
+ dir: Args.string({ description: 'The spawn template directory', default: '.' })
14
+ };
15
+ static flags = {
16
+ fix: Flags.boolean({ description: 'Add stub propertySchema entries for undeclared variables' })
17
+ };
18
+ async run() {
19
+ const { args, flags } = await this.parse(Lint);
20
+ const dir = path.resolve(args.dir);
21
+ const { undeclared } = await lintSpawnDir(dir);
22
+ if (undeclared.length === 0) {
23
+ this.log(chalk.green('✓ spawn.json declares everything the templates use'));
24
+ return;
25
+ }
26
+ this.log(chalk.yellow('Undeclared variables used in templates:'));
27
+ for (const variable of undeclared) {
28
+ this.log(` ${chalk.bold(variable.name)} ${chalk.dim(variable.files.join(', '))}`);
29
+ }
30
+ if (flags.fix) {
31
+ this.applyFix(dir, undeclared.map(v => v.name));
32
+ this.log(chalk.green(`Added ${undeclared.length} stub(s) to spawn.json — fill in description/default.`));
33
+ }
34
+ else {
35
+ this.error('spawn.json is missing declarations (run with --fix to add stubs)', { exit: 1 });
36
+ }
37
+ }
38
+ // Adds a string-typed stub to the root spawn.json's propertySchema for each
39
+ // undeclared name, leaving existing entries untouched.
40
+ applyFix(dir, names) {
41
+ const spawnJsonPath = path.join(dir, 'spawn.json');
42
+ const config = fs.existsSync(spawnJsonPath)
43
+ ? JSON.parse(fs.readFileSync(spawnJsonPath, { encoding: 'utf8' }))
44
+ : {};
45
+ config.propertySchema ??= {};
46
+ for (const name of names) {
47
+ config.propertySchema[name] ??= { type: 'string', description: 'TODO' };
48
+ }
49
+ fs.writeFileSync(spawnJsonPath, JSON.stringify(config, null, 2) + '\n');
50
+ }
51
+ }
@@ -4,12 +4,11 @@ export declare class Synchronize extends Command {
4
4
  static description: string;
5
5
  static examples: string[];
6
6
  static flags: {
7
- server: import("@oclif/core/lib/interfaces").OptionFlag<string | undefined, import("@oclif/core/lib/interfaces").CustomOptions>;
8
- publish: import("@oclif/core/lib/interfaces").BooleanFlag<boolean>;
9
- verbose: import("@oclif/core/lib/interfaces").BooleanFlag<boolean>;
10
- authHeaderFile: import("@oclif/core/lib/interfaces").OptionFlag<string | undefined, import("@oclif/core/lib/interfaces").CustomOptions>;
11
- dryRun: import("@oclif/core/lib/interfaces").BooleanFlag<boolean>;
12
- force: import("@oclif/core/lib/interfaces").BooleanFlag<boolean>;
7
+ server: import("@oclif/core/interfaces").OptionFlag<string | undefined, import("@oclif/core/interfaces").CustomOptions>;
8
+ publish: import("@oclif/core/interfaces").BooleanFlag<boolean>;
9
+ verbose: import("@oclif/core/interfaces").BooleanFlag<boolean>;
10
+ dryRun: import("@oclif/core/interfaces").BooleanFlag<boolean>;
11
+ force: import("@oclif/core/interfaces").BooleanFlag<boolean>;
13
12
  };
14
13
  run(): Promise<void>;
15
14
  logVerbose(message: string | (() => string), verbose: boolean): void;