@nocobase/cli 2.1.0-alpha.40 → 2.1.0-alpha.46
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/README.md +20 -8
- package/README.zh-CN.md +20 -8
- package/bin/run.js +9 -37
- package/dist/commands/app/destroy.js +225 -0
- package/dist/commands/app/down.js +24 -254
- package/dist/commands/app/restart.js +12 -5
- package/dist/commands/app/shared.js +122 -0
- package/dist/commands/app/start.js +41 -59
- package/dist/commands/app/stop.js +72 -26
- package/dist/commands/app/upgrade.js +312 -429
- package/dist/commands/config/delete.js +8 -1
- package/dist/commands/config/get.js +5 -0
- package/dist/commands/config/set.js +10 -1
- package/dist/commands/db/ps.js +5 -18
- package/dist/commands/db/start.js +23 -8
- package/dist/commands/env/add.js +66 -6
- package/dist/commands/env/auth.js +86 -27
- package/dist/commands/env/info.js +52 -8
- package/dist/commands/env/list.js +6 -7
- package/dist/commands/env/shared.js +41 -3
- package/dist/commands/env/status.js +10 -7
- package/dist/commands/init.js +214 -136
- package/dist/commands/install.js +364 -294
- package/dist/commands/license/plugins/shared.js +9 -3
- package/dist/commands/license/plugins/sync.js +54 -25
- package/dist/commands/self/update.js +58 -1
- package/dist/commands/source/dev.js +5 -5
- package/dist/commands/source/download.js +29 -25
- package/dist/generated/command-registry.js +3 -2
- package/dist/lib/api-client.js +6 -0
- package/dist/lib/api-command-compat.js +641 -0
- package/dist/lib/app-health.js +31 -18
- package/dist/lib/app-managed-resources.js +1 -1
- package/dist/lib/app-runtime.js +2 -2
- package/dist/lib/auth-store.js +56 -19
- package/dist/lib/backup.js +3 -3
- package/dist/lib/bootstrap.js +14 -8
- package/dist/lib/cli-config.js +137 -4
- package/dist/lib/cli-entry-error.js +44 -0
- package/dist/lib/cli-locale.js +19 -7
- package/dist/lib/db-connection-check.js +61 -0
- package/dist/lib/docker-log-stream.js +45 -0
- package/dist/lib/env-auth.js +98 -11
- package/dist/lib/env-config.js +3 -2
- package/dist/lib/env-guard.js +1 -1
- package/dist/lib/generated-command.js +17 -0
- package/dist/lib/prompt-validators.js +23 -5
- package/dist/lib/prompt-web-ui.js +143 -19
- package/dist/lib/run-npm.js +133 -23
- package/dist/lib/skills-manager.js +80 -4
- package/dist/lib/source-publish.js +4 -1
- package/dist/lib/startup-update.js +74 -50
- package/dist/lib/ui.js +4 -1
- package/dist/locale/en-US.json +92 -5
- package/dist/locale/zh-CN.json +92 -5
- package/package.json +34 -2
package/dist/commands/init.js
CHANGED
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
*/
|
|
9
9
|
import { Command, Flags } from '@oclif/core';
|
|
10
10
|
import pc from 'picocolors';
|
|
11
|
+
import crypto from 'node:crypto';
|
|
11
12
|
import { existsSync } from 'node:fs';
|
|
12
13
|
import path from 'node:path';
|
|
13
14
|
import { stdin as stdinStream, stdout as stdoutStream } from 'node:process';
|
|
@@ -15,9 +16,9 @@ import { getEnv, upsertEnv } from "../lib/auth-store.js";
|
|
|
15
16
|
import { runPromptCatalog, } from "../lib/prompt-catalog.js";
|
|
16
17
|
import { applyCliLocale, localeText, translateCli } from "../lib/cli-locale.js";
|
|
17
18
|
import { resolveDefaultConfigScope } from '../lib/cli-home.js';
|
|
18
|
-
import { runPromptCatalogWebUI
|
|
19
|
+
import { runPromptCatalogWebUI } from "../lib/prompt-web-ui.js";
|
|
19
20
|
import { validateApiBaseUrl, validateEnvKey } from "../lib/prompt-validators.js";
|
|
20
|
-
import {
|
|
21
|
+
import { installNocoBaseSkills, isNpmRegistryUnavailable } from '../lib/skills-manager.js';
|
|
21
22
|
import { omitKeys, pickKeys } from "../lib/object-utils.js";
|
|
22
23
|
import { printInfo, printStage, printVerbose, printWarning } from '../lib/ui.js';
|
|
23
24
|
import Download from "./download.js";
|
|
@@ -33,6 +34,8 @@ const INIT_ENV_ADD_FLAG_NAMES = [
|
|
|
33
34
|
'auth-type',
|
|
34
35
|
'access-token',
|
|
35
36
|
'token',
|
|
37
|
+
'username',
|
|
38
|
+
'password',
|
|
36
39
|
'skip-auth',
|
|
37
40
|
];
|
|
38
41
|
const initText = (key, values) => localeText(`commands.init.${key}`, values);
|
|
@@ -51,8 +54,8 @@ function existingAppOnly(def) {
|
|
|
51
54
|
function newInstallOnly(def) {
|
|
52
55
|
return withExtraHidden(def, (values) => values.hasNocobase !== 'no');
|
|
53
56
|
}
|
|
54
|
-
function
|
|
55
|
-
return withExtraHidden(def, (values) => values.hasNocobase !== 'no' || values.
|
|
57
|
+
function newInstallDownloadExecutionOnly(def) {
|
|
58
|
+
return withExtraHidden(def, (values) => values.hasNocobase !== 'no' || values.skipDownload === true);
|
|
56
59
|
}
|
|
57
60
|
function argvHasToken(argv, tokens) {
|
|
58
61
|
return tokens.some((token) => argv.includes(token));
|
|
@@ -65,9 +68,7 @@ function resolveInitDownloadVersion(results) {
|
|
|
65
68
|
return preset;
|
|
66
69
|
}
|
|
67
70
|
function initVersionPromptValue(version) {
|
|
68
|
-
return version === 'latest' || version === 'beta' || version === 'alpha'
|
|
69
|
-
? version
|
|
70
|
-
: 'other';
|
|
71
|
+
return version === 'latest' || version === 'beta' || version === 'alpha' ? version : 'other';
|
|
71
72
|
}
|
|
72
73
|
function yesInitialValue(def, fallback) {
|
|
73
74
|
if ('yesInitialValue' in def && def.yesInitialValue !== undefined) {
|
|
@@ -76,8 +77,7 @@ function yesInitialValue(def, fallback) {
|
|
|
76
77
|
return fallback;
|
|
77
78
|
}
|
|
78
79
|
function hasDownloadOverride(flags) {
|
|
79
|
-
return Boolean(String(flags.source ?? '').trim()
|
|
80
|
-
|| String(flags.version ?? '').trim());
|
|
80
|
+
return Boolean(String(flags.source ?? '').trim() || String(flags.version ?? '').trim());
|
|
81
81
|
}
|
|
82
82
|
function explicitApiBaseUrlFlag(flags) {
|
|
83
83
|
return String(flags['api-base-url'] ?? '').trim();
|
|
@@ -85,6 +85,16 @@ function explicitApiBaseUrlFlag(flags) {
|
|
|
85
85
|
function explicitDbHostFlag(flags) {
|
|
86
86
|
return String(flags['db-host'] ?? '').trim();
|
|
87
87
|
}
|
|
88
|
+
function optionalInitString(value) {
|
|
89
|
+
const text = String(value ?? '').trim();
|
|
90
|
+
return text || undefined;
|
|
91
|
+
}
|
|
92
|
+
function resolveManagedAppKey(value) {
|
|
93
|
+
return optionalInitString(value) ?? crypto.randomBytes(32).toString('hex');
|
|
94
|
+
}
|
|
95
|
+
function resolveManagedTimeZone(value) {
|
|
96
|
+
return optionalInitString(value) ?? (Intl.DateTimeFormat().resolvedOptions().timeZone || 'UTC');
|
|
97
|
+
}
|
|
88
98
|
function shouldAllowExistingInitEnv() {
|
|
89
99
|
return argvHasToken(process.argv.slice(2), ['--force', '-f']);
|
|
90
100
|
}
|
|
@@ -125,9 +135,7 @@ function formatSkippedAppNameRequiredMessage() {
|
|
|
125
135
|
].join('\n');
|
|
126
136
|
}
|
|
127
137
|
function shellQuoteArg(value) {
|
|
128
|
-
return /^[A-Za-z0-9_@%+=:,./-]+$/.test(value)
|
|
129
|
-
? value
|
|
130
|
-
: `'${value.replace(/'/g, `'\\''`)}'`;
|
|
138
|
+
return /^[A-Za-z0-9_@%+=:,./-]+$/.test(value) ? value : `'${value.replace(/'/g, `'\\''`)}'`;
|
|
131
139
|
}
|
|
132
140
|
function initTitle() {
|
|
133
141
|
return 'Set up NocoBase';
|
|
@@ -234,20 +242,27 @@ Prompt modes:
|
|
|
234
242
|
validate: validateApiBaseUrl,
|
|
235
243
|
}),
|
|
236
244
|
authType: existingAppOnly(EnvAdd.prompts.authType),
|
|
245
|
+
username: existingAppOnly(EnvAdd.prompts.username),
|
|
246
|
+
password: existingAppOnly(EnvAdd.prompts.password),
|
|
237
247
|
accessToken: existingAppOnly(EnvAdd.prompts.accessToken),
|
|
238
248
|
lang: newInstallOnly(Install.appPrompts.lang),
|
|
239
249
|
appRootPath: newInstallOnly(Install.appPrompts.appRootPath),
|
|
240
250
|
appPort: newInstallOnly(Install.appPrompts.appPort),
|
|
241
251
|
storagePath: newInstallOnly(Install.appPrompts.storagePath),
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
252
|
+
skipDownload: newInstallOnly({
|
|
253
|
+
type: 'boolean',
|
|
254
|
+
message: initText('prompts.skipDownload.message'),
|
|
255
|
+
initialValue: false,
|
|
256
|
+
yesInitialValue: false,
|
|
257
|
+
}),
|
|
258
|
+
source: newInstallOnly(Download.prompts.source),
|
|
259
|
+
version: newInstallOnly(Download.prompts.version),
|
|
260
|
+
otherVersion: newInstallOnly(Download.prompts.otherVersion),
|
|
261
|
+
dockerRegistry: newInstallOnly(Download.prompts.dockerRegistry),
|
|
262
|
+
dockerPlatform: newInstallOnly(Download.prompts.dockerPlatform),
|
|
263
|
+
dockerSave: newInstallDownloadExecutionOnly(Download.prompts.dockerSave),
|
|
264
|
+
gitUrl: newInstallOnly(Download.prompts.gitUrl),
|
|
265
|
+
outputDir: newInstallDownloadExecutionOnly({
|
|
251
266
|
...DOWNLOAD_OUTPUT_DIR_PROMPT,
|
|
252
267
|
hidden: (values) => {
|
|
253
268
|
const source = String(values.source ?? '').trim();
|
|
@@ -268,11 +283,11 @@ Prompt modes:
|
|
|
268
283
|
return typeof initialValue === 'function' ? initialValue(values) : String(initialValue ?? '');
|
|
269
284
|
},
|
|
270
285
|
}),
|
|
271
|
-
npmRegistry:
|
|
272
|
-
replace:
|
|
273
|
-
devDependencies:
|
|
274
|
-
build:
|
|
275
|
-
buildDts:
|
|
286
|
+
npmRegistry: newInstallOnly(Download.prompts.npmRegistry),
|
|
287
|
+
replace: newInstallDownloadExecutionOnly(Download.prompts.replace),
|
|
288
|
+
devDependencies: newInstallDownloadExecutionOnly(Download.prompts.devDependencies),
|
|
289
|
+
build: newInstallDownloadExecutionOnly(Download.prompts.build),
|
|
290
|
+
buildDts: newInstallDownloadExecutionOnly(Download.prompts.buildDts),
|
|
276
291
|
dbDialect: newInstallOnly(Install.dbPrompts.dbDialect),
|
|
277
292
|
builtinDb: newInstallOnly(Install.dbPrompts.builtinDb),
|
|
278
293
|
builtinDbImage: newInstallOnly(Install.dbPrompts.builtinDbImage),
|
|
@@ -281,23 +296,36 @@ Prompt modes:
|
|
|
281
296
|
dbDatabase: newInstallOnly(Install.dbPrompts.dbDatabase),
|
|
282
297
|
dbUser: newInstallOnly(Install.dbPrompts.dbUser),
|
|
283
298
|
dbPassword: newInstallOnly(Install.dbPrompts.dbPassword),
|
|
299
|
+
dbSchema: newInstallOnly(Install.dbPrompts.dbSchema),
|
|
300
|
+
dbTablePrefix: newInstallOnly(Install.dbPrompts.dbTablePrefix),
|
|
301
|
+
dbUnderscored: newInstallOnly(Install.dbPrompts.dbUnderscored),
|
|
284
302
|
rootUsername: newInstallOnly(Install.rootUserPrompts.rootUsername),
|
|
285
303
|
rootEmail: newInstallOnly(Install.rootUserPrompts.rootEmail),
|
|
286
304
|
rootPassword: newInstallOnly(Install.rootUserPrompts.rootPassword),
|
|
287
305
|
rootNickname: newInstallOnly(Install.rootUserPrompts.rootNickname),
|
|
288
306
|
};
|
|
289
307
|
buildPromptCatalog(flags) {
|
|
290
|
-
|
|
291
|
-
return Init.prompts;
|
|
292
|
-
}
|
|
293
|
-
const accessTokenPrompt = {
|
|
294
|
-
...EnvAdd.prompts.accessToken,
|
|
295
|
-
hidden: () => true,
|
|
296
|
-
};
|
|
297
|
-
return {
|
|
308
|
+
const prompts = {
|
|
298
309
|
...Init.prompts,
|
|
299
|
-
accessToken: existingAppOnly(accessTokenPrompt),
|
|
300
310
|
};
|
|
311
|
+
if (flags['skip-auth']) {
|
|
312
|
+
const accessTokenPrompt = {
|
|
313
|
+
...EnvAdd.prompts.accessToken,
|
|
314
|
+
hidden: () => true,
|
|
315
|
+
};
|
|
316
|
+
const usernamePrompt = {
|
|
317
|
+
...EnvAdd.prompts.username,
|
|
318
|
+
hidden: () => true,
|
|
319
|
+
};
|
|
320
|
+
const passwordPrompt = {
|
|
321
|
+
...EnvAdd.prompts.password,
|
|
322
|
+
hidden: () => true,
|
|
323
|
+
};
|
|
324
|
+
prompts.username = existingAppOnly(usernamePrompt);
|
|
325
|
+
prompts.password = existingAppOnly(passwordPrompt);
|
|
326
|
+
prompts.accessToken = existingAppOnly(accessTokenPrompt);
|
|
327
|
+
}
|
|
328
|
+
return prompts;
|
|
301
329
|
}
|
|
302
330
|
parsedFlagsForPromptSeeds;
|
|
303
331
|
static flags = {
|
|
@@ -319,7 +347,7 @@ Prompt modes:
|
|
|
319
347
|
default: false,
|
|
320
348
|
}),
|
|
321
349
|
'skip-skills': Flags.boolean({
|
|
322
|
-
description: 'Skip installing
|
|
350
|
+
description: 'Skip installing NocoBase AI coding skills during init',
|
|
323
351
|
default: false,
|
|
324
352
|
}),
|
|
325
353
|
'ui-host': Flags.string({
|
|
@@ -344,15 +372,14 @@ Prompt modes:
|
|
|
344
372
|
if (normalizedFlags.ui && normalizedFlags.yes) {
|
|
345
373
|
this.error('--ui cannot be used with --yes.');
|
|
346
374
|
}
|
|
347
|
-
if (normalizedFlags['skip-auth']
|
|
348
|
-
|
|
375
|
+
if (normalizedFlags['skip-auth'] &&
|
|
376
|
+
(normalizedFlags['access-token'] !== undefined || normalizedFlags.token !== undefined)) {
|
|
349
377
|
this.error('--skip-auth cannot be used with --access-token or --token.');
|
|
350
378
|
}
|
|
351
379
|
if (normalizedFlags.ui && normalizedFlags.resume) {
|
|
352
380
|
this.error('--ui cannot be used with --resume.');
|
|
353
381
|
}
|
|
354
|
-
if (!normalizedFlags.ui &&
|
|
355
|
-
(normalizedFlags['ui-host'] !== undefined || normalizedFlags['ui-port'] !== undefined)) {
|
|
382
|
+
if (!normalizedFlags.ui && (normalizedFlags['ui-host'] !== undefined || normalizedFlags['ui-port'] !== undefined)) {
|
|
356
383
|
this.error('--ui-host and --ui-port require --ui.');
|
|
357
384
|
}
|
|
358
385
|
if (normalizedFlags.resume) {
|
|
@@ -454,8 +481,17 @@ Prompt modes:
|
|
|
454
481
|
command: this,
|
|
455
482
|
});
|
|
456
483
|
const normalizedResults = {
|
|
484
|
+
...pickKeys(presetValues, [
|
|
485
|
+
'authType',
|
|
486
|
+
'accessToken',
|
|
487
|
+
'dbSchema',
|
|
488
|
+
'dbTablePrefix',
|
|
489
|
+
'dbUnderscored',
|
|
490
|
+
'skipAuth',
|
|
491
|
+
'username',
|
|
492
|
+
'password',
|
|
493
|
+
]),
|
|
457
494
|
...results,
|
|
458
|
-
...pickKeys(presetValues, ['dbSchema', 'dbTablePrefix', 'dbUnderscored', 'skipAuth']),
|
|
459
495
|
};
|
|
460
496
|
const hasNocobase = normalizedResults.hasNocobase === 'yes';
|
|
461
497
|
const existingEnv = !hasNocobase
|
|
@@ -510,9 +546,7 @@ Prompt modes:
|
|
|
510
546
|
}
|
|
511
547
|
}
|
|
512
548
|
const downloadSeed = { ...presetValues };
|
|
513
|
-
if (flags.yes
|
|
514
|
-
&& !Object.prototype.hasOwnProperty.call(downloadSeed, 'source')
|
|
515
|
-
&& downloadSeed.fetchSource !== false) {
|
|
549
|
+
if (flags.yes && !Object.prototype.hasOwnProperty.call(downloadSeed, 'source')) {
|
|
516
550
|
downloadSeed.source = 'docker';
|
|
517
551
|
}
|
|
518
552
|
const dbInitial = await Install.buildDbPromptInitialValues({
|
|
@@ -544,6 +578,8 @@ Prompt modes:
|
|
|
544
578
|
catalog: {
|
|
545
579
|
apiBaseUrl: c.apiBaseUrl,
|
|
546
580
|
authType: c.authType,
|
|
581
|
+
username: c.username,
|
|
582
|
+
password: c.password,
|
|
547
583
|
accessToken: c.accessToken,
|
|
548
584
|
},
|
|
549
585
|
},
|
|
@@ -555,7 +591,7 @@ Prompt modes:
|
|
|
555
591
|
appRootPath: c.appRootPath,
|
|
556
592
|
appPort: c.appPort,
|
|
557
593
|
storagePath: c.storagePath,
|
|
558
|
-
|
|
594
|
+
skipDownload: c.skipDownload,
|
|
559
595
|
},
|
|
560
596
|
},
|
|
561
597
|
{
|
|
@@ -589,6 +625,9 @@ Prompt modes:
|
|
|
589
625
|
dbDatabase: c.dbDatabase,
|
|
590
626
|
dbUser: c.dbUser,
|
|
591
627
|
dbPassword: c.dbPassword,
|
|
628
|
+
dbSchema: c.dbSchema,
|
|
629
|
+
dbTablePrefix: c.dbTablePrefix,
|
|
630
|
+
dbUnderscored: c.dbUnderscored,
|
|
592
631
|
},
|
|
593
632
|
},
|
|
594
633
|
{
|
|
@@ -614,8 +653,7 @@ Prompt modes:
|
|
|
614
653
|
preset.hasNocobase = 'yes';
|
|
615
654
|
preset.apiBaseUrl = apiBaseUrl;
|
|
616
655
|
}
|
|
617
|
-
else if (flags['default-api-base-url'] !== undefined
|
|
618
|
-
&& String(flags['default-api-base-url']).trim() !== '') {
|
|
656
|
+
else if (flags['default-api-base-url'] !== undefined && String(flags['default-api-base-url']).trim() !== '') {
|
|
619
657
|
preset.apiBaseUrl = String(flags['default-api-base-url']).trim();
|
|
620
658
|
}
|
|
621
659
|
if (flags['auth-type'] !== undefined && String(flags['auth-type']).trim() !== '') {
|
|
@@ -628,6 +666,12 @@ Prompt modes:
|
|
|
628
666
|
if (flags['access-token'] !== undefined || flags.token !== undefined) {
|
|
629
667
|
preset.accessToken = accessToken;
|
|
630
668
|
}
|
|
669
|
+
if (flags.username !== undefined) {
|
|
670
|
+
preset.username = String(flags.username ?? '').trim();
|
|
671
|
+
}
|
|
672
|
+
if (flags.password !== undefined) {
|
|
673
|
+
preset.password = String(flags.password ?? '');
|
|
674
|
+
}
|
|
631
675
|
if (flags.lang !== undefined && String(flags.lang).trim() !== '') {
|
|
632
676
|
preset.lang = String(flags.lang).trim();
|
|
633
677
|
}
|
|
@@ -683,8 +727,15 @@ Prompt modes:
|
|
|
683
727
|
if (argvHasToken(argv, ['--db-underscored', '--no-db-underscored'])) {
|
|
684
728
|
preset.dbUnderscored = Boolean(flags['db-underscored']);
|
|
685
729
|
}
|
|
686
|
-
if (argvHasToken(argv, ['--
|
|
687
|
-
preset.
|
|
730
|
+
if (argvHasToken(argv, ['--skip-download'])) {
|
|
731
|
+
preset.skipDownload = Boolean(flags['skip-download']);
|
|
732
|
+
if (preset.skipDownload) {
|
|
733
|
+
preset.dockerSave = false;
|
|
734
|
+
preset.replace = false;
|
|
735
|
+
preset.devDependencies = false;
|
|
736
|
+
preset.build = false;
|
|
737
|
+
preset.buildDts = false;
|
|
738
|
+
}
|
|
688
739
|
}
|
|
689
740
|
if (flags.source !== undefined && String(flags.source).trim() !== '') {
|
|
690
741
|
preset.source = String(flags.source).trim();
|
|
@@ -747,25 +798,23 @@ Prompt modes:
|
|
|
747
798
|
}
|
|
748
799
|
try {
|
|
749
800
|
logInitStage('Syncing agent skills');
|
|
750
|
-
|
|
751
|
-
if (!status.installed) {
|
|
752
|
-
printVerbose('Installing NocoBase agent skills (nb skills install)');
|
|
753
|
-
await installNocoBaseSkills();
|
|
754
|
-
printInfo('Agent skills ready.');
|
|
755
|
-
return;
|
|
756
|
-
}
|
|
757
|
-
printVerbose('Updating NocoBase agent skills (nb skills update)');
|
|
758
|
-
await updateNocoBaseSkills();
|
|
801
|
+
await installNocoBaseSkills();
|
|
759
802
|
printInfo('Agent skills ready.');
|
|
760
803
|
}
|
|
761
804
|
catch (error) {
|
|
762
805
|
const message = error instanceof Error ? error.message : String(error);
|
|
806
|
+
if (isNpmRegistryUnavailable(error)) {
|
|
807
|
+
printWarning(translateCli('commands.init.messages.skillsSyncRegistryUnavailable'));
|
|
808
|
+
printVerbose(`Skipped agent skills sync because the npm registry was unavailable: ${message}`);
|
|
809
|
+
return;
|
|
810
|
+
}
|
|
763
811
|
this.error(pc.red(`Skills sync failed: ${message}`));
|
|
764
812
|
this.exit(1);
|
|
765
813
|
}
|
|
766
814
|
}
|
|
767
815
|
async persistManagedEnvConfig(results, flags = {}) {
|
|
768
816
|
const envName = String(results.appName ?? DEFAULT_INIT_APP_NAME).trim() || DEFAULT_INIT_APP_NAME;
|
|
817
|
+
const existingEnv = await getEnv(envName, { scope: resolveDefaultConfigScope() });
|
|
769
818
|
const appPort = String(results.appPort ?? '').trim();
|
|
770
819
|
const source = String(results.source ?? '').trim();
|
|
771
820
|
const version = resolveInitDownloadVersion(results);
|
|
@@ -786,12 +835,18 @@ Prompt modes:
|
|
|
786
835
|
const dbTablePrefix = String(results.dbTablePrefix ?? '').trim();
|
|
787
836
|
const apiBaseUrl = String(results.apiBaseUrl ?? '').trim();
|
|
788
837
|
const authType = String(results.authType ?? '').trim() || 'oauth';
|
|
838
|
+
const authUsername = authType === 'basic' ? String(results.username ?? results.rootUsername ?? '').trim() : '';
|
|
789
839
|
const accessToken = String(results.accessToken ?? '');
|
|
840
|
+
const skipDownload = results.skipDownload === true;
|
|
841
|
+
const appKey = resolveManagedAppKey(results.appKey ?? existingEnv?.config.appKey);
|
|
842
|
+
const timeZone = resolveManagedTimeZone(results.timeZone ?? existingEnv?.config.timezone);
|
|
790
843
|
const builtinDb = explicitDbHostFlag(flags)
|
|
791
844
|
? false
|
|
792
845
|
: results.builtinDb === undefined
|
|
793
846
|
? undefined
|
|
794
847
|
: Boolean(results.builtinDb);
|
|
848
|
+
results.appKey = appKey;
|
|
849
|
+
results.timeZone = timeZone;
|
|
795
850
|
await upsertEnv(envName, {
|
|
796
851
|
...(source === 'docker'
|
|
797
852
|
? { kind: 'docker' }
|
|
@@ -802,7 +857,8 @@ Prompt modes:
|
|
|
802
857
|
: {}),
|
|
803
858
|
...(apiBaseUrl ? { apiBaseUrl } : appPort ? { apiBaseUrl: `http://127.0.0.1:${appPort}/api` } : {}),
|
|
804
859
|
...(authType ? { authType } : {}),
|
|
805
|
-
...(
|
|
860
|
+
...(authUsername ? { authUsername } : {}),
|
|
861
|
+
...((authType === 'token' || authType === 'basic') && accessToken ? { accessToken } : {}),
|
|
806
862
|
...(source ? { source } : {}),
|
|
807
863
|
...(version ? { downloadVersion: version } : {}),
|
|
808
864
|
...(dockerRegistry ? { dockerRegistry } : {}),
|
|
@@ -812,9 +868,13 @@ Prompt modes:
|
|
|
812
868
|
...(appRootPath ? { appRootPath } : {}),
|
|
813
869
|
...(storagePath ? { storagePath } : {}),
|
|
814
870
|
...(appPort ? { appPort } : {}),
|
|
815
|
-
...(
|
|
816
|
-
...(
|
|
817
|
-
...(results.
|
|
871
|
+
...(appKey ? { appKey } : {}),
|
|
872
|
+
...(timeZone ? { timezone: timeZone } : {}),
|
|
873
|
+
...(!skipDownload && results.devDependencies !== undefined
|
|
874
|
+
? { devDependencies: Boolean(results.devDependencies) }
|
|
875
|
+
: {}),
|
|
876
|
+
...(!skipDownload && results.build !== undefined ? { build: Boolean(results.build) } : {}),
|
|
877
|
+
...(!skipDownload && results.buildDts !== undefined ? { buildDts: Boolean(results.buildDts) } : {}),
|
|
818
878
|
...(builtinDb !== undefined ? { builtinDb } : {}),
|
|
819
879
|
...(dbDialect ? { dbDialect } : {}),
|
|
820
880
|
...(builtinDbImage || builtinDb === false ? { builtinDbImage: builtinDbImage || undefined } : {}),
|
|
@@ -834,12 +894,20 @@ Prompt modes:
|
|
|
834
894
|
argv.push('--api-base-url', String(results.apiBaseUrl ?? DEFAULT_INIT_API_BASE_URL));
|
|
835
895
|
argv.push('--auth-type', String(results.authType ?? 'oauth'));
|
|
836
896
|
const accessToken = String(results.accessToken ?? '');
|
|
897
|
+
const username = String(results.username ?? '').trim();
|
|
898
|
+
const password = String(results.password ?? '');
|
|
837
899
|
if (results.skipAuth === true) {
|
|
838
900
|
argv.push('--skip-auth');
|
|
839
901
|
}
|
|
840
902
|
else if (results.authType === 'token' && accessToken) {
|
|
841
903
|
argv.push('--access-token', accessToken);
|
|
842
904
|
}
|
|
905
|
+
if (results.authType === 'basic' && username) {
|
|
906
|
+
argv.push('--username', username);
|
|
907
|
+
}
|
|
908
|
+
if (results.authType === 'basic' && results.skipAuth !== true && password) {
|
|
909
|
+
argv.push('--password', password);
|
|
910
|
+
}
|
|
843
911
|
return argv;
|
|
844
912
|
}
|
|
845
913
|
buildInstallArgv(results, flags, options) {
|
|
@@ -851,15 +919,18 @@ Prompt modes:
|
|
|
851
919
|
const processArgv = process.argv.slice(2);
|
|
852
920
|
const envName = String(results.appName ?? DEFAULT_INIT_APP_NAME).trim() || DEFAULT_INIT_APP_NAME;
|
|
853
921
|
const source = String(results.source ?? '').trim();
|
|
922
|
+
const skipDownload = Boolean(flags['skip-download']) || results.skipDownload === true;
|
|
854
923
|
const hasNocobase = String(results.hasNocobase ?? '').trim() === 'yes';
|
|
855
924
|
const apiBaseUrl = String(results.apiBaseUrl ?? '').trim();
|
|
856
925
|
const authType = String(results.authType ?? '').trim();
|
|
857
926
|
const accessToken = String(results.accessToken ?? '');
|
|
927
|
+
const username = String(results.username ?? flags.username ?? '').trim();
|
|
928
|
+
const password = String(results.password ?? flags.password ?? '');
|
|
858
929
|
argv.push('--env', envName);
|
|
859
930
|
if (options?.resume) {
|
|
860
931
|
argv.push('--resume');
|
|
861
932
|
}
|
|
862
|
-
if (
|
|
933
|
+
if (flags.verbose) {
|
|
863
934
|
argv.push('--verbose');
|
|
864
935
|
}
|
|
865
936
|
if (hasNocobase && apiBaseUrl) {
|
|
@@ -874,6 +945,12 @@ Prompt modes:
|
|
|
874
945
|
if (authType === 'token' && accessToken) {
|
|
875
946
|
argv.push('--access-token', accessToken);
|
|
876
947
|
}
|
|
948
|
+
if (authType === 'basic' && username) {
|
|
949
|
+
argv.push('--username', username);
|
|
950
|
+
}
|
|
951
|
+
if (authType === 'basic' && password) {
|
|
952
|
+
argv.push('--password', password);
|
|
953
|
+
}
|
|
877
954
|
const lang = String(results.lang ?? '').trim();
|
|
878
955
|
if (lang) {
|
|
879
956
|
argv.push('--lang', lang);
|
|
@@ -890,54 +967,56 @@ Prompt modes:
|
|
|
890
967
|
if (storagePath) {
|
|
891
968
|
argv.push('--storage-path', storagePath);
|
|
892
969
|
}
|
|
893
|
-
if (
|
|
970
|
+
if (flags.force) {
|
|
894
971
|
argv.push('--force');
|
|
895
972
|
}
|
|
896
|
-
if (
|
|
897
|
-
argv.push('--
|
|
898
|
-
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
973
|
+
if (source) {
|
|
974
|
+
argv.push('--source', source);
|
|
975
|
+
}
|
|
976
|
+
const version = resolveInitDownloadVersion(results);
|
|
977
|
+
if (version) {
|
|
978
|
+
argv.push('--version', version);
|
|
979
|
+
}
|
|
980
|
+
const gitUrl = String(results.gitUrl ?? '').trim();
|
|
981
|
+
if (gitUrl) {
|
|
982
|
+
argv.push('--git-url', gitUrl);
|
|
983
|
+
}
|
|
984
|
+
const dockerRegistry = String(results.dockerRegistry ?? '').trim();
|
|
985
|
+
if (dockerRegistry) {
|
|
986
|
+
argv.push('--docker-registry', dockerRegistry);
|
|
987
|
+
}
|
|
988
|
+
const dockerPlatform = String(results.dockerPlatform ?? '').trim();
|
|
989
|
+
if (dockerPlatform) {
|
|
990
|
+
argv.push('--docker-platform', dockerPlatform);
|
|
991
|
+
}
|
|
992
|
+
const npmRegistry = String(results.npmRegistry ?? '').trim();
|
|
993
|
+
if (npmRegistry) {
|
|
994
|
+
argv.push('--npm-registry', npmRegistry);
|
|
995
|
+
}
|
|
996
|
+
if (skipDownload) {
|
|
997
|
+
argv.push('--skip-download');
|
|
998
|
+
}
|
|
999
|
+
else {
|
|
905
1000
|
const outputDir = String(results.outputDir ?? '').trim();
|
|
906
1001
|
if (outputDir) {
|
|
907
1002
|
argv.push('--output-dir', outputDir);
|
|
908
1003
|
}
|
|
909
|
-
|
|
910
|
-
if (gitUrl) {
|
|
911
|
-
argv.push('--git-url', gitUrl);
|
|
912
|
-
}
|
|
913
|
-
const dockerRegistry = String(results.dockerRegistry ?? '').trim();
|
|
914
|
-
if (dockerRegistry) {
|
|
915
|
-
argv.push('--docker-registry', dockerRegistry);
|
|
916
|
-
}
|
|
917
|
-
const dockerPlatform = String(results.dockerPlatform ?? '').trim();
|
|
918
|
-
if (dockerPlatform) {
|
|
919
|
-
argv.push('--docker-platform', dockerPlatform);
|
|
920
|
-
}
|
|
921
|
-
const npmRegistry = String(results.npmRegistry ?? '').trim();
|
|
922
|
-
if (npmRegistry) {
|
|
923
|
-
argv.push('--npm-registry', npmRegistry);
|
|
924
|
-
}
|
|
925
|
-
if (Boolean(results.replace)) {
|
|
1004
|
+
if (results.replace) {
|
|
926
1005
|
argv.push('--replace');
|
|
927
1006
|
}
|
|
928
|
-
if (
|
|
1007
|
+
if (results.devDependencies) {
|
|
929
1008
|
argv.push('--dev-dependencies');
|
|
930
1009
|
}
|
|
931
|
-
if (
|
|
1010
|
+
if (results.dockerSave) {
|
|
932
1011
|
argv.push('--docker-save');
|
|
933
1012
|
}
|
|
934
|
-
if (results.build !== undefined && !
|
|
1013
|
+
if (results.build !== undefined && !results.build) {
|
|
935
1014
|
argv.push('--no-build');
|
|
936
1015
|
}
|
|
937
1016
|
else if (argvHasToken(processArgv, ['--build', '--no-build']) && flags.build === false) {
|
|
938
1017
|
argv.push('--no-build');
|
|
939
1018
|
}
|
|
940
|
-
if (
|
|
1019
|
+
if (results.buildDts) {
|
|
941
1020
|
argv.push('--build-dts');
|
|
942
1021
|
}
|
|
943
1022
|
}
|
|
@@ -965,9 +1044,9 @@ Prompt modes:
|
|
|
965
1044
|
const dbPortWasProvided = argvHasToken(processArgv, ['--db-port']);
|
|
966
1045
|
const dockerBuiltinDbPortIsHidden = builtinDb && source === 'docker';
|
|
967
1046
|
const dbDefaultPort = defaultDbPortForDialect(dbDialect);
|
|
968
|
-
if (dbPort
|
|
969
|
-
|
|
970
|
-
|
|
1047
|
+
if (dbPort &&
|
|
1048
|
+
(!dockerBuiltinDbPortIsHidden || dbPortWasProvided) &&
|
|
1049
|
+
(!flags.yes || dbPortWasProvided || dbPort !== dbDefaultPort)) {
|
|
971
1050
|
argv.push('--db-port', dbPort);
|
|
972
1051
|
}
|
|
973
1052
|
const dbDatabase = String(results.dbDatabase ?? '').trim();
|
|
@@ -991,7 +1070,7 @@ Prompt modes:
|
|
|
991
1070
|
argv.push('--db-table-prefix', dbTablePrefix);
|
|
992
1071
|
}
|
|
993
1072
|
if (results.dbUnderscored !== undefined) {
|
|
994
|
-
argv.push(
|
|
1073
|
+
argv.push(results.dbUnderscored ? '--db-underscored' : '--no-db-underscored');
|
|
995
1074
|
}
|
|
996
1075
|
const rootUsername = String(results.rootUsername ?? '').trim();
|
|
997
1076
|
if (rootUsername) {
|
|
@@ -1013,50 +1092,54 @@ Prompt modes:
|
|
|
1013
1092
|
}
|
|
1014
1093
|
buildManagedInstallResumeCommand(results, flags) {
|
|
1015
1094
|
const argv = ['nb', 'init'];
|
|
1016
|
-
if (
|
|
1095
|
+
if (flags.yes) {
|
|
1017
1096
|
argv.push('--yes');
|
|
1018
1097
|
}
|
|
1019
1098
|
const envName = String(results.appName ?? DEFAULT_INIT_APP_NAME).trim() || DEFAULT_INIT_APP_NAME;
|
|
1020
1099
|
argv.push('--env', envName);
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1100
|
+
const source = String(results.source ?? '').trim();
|
|
1101
|
+
const skipDownload = Boolean(flags['skip-download']) || results.skipDownload === true;
|
|
1102
|
+
if (source) {
|
|
1103
|
+
argv.push('--source', source);
|
|
1104
|
+
}
|
|
1105
|
+
const version = resolveInitDownloadVersion(results);
|
|
1106
|
+
if (version) {
|
|
1107
|
+
argv.push('--version', version);
|
|
1108
|
+
}
|
|
1109
|
+
const gitUrl = String(results.gitUrl ?? '').trim();
|
|
1110
|
+
if (gitUrl) {
|
|
1111
|
+
argv.push('--git-url', gitUrl);
|
|
1112
|
+
}
|
|
1113
|
+
const dockerRegistry = String(results.dockerRegistry ?? '').trim();
|
|
1114
|
+
if (dockerRegistry) {
|
|
1115
|
+
argv.push('--docker-registry', dockerRegistry);
|
|
1116
|
+
}
|
|
1117
|
+
const dockerPlatform = String(results.dockerPlatform ?? '').trim();
|
|
1118
|
+
if (dockerPlatform) {
|
|
1119
|
+
argv.push('--docker-platform', dockerPlatform);
|
|
1120
|
+
}
|
|
1121
|
+
const npmRegistry = String(results.npmRegistry ?? '').trim();
|
|
1122
|
+
if (npmRegistry) {
|
|
1123
|
+
argv.push('--npm-registry', npmRegistry);
|
|
1124
|
+
}
|
|
1125
|
+
if (skipDownload) {
|
|
1126
|
+
argv.push('--skip-download');
|
|
1127
|
+
}
|
|
1128
|
+
else {
|
|
1030
1129
|
const outputDir = String(results.outputDir ?? '').trim();
|
|
1031
1130
|
if (outputDir && outputDir !== String(results.appRootPath ?? '').trim()) {
|
|
1032
1131
|
argv.push('--output-dir', outputDir);
|
|
1033
1132
|
}
|
|
1034
|
-
|
|
1035
|
-
if (gitUrl) {
|
|
1036
|
-
argv.push('--git-url', gitUrl);
|
|
1037
|
-
}
|
|
1038
|
-
const dockerRegistry = String(results.dockerRegistry ?? '').trim();
|
|
1039
|
-
if (dockerRegistry) {
|
|
1040
|
-
argv.push('--docker-registry', dockerRegistry);
|
|
1041
|
-
}
|
|
1042
|
-
const dockerPlatform = String(results.dockerPlatform ?? '').trim();
|
|
1043
|
-
if (dockerPlatform) {
|
|
1044
|
-
argv.push('--docker-platform', dockerPlatform);
|
|
1045
|
-
}
|
|
1046
|
-
const npmRegistry = String(results.npmRegistry ?? '').trim();
|
|
1047
|
-
if (npmRegistry) {
|
|
1048
|
-
argv.push('--npm-registry', npmRegistry);
|
|
1049
|
-
}
|
|
1050
|
-
if (Boolean(results.devDependencies)) {
|
|
1133
|
+
if (results.devDependencies) {
|
|
1051
1134
|
argv.push('--dev-dependencies');
|
|
1052
1135
|
}
|
|
1053
|
-
if (
|
|
1136
|
+
if (results.dockerSave) {
|
|
1054
1137
|
argv.push('--docker-save');
|
|
1055
1138
|
}
|
|
1056
|
-
if (results.build !== undefined && !
|
|
1139
|
+
if (results.build !== undefined && !results.build) {
|
|
1057
1140
|
argv.push('--no-build');
|
|
1058
1141
|
}
|
|
1059
|
-
if (
|
|
1142
|
+
if (results.buildDts) {
|
|
1060
1143
|
argv.push('--build-dts');
|
|
1061
1144
|
}
|
|
1062
1145
|
}
|
|
@@ -1065,11 +1148,7 @@ Prompt modes:
|
|
|
1065
1148
|
}
|
|
1066
1149
|
formatManagedInstallFailureMessage(message, results, flags) {
|
|
1067
1150
|
const command = this.buildManagedInstallResumeCommand(results, flags);
|
|
1068
|
-
return [
|
|
1069
|
-
message,
|
|
1070
|
-
'',
|
|
1071
|
-
translateCli('commands.init.messages.resumeAfterInstallFailure', { command }),
|
|
1072
|
-
].join('\n');
|
|
1151
|
+
return [message, '', translateCli('commands.init.messages.resumeAfterInstallFailure', { command })].join('\n');
|
|
1073
1152
|
}
|
|
1074
1153
|
buildResumeInstallArgv(flags) {
|
|
1075
1154
|
const preset = this.buildPresetValuesFromFlags(flags);
|
|
@@ -1080,10 +1159,9 @@ Prompt modes:
|
|
|
1080
1159
|
preset.rootPassword ??= yesInitialValue(Install.rootUserPrompts.rootPassword, 'admin123');
|
|
1081
1160
|
preset.rootNickname ??= yesInitialValue(Install.rootUserPrompts.rootNickname, 'Super Admin');
|
|
1082
1161
|
}
|
|
1083
|
-
if (
|
|
1084
|
-
preset.
|
|
1162
|
+
if (!flags['skip-download']) {
|
|
1163
|
+
preset.replace ??= true;
|
|
1085
1164
|
}
|
|
1086
|
-
preset.replace ??= true;
|
|
1087
1165
|
return this.buildInstallArgv(preset, flags, {
|
|
1088
1166
|
nonInteractive: Boolean(flags.yes),
|
|
1089
1167
|
resume: true,
|