@hubspot/cli 4.2.1-beta.3 → 5.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.
- package/bin/cli.js +5 -2
- package/commands/customObject.js +10 -14
- package/commands/mv.js +2 -1
- package/commands/project/add.js +2 -1
- package/commands/project/create.js +4 -5
- package/commands/project/deploy.js +13 -1
- package/commands/project/dev.js +17 -18
- package/commands/project/download.js +2 -1
- package/commands/project/listBuilds.js +2 -2
- package/commands/project/logs.js +2 -2
- package/commands/project/open.js +2 -1
- package/commands/project/upload.js +2 -2
- package/commands/project/watch.js +2 -1
- package/commands/project.js +2 -1
- package/commands/secrets/updateSecret.js +1 -1
- package/commands/upload.js +35 -1
- package/lang/en.lyaml +30 -20
- package/lib/LocalDevManager.js +29 -29
- package/lib/projects.js +7 -16
- package/lib/prompts/cleanUploadPrompt.js +20 -0
- package/lib/prompts/projectDevTargetAccountPrompt.js +16 -5
- package/lib/prompts/projectNamePrompt.js +2 -1
- package/lib/ui.js +26 -24
- package/package.json +3 -3
package/bin/cli.js
CHANGED
|
@@ -42,7 +42,11 @@ const cmsCommand = require('../commands/cms');
|
|
|
42
42
|
const feedbackCommand = require('../commands/feedback');
|
|
43
43
|
const { EXIT_CODES } = require('../lib/enums/exitCodes');
|
|
44
44
|
|
|
45
|
-
const notifier = updateNotifier({
|
|
45
|
+
const notifier = updateNotifier({
|
|
46
|
+
pkg: { ...pkg, name: '@hubspot/cli' },
|
|
47
|
+
distTag: 'latest',
|
|
48
|
+
shouldNotifyInNpmScript: true,
|
|
49
|
+
});
|
|
46
50
|
|
|
47
51
|
const i18nKey = 'cli.commands.generalErrors';
|
|
48
52
|
|
|
@@ -51,7 +55,6 @@ const CLI_UPGRADE_MESSAGE =
|
|
|
51
55
|
'\n\nTo upgrade, run:\n\nnpm uninstall -g @hubspot/cms-cli\nand npm install -g @hubspot/cli';
|
|
52
56
|
|
|
53
57
|
notifier.notify({
|
|
54
|
-
shouldNotifyInNpmScript: true,
|
|
55
58
|
message: pkg.name === '@hubspot/cms-cli' ? CLI_UPGRADE_MESSAGE : null,
|
|
56
59
|
});
|
|
57
60
|
|
package/commands/customObject.js
CHANGED
|
@@ -1,28 +1,24 @@
|
|
|
1
|
-
const chalk = require('chalk');
|
|
2
1
|
const { addConfigOptions, addAccountOptions } = require('../lib/commonOpts');
|
|
3
2
|
const schemaCommand = require('./customObject/schema');
|
|
4
3
|
const createCommand = require('./customObject/create');
|
|
5
4
|
const { i18n } = require('../lib/lang');
|
|
6
5
|
const { logger } = require('@hubspot/cli-lib/logger');
|
|
7
|
-
const {
|
|
6
|
+
const { uiBetaTag, uiLink } = require('../lib/ui');
|
|
8
7
|
|
|
9
8
|
const i18nKey = 'cli.commands.customObject';
|
|
10
9
|
|
|
11
10
|
exports.command = ['custom-object', 'custom', 'co'];
|
|
12
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
11
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
13
12
|
|
|
14
13
|
const logBetaMessage = () => {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
)
|
|
24
|
-
);
|
|
25
|
-
});
|
|
14
|
+
uiBetaTag(i18n(`${i18nKey}.betaMessage`));
|
|
15
|
+
logger.log(
|
|
16
|
+
uiLink(
|
|
17
|
+
i18n(`${i18nKey}.seeMoreLink`),
|
|
18
|
+
'https://developers.hubspot.com/docs/api/crm/crm-custom-objects'
|
|
19
|
+
)
|
|
20
|
+
);
|
|
21
|
+
logger.log();
|
|
26
22
|
};
|
|
27
23
|
|
|
28
24
|
exports.builder = yargs => {
|
package/commands/mv.js
CHANGED
|
@@ -15,6 +15,7 @@ const { trackCommandUsage } = require('../lib/usageTracking');
|
|
|
15
15
|
const { isPathFolder } = require('../lib/filesystem');
|
|
16
16
|
const { loadAndValidateOptions } = require('../lib/validation');
|
|
17
17
|
const { i18n } = require('../lib/lang');
|
|
18
|
+
const { uiBetaTag } = require('../lib/ui');
|
|
18
19
|
|
|
19
20
|
const i18nKey = 'cli.commands.mv';
|
|
20
21
|
|
|
@@ -28,7 +29,7 @@ const getCorrectedDestPath = (srcPath, destPath) => {
|
|
|
28
29
|
};
|
|
29
30
|
|
|
30
31
|
exports.command = 'mv <srcPath> <destPath>';
|
|
31
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
32
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
32
33
|
|
|
33
34
|
exports.handler = async options => {
|
|
34
35
|
await loadAndValidateOptions(options);
|
package/commands/project/add.js
CHANGED
|
@@ -7,11 +7,12 @@ const { i18n } = require('../../lib/lang');
|
|
|
7
7
|
const { projectAddPrompt } = require('../../lib/prompts/projectAddPrompt');
|
|
8
8
|
const { createProjectComponent } = require('../../lib/projects');
|
|
9
9
|
const { loadAndValidateOptions } = require('../../lib/validation');
|
|
10
|
+
const { uiBetaTag } = require('../../lib/ui');
|
|
10
11
|
|
|
11
12
|
const i18nKey = 'cli.commands.project.subcommands.add';
|
|
12
13
|
|
|
13
14
|
exports.command = 'add';
|
|
14
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
15
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
15
16
|
|
|
16
17
|
exports.handler = async options => {
|
|
17
18
|
await loadAndValidateOptions(options);
|
|
@@ -14,13 +14,13 @@ const {
|
|
|
14
14
|
} = require('../../lib/prompts/createProjectPrompt');
|
|
15
15
|
const { createProjectConfig } = require('../../lib/projects');
|
|
16
16
|
const { i18n } = require('../../lib/lang');
|
|
17
|
-
const { uiFeatureHighlight } = require('../../lib/ui');
|
|
17
|
+
const { uiBetaTag, uiFeatureHighlight } = require('../../lib/ui');
|
|
18
18
|
const { logger } = require('@hubspot/cli-lib/logger');
|
|
19
19
|
|
|
20
20
|
const i18nKey = 'cli.commands.project.subcommands.create';
|
|
21
21
|
|
|
22
22
|
exports.command = 'create';
|
|
23
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
23
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
24
24
|
|
|
25
25
|
exports.handler = async options => {
|
|
26
26
|
await loadAndValidateOptions(options);
|
|
@@ -38,15 +38,14 @@ exports.handler = async options => {
|
|
|
38
38
|
await createProjectConfig(
|
|
39
39
|
path.resolve(getCwd(), options.location || location),
|
|
40
40
|
options.name || name,
|
|
41
|
-
|
|
41
|
+
template || { path: options.template },
|
|
42
42
|
options.templateSource
|
|
43
43
|
);
|
|
44
44
|
|
|
45
45
|
logger.log('');
|
|
46
46
|
logger.log(chalk.bold(i18n(`${i18nKey}.logs.welcomeMessage`)));
|
|
47
47
|
uiFeatureHighlight([
|
|
48
|
-
'
|
|
49
|
-
'projectDeployCommand',
|
|
48
|
+
'projectDevCommand',
|
|
50
49
|
'projectHelpCommand',
|
|
51
50
|
'feedbackCommand',
|
|
52
51
|
]);
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
const chalk = require('chalk');
|
|
1
2
|
const {
|
|
2
3
|
addAccountOptions,
|
|
3
4
|
addConfigOptions,
|
|
@@ -16,13 +17,15 @@ const { getProjectConfig, pollDeployStatus } = require('../../lib/projects');
|
|
|
16
17
|
const { projectNamePrompt } = require('../../lib/prompts/projectNamePrompt');
|
|
17
18
|
const { buildIdPrompt } = require('../../lib/prompts/buildIdPrompt');
|
|
18
19
|
const { i18n } = require('../../lib/lang');
|
|
20
|
+
const { uiBetaTag } = require('../../lib/ui');
|
|
19
21
|
const { getAccountConfig } = require('@hubspot/cli-lib');
|
|
20
22
|
|
|
21
23
|
const i18nKey = 'cli.commands.project.subcommands.deploy';
|
|
22
24
|
const { EXIT_CODES } = require('../../lib/enums/exitCodes');
|
|
25
|
+
const { uiCommandReference, uiAccountDescription } = require('../../lib/ui');
|
|
23
26
|
|
|
24
27
|
exports.command = 'deploy [--project] [--buildId]';
|
|
25
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
28
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
26
29
|
|
|
27
30
|
exports.handler = async options => {
|
|
28
31
|
await loadAndValidateOptions(options);
|
|
@@ -98,6 +101,15 @@ exports.handler = async options => {
|
|
|
98
101
|
buildIdToDeploy
|
|
99
102
|
);
|
|
100
103
|
} catch (e) {
|
|
104
|
+
if (e.statusCode === 404) {
|
|
105
|
+
logger.error(
|
|
106
|
+
i18n(`${i18nKey}.errors.projectNotFound`, {
|
|
107
|
+
projectName: chalk.bold(projectName),
|
|
108
|
+
accountIdentifier: uiAccountDescription(accountId),
|
|
109
|
+
command: uiCommandReference('hs project upload'),
|
|
110
|
+
})
|
|
111
|
+
);
|
|
112
|
+
}
|
|
101
113
|
if (e.statusCode === 400) {
|
|
102
114
|
logger.error(e.error.message);
|
|
103
115
|
} else {
|
package/commands/project/dev.js
CHANGED
|
@@ -25,7 +25,7 @@ const {
|
|
|
25
25
|
const { EXIT_CODES } = require('../../lib/enums/exitCodes');
|
|
26
26
|
const {
|
|
27
27
|
uiAccountDescription,
|
|
28
|
-
|
|
28
|
+
uiBetaTag,
|
|
29
29
|
uiCommandReference,
|
|
30
30
|
uiLine,
|
|
31
31
|
} = require('../../lib/ui');
|
|
@@ -66,7 +66,7 @@ const {
|
|
|
66
66
|
const i18nKey = 'cli.commands.project.subcommands.dev';
|
|
67
67
|
|
|
68
68
|
exports.command = 'dev [--account]';
|
|
69
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
69
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
70
70
|
|
|
71
71
|
exports.handler = async options => {
|
|
72
72
|
await loadAndValidateOptions(options);
|
|
@@ -78,10 +78,7 @@ exports.handler = async options => {
|
|
|
78
78
|
|
|
79
79
|
const { projectConfig, projectDir } = await getProjectConfig();
|
|
80
80
|
|
|
81
|
-
|
|
82
|
-
console.clear();
|
|
83
|
-
}
|
|
84
|
-
uiBetaMessage(i18n(`${i18nKey}.logs.betaMessage`));
|
|
81
|
+
uiBetaTag(i18n(`${i18nKey}.logs.betaMessage`));
|
|
85
82
|
|
|
86
83
|
if (!projectConfig) {
|
|
87
84
|
logger.error(i18n(`${i18nKey}.errors.noProjectConfig`));
|
|
@@ -203,19 +200,18 @@ exports.handler = async options => {
|
|
|
203
200
|
);
|
|
204
201
|
|
|
205
202
|
let deployedBuild;
|
|
203
|
+
let isGithubLinked;
|
|
206
204
|
|
|
207
205
|
if (projectExists) {
|
|
208
206
|
const project = await fetchProject(targetAccountId, projectConfig.name);
|
|
209
207
|
deployedBuild = project.deployedBuild;
|
|
208
|
+
isGithubLinked =
|
|
209
|
+
project.sourceIntegration &&
|
|
210
|
+
project.sourceIntegration.source === 'GITHUB';
|
|
210
211
|
}
|
|
211
212
|
|
|
212
213
|
SpinniesManager.init();
|
|
213
214
|
|
|
214
|
-
if (!options.debug) {
|
|
215
|
-
console.clear();
|
|
216
|
-
}
|
|
217
|
-
uiBetaMessage(i18n(`${i18nKey}.logs.betaMessage`));
|
|
218
|
-
|
|
219
215
|
if (!projectExists) {
|
|
220
216
|
// Create the project without prompting if this is a newly created sandbox
|
|
221
217
|
let shouldCreateProject = createNewSandbox;
|
|
@@ -242,13 +238,14 @@ exports.handler = async options => {
|
|
|
242
238
|
if (shouldCreateProject) {
|
|
243
239
|
await showPlatformVersionWarning(accountId, projectConfig);
|
|
244
240
|
|
|
241
|
+
SpinniesManager.add('createProject', {
|
|
242
|
+
text: i18n(`${i18nKey}.status.creatingProject`, {
|
|
243
|
+
accountIdentifier: uiAccountDescription(targetAccountId),
|
|
244
|
+
projectName: projectConfig.name,
|
|
245
|
+
}),
|
|
246
|
+
});
|
|
247
|
+
|
|
245
248
|
try {
|
|
246
|
-
SpinniesManager.add('createProject', {
|
|
247
|
-
text: i18n(`${i18nKey}.status.creatingProject`, {
|
|
248
|
-
accountIdentifier: uiAccountDescription(targetAccountId),
|
|
249
|
-
projectName: projectConfig.name,
|
|
250
|
-
}),
|
|
251
|
-
});
|
|
252
249
|
await createProject(targetAccountId, projectConfig.name);
|
|
253
250
|
SpinniesManager.succeed('createProject', {
|
|
254
251
|
text: i18n(`${i18nKey}.status.createdProject`, {
|
|
@@ -258,6 +255,7 @@ exports.handler = async options => {
|
|
|
258
255
|
succeedColor: 'white',
|
|
259
256
|
});
|
|
260
257
|
} catch (err) {
|
|
258
|
+
SpinniesManager.fail('createProject');
|
|
261
259
|
logger.log(i18n(`${i18nKey}.status.failedToCreateProject`));
|
|
262
260
|
process.exit(EXIT_CODES.ERROR);
|
|
263
261
|
}
|
|
@@ -317,7 +315,7 @@ exports.handler = async options => {
|
|
|
317
315
|
|
|
318
316
|
logger.log();
|
|
319
317
|
failedSubTasks.forEach(failedSubTask => {
|
|
320
|
-
console.
|
|
318
|
+
console.error(failedSubTask.errorMessage);
|
|
321
319
|
});
|
|
322
320
|
logger.log();
|
|
323
321
|
|
|
@@ -333,6 +331,7 @@ exports.handler = async options => {
|
|
|
333
331
|
projectConfig,
|
|
334
332
|
projectDir,
|
|
335
333
|
targetAccountId,
|
|
334
|
+
isGithubLinked,
|
|
336
335
|
});
|
|
337
336
|
|
|
338
337
|
await LocalDev.start();
|
|
@@ -23,12 +23,13 @@ const {
|
|
|
23
23
|
downloadProjectPrompt,
|
|
24
24
|
} = require('../../lib/prompts/downloadProjectPrompt');
|
|
25
25
|
const { i18n } = require('../../lib/lang');
|
|
26
|
+
const { uiBetaTag } = require('../../lib/ui');
|
|
26
27
|
|
|
27
28
|
const i18nKey = 'cli.commands.project.subcommands.download';
|
|
28
29
|
const { EXIT_CODES } = require('../../lib/enums/exitCodes');
|
|
29
30
|
|
|
30
31
|
exports.command = 'download [--project]';
|
|
31
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
32
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
32
33
|
|
|
33
34
|
exports.handler = async options => {
|
|
34
35
|
await loadAndValidateOptions(options);
|
|
@@ -22,7 +22,7 @@ const {
|
|
|
22
22
|
getTableHeader,
|
|
23
23
|
} = require('@hubspot/cli-lib/lib/table');
|
|
24
24
|
const { getCwd } = require('@hubspot/cli-lib/path');
|
|
25
|
-
const { uiLink } = require('../../lib/ui');
|
|
25
|
+
const { uiBetaTag, uiLink } = require('../../lib/ui');
|
|
26
26
|
const { loadAndValidateOptions } = require('../../lib/validation');
|
|
27
27
|
const {
|
|
28
28
|
getProjectConfig,
|
|
@@ -35,7 +35,7 @@ const { promptUser } = require('../../lib/prompts/promptUtils');
|
|
|
35
35
|
const i18nKey = 'cli.commands.project.subcommands.listBuilds';
|
|
36
36
|
|
|
37
37
|
exports.command = 'list-builds [path]';
|
|
38
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
38
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
39
39
|
|
|
40
40
|
exports.handler = async options => {
|
|
41
41
|
await loadAndValidateOptions(options);
|
package/commands/project/logs.js
CHANGED
|
@@ -32,7 +32,7 @@ const {
|
|
|
32
32
|
// } = require('@hubspot/cli-lib/api/results');
|
|
33
33
|
const { ensureProjectExists } = require('../../lib/projects');
|
|
34
34
|
const { loadAndValidateOptions } = require('../../lib/validation');
|
|
35
|
-
const { uiLine, uiLink } = require('../../lib/ui');
|
|
35
|
+
const { uiBetaTag, uiLine, uiLink } = require('../../lib/ui');
|
|
36
36
|
const { projectLogsPrompt } = require('../../lib/prompts/projectsLogsPrompt');
|
|
37
37
|
// const { tailLogs } = require('../../lib/serverlessLogs');
|
|
38
38
|
const { i18n } = require('../../lib/lang');
|
|
@@ -136,7 +136,7 @@ const getPrivateAppsUrl = accountId => {
|
|
|
136
136
|
// };
|
|
137
137
|
|
|
138
138
|
exports.command = 'logs [--project] [--app] [--function] [--endpoint]';
|
|
139
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
139
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
140
140
|
|
|
141
141
|
exports.handler = async options => {
|
|
142
142
|
await loadAndValidateOptions(options);
|
package/commands/project/open.js
CHANGED
|
@@ -16,12 +16,13 @@ const {
|
|
|
16
16
|
ensureProjectExists,
|
|
17
17
|
} = require('../../lib/projects');
|
|
18
18
|
const { projectNamePrompt } = require('../../lib/prompts/projectNamePrompt');
|
|
19
|
+
const { uiBetaTag } = require('../../lib/ui');
|
|
19
20
|
const { EXIT_CODES } = require('../../lib/enums/exitCodes');
|
|
20
21
|
|
|
21
22
|
const i18nKey = 'cli.commands.project.subcommands.open';
|
|
22
23
|
|
|
23
24
|
exports.command = 'open [--project]';
|
|
24
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
25
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
25
26
|
|
|
26
27
|
exports.handler = async options => {
|
|
27
28
|
await loadAndValidateOptions(options);
|
|
@@ -6,7 +6,7 @@ const {
|
|
|
6
6
|
} = require('../../lib/commonOpts');
|
|
7
7
|
const chalk = require('chalk');
|
|
8
8
|
const { logger } = require('@hubspot/cli-lib/logger');
|
|
9
|
-
const { uiLine } = require('../../lib/ui');
|
|
9
|
+
const { uiBetaTag, uiLine } = require('../../lib/ui');
|
|
10
10
|
const { trackCommandUsage } = require('../../lib/usageTracking');
|
|
11
11
|
const { loadAndValidateOptions } = require('../../lib/validation');
|
|
12
12
|
const {
|
|
@@ -33,7 +33,7 @@ const { EXIT_CODES } = require('../../lib/enums/exitCodes');
|
|
|
33
33
|
const i18nKey = 'cli.commands.project.subcommands.upload';
|
|
34
34
|
|
|
35
35
|
exports.command = 'upload [path]';
|
|
36
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
36
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
37
37
|
|
|
38
38
|
exports.handler = async options => {
|
|
39
39
|
await loadAndValidateOptions(options);
|
|
@@ -13,6 +13,7 @@ const {
|
|
|
13
13
|
addUseEnvironmentOptions,
|
|
14
14
|
} = require('../../lib/commonOpts');
|
|
15
15
|
const { trackCommandUsage } = require('../../lib/usageTracking');
|
|
16
|
+
const { uiBetaTag } = require('../../lib/ui');
|
|
16
17
|
const {
|
|
17
18
|
ensureProjectExists,
|
|
18
19
|
getProjectConfig,
|
|
@@ -34,7 +35,7 @@ const { handleKeypress, handleExit } = require('@hubspot/cli-lib/lib/process');
|
|
|
34
35
|
const i18nKey = 'cli.commands.project.subcommands.watch';
|
|
35
36
|
|
|
36
37
|
exports.command = 'watch [path]';
|
|
37
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
38
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
38
39
|
|
|
39
40
|
const handleBuildStatus = async (accountId, projectName, buildId) => {
|
|
40
41
|
const {
|
package/commands/project.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
const { addConfigOptions, addAccountOptions } = require('../lib/commonOpts');
|
|
2
2
|
const { i18n } = require('../lib/lang');
|
|
3
|
+
const { uiBetaTag } = require('../lib/ui');
|
|
3
4
|
const deploy = require('./project/deploy');
|
|
4
5
|
const create = require('./project/create');
|
|
5
6
|
const upload = require('./project/upload');
|
|
@@ -14,7 +15,7 @@ const add = require('./project/add');
|
|
|
14
15
|
const i18nKey = 'cli.commands.project';
|
|
15
16
|
|
|
16
17
|
exports.command = 'project';
|
|
17
|
-
exports.describe = i18n(`${i18nKey}.describe`);
|
|
18
|
+
exports.describe = uiBetaTag(i18n(`${i18nKey}.describe`), false);
|
|
18
19
|
|
|
19
20
|
exports.builder = yargs => {
|
|
20
21
|
addConfigOptions(yargs, true);
|
package/commands/upload.js
CHANGED
|
@@ -2,7 +2,7 @@ const fs = require('fs');
|
|
|
2
2
|
const path = require('path');
|
|
3
3
|
const { uploadFolder, hasUploadErrors } = require('@hubspot/cli-lib');
|
|
4
4
|
const { getFileMapperQueryValues } = require('@hubspot/cli-lib/fileMapper');
|
|
5
|
-
const { upload } = require('@hubspot/cli-lib/api/fileMapper');
|
|
5
|
+
const { upload, deleteFile } = require('@hubspot/cli-lib/api/fileMapper');
|
|
6
6
|
const {
|
|
7
7
|
getCwd,
|
|
8
8
|
convertToUnixPath,
|
|
@@ -26,6 +26,7 @@ const {
|
|
|
26
26
|
getMode,
|
|
27
27
|
} = require('../lib/commonOpts');
|
|
28
28
|
const { uploadPrompt } = require('../lib/prompts/uploadPrompt');
|
|
29
|
+
const { cleanUploadPrompt } = require('../lib/prompts/cleanUploadPrompt');
|
|
29
30
|
const { validateMode, loadAndValidateOptions } = require('../lib/validation');
|
|
30
31
|
const { trackCommandUsage } = require('../lib/usageTracking');
|
|
31
32
|
const { getUploadableFileList } = require('../lib/upload');
|
|
@@ -204,6 +205,29 @@ exports.handler = async options => {
|
|
|
204
205
|
absoluteSrcPath,
|
|
205
206
|
options.convertFields
|
|
206
207
|
);
|
|
208
|
+
|
|
209
|
+
if (options.clean) {
|
|
210
|
+
// If clean is true, will first delete the dest folder and then upload src. Cleans up files that only exist on HS.
|
|
211
|
+
let cleanUpload = options.force;
|
|
212
|
+
if (!options.force) {
|
|
213
|
+
cleanUpload = await cleanUploadPrompt(accountId, dest);
|
|
214
|
+
}
|
|
215
|
+
if (cleanUpload) {
|
|
216
|
+
try {
|
|
217
|
+
await deleteFile(accountId, dest);
|
|
218
|
+
logger.log(
|
|
219
|
+
i18n(`${i18nKey}.cleaning`, { accountId, filePath: dest })
|
|
220
|
+
);
|
|
221
|
+
} catch (error) {
|
|
222
|
+
logger.error(
|
|
223
|
+
i18n(`${i18nKey}.errors.deleteFailed`, {
|
|
224
|
+
accountId,
|
|
225
|
+
path: dest,
|
|
226
|
+
})
|
|
227
|
+
);
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
}
|
|
207
231
|
uploadFolder(
|
|
208
232
|
accountId,
|
|
209
233
|
absoluteSrcPath,
|
|
@@ -276,5 +300,15 @@ exports.builder = yargs => {
|
|
|
276
300
|
type: 'boolean',
|
|
277
301
|
default: false,
|
|
278
302
|
});
|
|
303
|
+
yargs.option('clean', {
|
|
304
|
+
describe: i18n(`${i18nKey}.options.clean.describe`),
|
|
305
|
+
type: 'boolean',
|
|
306
|
+
default: false,
|
|
307
|
+
});
|
|
308
|
+
yargs.option('force', {
|
|
309
|
+
describe: i18n(`${i18nKey}.options.force.describe`),
|
|
310
|
+
type: 'boolean',
|
|
311
|
+
default: false,
|
|
312
|
+
});
|
|
279
313
|
return yargs;
|
|
280
314
|
};
|
package/lang/en.lyaml
CHANGED
|
@@ -180,7 +180,7 @@ en:
|
|
|
180
180
|
customObject:
|
|
181
181
|
betaMessage: "The Custom Object CLI is currently in beta and is subject to change."
|
|
182
182
|
describe: "Manage Custom Objects. This feature is currently in beta and the CLI contract is subject to change."
|
|
183
|
-
seeMoreLink: "
|
|
183
|
+
seeMoreLink: "View our docs to find out more."
|
|
184
184
|
subcommands:
|
|
185
185
|
create:
|
|
186
186
|
describe: "Create custom object instances"
|
|
@@ -456,10 +456,10 @@ en:
|
|
|
456
456
|
describe: "Shortcut of the link you'd like to open"
|
|
457
457
|
selectLink: "Select a link to open"
|
|
458
458
|
project:
|
|
459
|
-
describe: "
|
|
459
|
+
describe: "Commands for working with projects. For more information, visit our documentation: https://developers.hubspot.com/docs/platform/build-and-deploy-using-hubspot-projects"
|
|
460
460
|
subcommands:
|
|
461
461
|
dev:
|
|
462
|
-
describe: "
|
|
462
|
+
describe: "Start local dev for the current project"
|
|
463
463
|
logs:
|
|
464
464
|
betaMessage: "HubSpot projects local development"
|
|
465
465
|
nonSandboxWarning: "Testing in a sandbox is strongly recommended. To switch the target account, select an option below or run {{#bold}}`hs accounts use`{{/bold}} before running the command again."
|
|
@@ -480,7 +480,7 @@ en:
|
|
|
480
480
|
examples:
|
|
481
481
|
default: "Start local dev for the current project"
|
|
482
482
|
create:
|
|
483
|
-
describe: "
|
|
483
|
+
describe: "Create a new project"
|
|
484
484
|
logs:
|
|
485
485
|
welcomeMessage: "Welcome to HubSpot Developer Projects!"
|
|
486
486
|
examples:
|
|
@@ -495,7 +495,7 @@ en:
|
|
|
495
495
|
templateSource:
|
|
496
496
|
describe: "Path to custom GitHub repository from which to create project template"
|
|
497
497
|
add:
|
|
498
|
-
describe: "
|
|
498
|
+
describe: "Create a new component within a project"
|
|
499
499
|
options:
|
|
500
500
|
name:
|
|
501
501
|
describe: "Component name"
|
|
@@ -510,13 +510,14 @@ en:
|
|
|
510
510
|
examples:
|
|
511
511
|
default: "Create a component within your project"
|
|
512
512
|
deploy:
|
|
513
|
-
describe: "
|
|
513
|
+
describe: "Deploy a project build"
|
|
514
514
|
debug:
|
|
515
515
|
deploying: "Deploying project at path: {{ path }}"
|
|
516
516
|
errors:
|
|
517
517
|
deploy: "Deploy error: {{ details }}"
|
|
518
518
|
noBuilds: "Deploy error: no builds for this project were found."
|
|
519
519
|
noBuildId: "You must specify a build to deploy"
|
|
520
|
+
projectNotFound: "{{ projectName }} does not exist in account {{ accountIdentifier }}. Run {{ command }} to upload your project files to HubSpot."
|
|
520
521
|
examples:
|
|
521
522
|
default: "Deploy the latest build of the current project"
|
|
522
523
|
withOptions: "Deploy build 5 of the project my-project"
|
|
@@ -526,9 +527,9 @@ en:
|
|
|
526
527
|
project:
|
|
527
528
|
describe: "Project name"
|
|
528
529
|
listBuilds:
|
|
529
|
-
describe: "
|
|
530
|
+
describe: "List the project's builds"
|
|
530
531
|
logs:
|
|
531
|
-
describe: "
|
|
532
|
+
describe: "Get execution logs for a serverless function within a project"
|
|
532
533
|
errors:
|
|
533
534
|
invalidAppName: "Could not find app with name \"{{ appName }}\" in project \"{{ projectName }}\""
|
|
534
535
|
logs:
|
|
@@ -563,7 +564,7 @@ en:
|
|
|
563
564
|
endpoint:
|
|
564
565
|
describe: "Public endpoint path"
|
|
565
566
|
upload:
|
|
566
|
-
describe: "
|
|
567
|
+
describe: "Upload your project files and create a new build"
|
|
567
568
|
examples:
|
|
568
569
|
default: "Upload a project"
|
|
569
570
|
logs:
|
|
@@ -581,7 +582,7 @@ en:
|
|
|
581
582
|
path:
|
|
582
583
|
describe: "Path to a project folder"
|
|
583
584
|
watch:
|
|
584
|
-
describe: "
|
|
585
|
+
describe: "Watch your local project for changes and automatically upload changed files to a new build in HubSpot"
|
|
585
586
|
examples:
|
|
586
587
|
default: "Watch a project within the myProjectFolder folder"
|
|
587
588
|
logs:
|
|
@@ -593,7 +594,7 @@ en:
|
|
|
593
594
|
initialUpload:
|
|
594
595
|
describe: "Upload directory before watching for updates"
|
|
595
596
|
download:
|
|
596
|
-
describe: "
|
|
597
|
+
describe: "Download your project files from HubSpot and write to a path on your computer"
|
|
597
598
|
examples:
|
|
598
599
|
default: "Download the project myProject into myProjectFolder folder"
|
|
599
600
|
logs:
|
|
@@ -612,7 +613,7 @@ en:
|
|
|
612
613
|
dest:
|
|
613
614
|
describe: "Destination folder for the project"
|
|
614
615
|
open:
|
|
615
|
-
describe: "
|
|
616
|
+
describe: "Open the specified project's details page in the browser"
|
|
616
617
|
options:
|
|
617
618
|
project:
|
|
618
619
|
describe: "Name of project to open"
|
|
@@ -743,7 +744,7 @@ en:
|
|
|
743
744
|
describe: "Name of the secret to be updated"
|
|
744
745
|
success:
|
|
745
746
|
update: "The secret \"{{ secretName }}\" was updated in the HubSpot account: {{ accountIdentifier }}"
|
|
746
|
-
|
|
747
|
+
updateExplanation: "Existing serverless functions will start using this new value within 10 seconds."
|
|
747
748
|
theme:
|
|
748
749
|
describe: "Commands for working with themes, including marketplace validation with the marketplace-validate subcommand."
|
|
749
750
|
subcommands:
|
|
@@ -803,6 +804,7 @@ en:
|
|
|
803
804
|
invalidPath: "The path \"{{ path }}\" is not a path to a file or folder"
|
|
804
805
|
uploadFailed: "Uploading file \"{{ src }}\" to \"{{ dest }}\" failed"
|
|
805
806
|
someFilesFailed: "One or more files failed to upload to \"{{ dest }}\" in the Design Manager"
|
|
807
|
+
deleteFailed: "Deleting \"{{ path }}\" from account {{ accountId }} failed"
|
|
806
808
|
options:
|
|
807
809
|
options:
|
|
808
810
|
describe: "Options to pass to javascript fields files"
|
|
@@ -810,6 +812,10 @@ en:
|
|
|
810
812
|
describe: "If true, saves all output from javascript fields files as 'fields.output.json'."
|
|
811
813
|
convertFields:
|
|
812
814
|
describe: "If true, converts any javascript fields files contained in module folder or project root."
|
|
815
|
+
clean:
|
|
816
|
+
describe: "Will cause upload to delete files in your HubSpot account that are not found locally."
|
|
817
|
+
force:
|
|
818
|
+
describe: "Skips confirmation prompts when doing a clean upload."
|
|
813
819
|
previewUrl: "To preview this theme, visit: {{ previewUrl }}"
|
|
814
820
|
positionals:
|
|
815
821
|
src:
|
|
@@ -821,6 +827,7 @@ en:
|
|
|
821
827
|
uploadComplete: "Uploading files to \"{{ dest }}\" in the Design Manager is complete"
|
|
822
828
|
uploading: "Uploading files from \"{{ src }}\" to \"{{ dest }}\" in the Design Manager of account {{ accountId }}"
|
|
823
829
|
notUploaded: "There was an error processing \"{{ src }}\". The file has not been uploaded."
|
|
830
|
+
cleaning: "Removing \"{{ filePath }}\" from account {{ accountId }} and uploading local..."
|
|
824
831
|
watch:
|
|
825
832
|
describe: "Watch a directory on your computer for changes and upload the changed files to the HubSpot CMS."
|
|
826
833
|
errors:
|
|
@@ -865,8 +872,8 @@ en:
|
|
|
865
872
|
noCompatibleComponents: "Skipping call to {{ serverKey }} because there are no compatible components in the project."
|
|
866
873
|
LocalDevManager:
|
|
867
874
|
failedToInitialize: "Missing required arguments to initialize Local Dev"
|
|
875
|
+
noDeployedBuild: "There is no deployed build for this project in {{ accountIdentifier }}. Run {{ uploadCommand }} to upload and deploy your project."
|
|
868
876
|
noComponents: "There are no components in this project."
|
|
869
|
-
noDeployedBuild: "There is no deployed build for this project in {{ accountIdentifier }}."
|
|
870
877
|
noRunnableComponents: "There are no components in this project that support local development."
|
|
871
878
|
betaMessage: "HubSpot projects local development"
|
|
872
879
|
running: "Running {{#bold}}{{ projectName }}{{/bold}} locally on {{ accountIdentifier }}, waiting for changes ..."
|
|
@@ -878,13 +885,13 @@ en:
|
|
|
878
885
|
uploadWarning:
|
|
879
886
|
appLabel: "[App]"
|
|
880
887
|
uiExtensionLabel: "[UI Extension]"
|
|
881
|
-
configEdit: "You edited the configuration file {{#bold}}{{ path }}{{/bold}}. Changes to configuration files cannot be handled by the local dev server."
|
|
882
888
|
missingComponents: "The deployed build for this project does not contain {{#bold}}'{{ missingComponents }}'{{/bold}}. This may cause issues in local development."
|
|
883
|
-
|
|
889
|
+
defaultWarning: "Changing project configuration requires a new project build."
|
|
890
|
+
header: "{{ warning }} To reflect these changes and continue testing:"
|
|
884
891
|
stopDev: " * Stop {{ command }}"
|
|
885
892
|
runUpload: " * Run {{ command }}"
|
|
886
|
-
runUploadWithAccount: " * Run {{ command }}"
|
|
887
893
|
restartDev: " * Re-run {{ command }}"
|
|
894
|
+
pushToGithub: " * Commit and push your changes to GitHub"
|
|
888
895
|
devServer:
|
|
889
896
|
cleanupError: "Failed to cleanup local dev server: {{ message }}"
|
|
890
897
|
setupError: "Failed to setup local dev server: {{ message }}"
|
|
@@ -960,7 +967,7 @@ en:
|
|
|
960
967
|
message: "Run {{ command }} to upload your project to HubSpot and trigger builds"
|
|
961
968
|
projectDevCommand:
|
|
962
969
|
command: "hs project dev"
|
|
963
|
-
message: "Run {{ command }} to
|
|
970
|
+
message: "Run {{ command }} to set up your test environment and start local development"
|
|
964
971
|
sandboxSyncDevelopmentCommand:
|
|
965
972
|
command: "hs sandbox sync"
|
|
966
973
|
message: "Run {{ command }} to to update CRM object definitions in your sandbox"
|
|
@@ -989,7 +996,8 @@ en:
|
|
|
989
996
|
createNewSandboxOption: "<Test on a new development sandbox>"
|
|
990
997
|
chooseDefaultAccountOption: "<{{#bold}}\U00002757{{/bold}} Test on this production account {{#bold}}\U00002757{{/bold}}>"
|
|
991
998
|
promptMessage: "[--account] Choose a sandbox under {{ accountIdentifier }} to test with:"
|
|
992
|
-
sandboxLimit: "
|
|
999
|
+
sandboxLimit: "Your account reached the limit of {{ limit }} development sandboxes"
|
|
1000
|
+
sandboxLimitWithSuggestion: "Your account reached the limit of {{ limit }} development sandboxes. Run {{ authCommand }} to add an existing one to the config."
|
|
993
1001
|
confirmDefaultSandboxAccount: "Continue testing on {{#bold}}{{ accountName }} ({{ accountType }}){{/bold}}? (Y/n)"
|
|
994
1002
|
projectLogsPrompt:
|
|
995
1003
|
projectName:
|
|
@@ -1109,7 +1117,7 @@ en:
|
|
|
1109
1117
|
enterName: "[--project] Enter project name:"
|
|
1110
1118
|
errors:
|
|
1111
1119
|
invalidName: "You entered an invalid name. Please try again."
|
|
1112
|
-
projectDoesNotExist: "Project
|
|
1120
|
+
projectDoesNotExist: "Project {{#bold}}{{ projectName }}{{/bold}} could not be found in \"{{ accountIdentifier }}\""
|
|
1113
1121
|
feedbackPrompt:
|
|
1114
1122
|
feedbackType:
|
|
1115
1123
|
message: "What type of feedback would you like to leave?"
|
|
@@ -1122,6 +1130,8 @@ en:
|
|
|
1122
1130
|
errors:
|
|
1123
1131
|
buildIdDoesNotExist: "Build {{ buildId }} does not exist for project {{ projectName }}."
|
|
1124
1132
|
buildAlreadyDeployed: "Build {{ buildId }} is already deployed."
|
|
1133
|
+
cleanUploadPrompt:
|
|
1134
|
+
message: "You are about to remove any remote files in \"{{ filePath }}\" on HubSpot account {{ accountId }} that don't exist locally. Are you sure you want to do this?"
|
|
1125
1135
|
convertFields:
|
|
1126
1136
|
positionals:
|
|
1127
1137
|
src:
|
package/lib/LocalDevManager.js
CHANGED
|
@@ -23,7 +23,7 @@ const {
|
|
|
23
23
|
UI_COLORS,
|
|
24
24
|
uiCommandReference,
|
|
25
25
|
uiAccountDescription,
|
|
26
|
-
|
|
26
|
+
uiBetaTag,
|
|
27
27
|
uiLink,
|
|
28
28
|
uiLine,
|
|
29
29
|
} = require('./ui');
|
|
@@ -44,6 +44,7 @@ class LocalDevManager {
|
|
|
44
44
|
this.projectDir = options.projectDir;
|
|
45
45
|
this.debug = options.debug || false;
|
|
46
46
|
this.deployedBuild = options.deployedBuild;
|
|
47
|
+
this.isGithubLinked = options.isGithubLinked;
|
|
47
48
|
this.watcher = null;
|
|
48
49
|
this.uploadWarnings = {};
|
|
49
50
|
|
|
@@ -64,12 +65,13 @@ class LocalDevManager {
|
|
|
64
65
|
|
|
65
66
|
// Local dev currently relies on the existence of a deployed build in the target account
|
|
66
67
|
if (!this.deployedBuild) {
|
|
67
|
-
logger.log();
|
|
68
68
|
logger.error(
|
|
69
69
|
i18n(`${i18nKey}.noDeployedBuild`, {
|
|
70
70
|
accountIdentifier: uiAccountDescription(this.targetAccountId),
|
|
71
|
+
uploadCommand: this.getUploadCommand(),
|
|
71
72
|
})
|
|
72
73
|
);
|
|
74
|
+
logger.log();
|
|
73
75
|
process.exit(EXIT_CODES.SUCCESS);
|
|
74
76
|
}
|
|
75
77
|
|
|
@@ -77,7 +79,6 @@ class LocalDevManager {
|
|
|
77
79
|
|
|
78
80
|
// The project is empty, there is nothing to run locally
|
|
79
81
|
if (!components.length) {
|
|
80
|
-
logger.log();
|
|
81
82
|
logger.error(i18n(`${i18nKey}.noComponents`));
|
|
82
83
|
process.exit(EXIT_CODES.SUCCESS);
|
|
83
84
|
}
|
|
@@ -88,19 +89,19 @@ class LocalDevManager {
|
|
|
88
89
|
|
|
89
90
|
// The project does not contain any components that support local development
|
|
90
91
|
if (!runnableComponents.length) {
|
|
91
|
-
logger.log();
|
|
92
92
|
logger.error(i18n(`${i18nKey}.noRunnableComponents`));
|
|
93
93
|
process.exit(EXIT_CODES.SUCCESS);
|
|
94
94
|
}
|
|
95
95
|
|
|
96
|
-
logger.log();
|
|
97
96
|
const setupSucceeded = await this.devServerSetup(runnableComponents);
|
|
98
97
|
|
|
99
|
-
if (setupSucceeded
|
|
98
|
+
if (!setupSucceeded) {
|
|
99
|
+
process.exit(EXIT_CODES.ERROR);
|
|
100
|
+
} else if (!this.debug) {
|
|
100
101
|
console.clear();
|
|
101
102
|
}
|
|
102
103
|
|
|
103
|
-
|
|
104
|
+
uiBetaTag(i18n(`${i18nKey}.betaMessage`));
|
|
104
105
|
logger.log();
|
|
105
106
|
logger.log(
|
|
106
107
|
chalk.hex(UI_COLORS.SORBET)(
|
|
@@ -165,32 +166,35 @@ class LocalDevManager {
|
|
|
165
166
|
});
|
|
166
167
|
}
|
|
167
168
|
|
|
169
|
+
getUploadCommand() {
|
|
170
|
+
const currentDefaultAccount = getConfigDefaultAccount();
|
|
171
|
+
|
|
172
|
+
return this.targetAccountId !== getAccountId(currentDefaultAccount)
|
|
173
|
+
? uiCommandReference(
|
|
174
|
+
`hs project upload --account=${this.targetAccountId}`
|
|
175
|
+
)
|
|
176
|
+
: uiCommandReference('hs project upload');
|
|
177
|
+
}
|
|
178
|
+
|
|
168
179
|
logUploadWarning(reason) {
|
|
180
|
+
const warning = reason || i18n(`${i18nKey}.uploadWarning.defaultWarning`);
|
|
181
|
+
|
|
169
182
|
// Avoid logging the warning to the console if it is currently the most
|
|
170
183
|
// recently logged warning. We do not want to spam the console with the same message.
|
|
171
|
-
if (!this.uploadWarnings[
|
|
172
|
-
const currentDefaultAccount = getConfigDefaultAccount();
|
|
173
|
-
const defaultAccountId = getAccountId(currentDefaultAccount);
|
|
174
|
-
|
|
184
|
+
if (!this.uploadWarnings[warning]) {
|
|
175
185
|
logger.log();
|
|
176
|
-
logger.warn(i18n(`${i18nKey}.uploadWarning.header`, {
|
|
186
|
+
logger.warn(i18n(`${i18nKey}.uploadWarning.header`, { warning }));
|
|
177
187
|
logger.log(
|
|
178
188
|
i18n(`${i18nKey}.uploadWarning.stopDev`, {
|
|
179
189
|
command: uiCommandReference('hs project dev'),
|
|
180
190
|
})
|
|
181
191
|
);
|
|
182
|
-
if (this.
|
|
183
|
-
logger.log(
|
|
184
|
-
i18n(`${i18nKey}.uploadWarning.runUploadWithAccount`, {
|
|
185
|
-
command: uiCommandReference(
|
|
186
|
-
`hs project upload --account=${this.targetAccountId}`
|
|
187
|
-
),
|
|
188
|
-
})
|
|
189
|
-
);
|
|
192
|
+
if (this.isGithubLinked) {
|
|
193
|
+
logger.log(i18n(`${i18nKey}.uploadWarning.pushToGithub`));
|
|
190
194
|
} else {
|
|
191
195
|
logger.log(
|
|
192
196
|
i18n(`${i18nKey}.uploadWarning.runUpload`, {
|
|
193
|
-
command:
|
|
197
|
+
command: this.getUploadCommand(),
|
|
194
198
|
})
|
|
195
199
|
);
|
|
196
200
|
}
|
|
@@ -200,8 +204,8 @@ class LocalDevManager {
|
|
|
200
204
|
})
|
|
201
205
|
);
|
|
202
206
|
|
|
203
|
-
this.mostRecentUploadWarning =
|
|
204
|
-
this.uploadWarnings[
|
|
207
|
+
this.mostRecentUploadWarning = warning;
|
|
208
|
+
this.uploadWarnings[warning] = true;
|
|
205
209
|
}
|
|
206
210
|
}
|
|
207
211
|
|
|
@@ -245,7 +249,7 @@ class LocalDevManager {
|
|
|
245
249
|
!deployedComponentNames.includes(cardConfig.data.title)
|
|
246
250
|
) {
|
|
247
251
|
missingComponents.push(
|
|
248
|
-
`${i18n(`${i18nKey}.uploadWarning.
|
|
252
|
+
`${i18n(`${i18nKey}.uploadWarning.uiExtensionLabel`)} ${
|
|
249
253
|
cardConfig.data.title
|
|
250
254
|
}`
|
|
251
255
|
);
|
|
@@ -298,11 +302,7 @@ class LocalDevManager {
|
|
|
298
302
|
|
|
299
303
|
handleWatchEvent(filePath, event, configPaths) {
|
|
300
304
|
if (configPaths.includes(filePath)) {
|
|
301
|
-
this.logUploadWarning(
|
|
302
|
-
i18n(`${i18nKey}.uploadWarning.configEdit`, {
|
|
303
|
-
path: path.relative(this.projectDir, filePath),
|
|
304
|
-
})
|
|
305
|
-
);
|
|
305
|
+
this.logUploadWarning();
|
|
306
306
|
} else {
|
|
307
307
|
this.devServerFileChange(filePath, event);
|
|
308
308
|
}
|
package/lib/projects.js
CHANGED
|
@@ -133,24 +133,15 @@ const createProjectConfig = async (
|
|
|
133
133
|
}`
|
|
134
134
|
);
|
|
135
135
|
|
|
136
|
+
await downloadGitHubRepoContents(templateSource, template.path, projectPath);
|
|
137
|
+
const _config = JSON.parse(fs.readFileSync(projectConfigPath));
|
|
138
|
+
writeProjectConfig(projectConfigPath, {
|
|
139
|
+
..._config,
|
|
140
|
+
name: projectName,
|
|
141
|
+
});
|
|
142
|
+
|
|
136
143
|
if (template.name === 'no-template') {
|
|
137
144
|
fs.ensureDirSync(path.join(projectPath, 'src'));
|
|
138
|
-
|
|
139
|
-
writeProjectConfig(projectConfigPath, {
|
|
140
|
-
name: projectName,
|
|
141
|
-
srcDir: 'src',
|
|
142
|
-
});
|
|
143
|
-
} else {
|
|
144
|
-
await downloadGitHubRepoContents(
|
|
145
|
-
templateSource,
|
|
146
|
-
template.path,
|
|
147
|
-
projectPath
|
|
148
|
-
);
|
|
149
|
-
const _config = JSON.parse(fs.readFileSync(projectConfigPath));
|
|
150
|
-
writeProjectConfig(projectConfigPath, {
|
|
151
|
-
..._config,
|
|
152
|
-
name: projectName,
|
|
153
|
-
});
|
|
154
145
|
}
|
|
155
146
|
|
|
156
147
|
return true;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
const { promptUser } = require('./promptUtils');
|
|
2
|
+
const { i18n } = require('../lang');
|
|
3
|
+
|
|
4
|
+
const i18nKey = 'cli.lib.prompts.cleanUploadPrompt';
|
|
5
|
+
|
|
6
|
+
const cleanUploadPrompt = async (accountId, filePath) => {
|
|
7
|
+
const promptAnswer = await promptUser([
|
|
8
|
+
{
|
|
9
|
+
name: 'cleanUpload',
|
|
10
|
+
message: i18n(`${i18nKey}.message`, { accountId, filePath }),
|
|
11
|
+
type: 'confirm',
|
|
12
|
+
default: false,
|
|
13
|
+
},
|
|
14
|
+
]);
|
|
15
|
+
return promptAnswer.cleanUpload;
|
|
16
|
+
};
|
|
17
|
+
|
|
18
|
+
module.exports = {
|
|
19
|
+
cleanUploadPrompt,
|
|
20
|
+
};
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
const { promptUser } = require('./promptUtils');
|
|
2
2
|
const { i18n } = require('../lang');
|
|
3
|
-
const { uiAccountDescription } = require('../ui');
|
|
3
|
+
const { uiAccountDescription, uiCommandReference } = require('../ui');
|
|
4
4
|
const { isSandbox, getAccountName } = require('../sandboxes');
|
|
5
5
|
const { getAccountId } = require('@hubspot/cli-lib');
|
|
6
6
|
const { getSandboxUsageLimits } = require('@hubspot/cli-lib/sandboxes');
|
|
@@ -26,13 +26,24 @@ const selectTargetAccountPrompt = async (accounts, defaultAccountConfig) => {
|
|
|
26
26
|
logger.debug('Unable to fetch sandbox usage limits: ', err);
|
|
27
27
|
}
|
|
28
28
|
|
|
29
|
-
const sandboxAccounts = accounts
|
|
29
|
+
const sandboxAccounts = accounts
|
|
30
|
+
.reverse()
|
|
31
|
+
.filter(
|
|
32
|
+
config => isSandbox(config) && config.parentAccountId === defaultAccountId
|
|
33
|
+
);
|
|
30
34
|
let disabledMessage = false;
|
|
31
35
|
|
|
32
36
|
if (sandboxUsage['DEVELOPER'] && sandboxUsage['DEVELOPER'].available === 0) {
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
37
|
+
if (sandboxAccounts.length < sandboxUsage['DEVELOPER'].limit) {
|
|
38
|
+
disabledMessage = i18n(`${i18nKey}.sandboxLimitWithSuggestion`, {
|
|
39
|
+
authCommand: uiCommandReference('hs auth'),
|
|
40
|
+
limit: sandboxUsage['DEVELOPER'].limit,
|
|
41
|
+
});
|
|
42
|
+
} else {
|
|
43
|
+
disabledMessage = i18n(`${i18nKey}.sandboxLimit`, {
|
|
44
|
+
limit: sandboxUsage['DEVELOPER'].limit,
|
|
45
|
+
});
|
|
46
|
+
}
|
|
36
47
|
}
|
|
37
48
|
|
|
38
49
|
// Order choices by Developer Sandbox -> Standard Sandbox
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
const { promptUser } = require('./promptUtils');
|
|
2
2
|
const { i18n } = require('../lang');
|
|
3
3
|
const { ensureProjectExists } = require('../projects');
|
|
4
|
+
const { uiAccountDescription } = require('../ui');
|
|
4
5
|
|
|
5
6
|
const i18nKey = 'cli.lib.prompts.projectNamePrompt';
|
|
6
7
|
|
|
@@ -20,7 +21,7 @@ const projectNamePrompt = (accountId, options = {}) => {
|
|
|
20
21
|
if (!projectExists) {
|
|
21
22
|
return i18n(`${i18nKey}.errors.projectDoesNotExist`, {
|
|
22
23
|
projectName: val,
|
|
23
|
-
accountId,
|
|
24
|
+
accountIdentifier: uiAccountDescription(accountId),
|
|
24
25
|
});
|
|
25
26
|
}
|
|
26
27
|
return true;
|
package/lib/ui.js
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
const process = require('process');
|
|
2
1
|
const chalk = require('chalk');
|
|
3
2
|
const supportsHyperlinks = require('../lib/supportHyperlinks');
|
|
4
3
|
const supportsColor = require('../lib/supportsColor');
|
|
@@ -42,11 +41,13 @@ const getTerminalUISupport = () => {
|
|
|
42
41
|
* @param {object} options
|
|
43
42
|
* @returns {string}
|
|
44
43
|
*/
|
|
45
|
-
const uiLink = (linkText, url
|
|
44
|
+
const uiLink = (linkText, url) => {
|
|
46
45
|
const terminalUISupport = getTerminalUISupport();
|
|
47
46
|
const encodedUrl = encodeURI(url);
|
|
47
|
+
|
|
48
48
|
if (terminalUISupport.hyperlinks) {
|
|
49
49
|
const CLOSE_SEQUENCE = '\u001B]8;;\u0007';
|
|
50
|
+
|
|
50
51
|
const result = [
|
|
51
52
|
'\u001B]8;;',
|
|
52
53
|
encodedUrl,
|
|
@@ -55,16 +56,7 @@ const uiLink = (linkText, url, { inSpinnies = false } = {}) => {
|
|
|
55
56
|
CLOSE_SEQUENCE,
|
|
56
57
|
].join('');
|
|
57
58
|
|
|
58
|
-
|
|
59
|
-
// See https://github.com/jbcarpanelli/spinnies/blob/d672dedcab8c8ce0f6de0bb26ca5582bf602afd7/utils.js#L68-L74
|
|
60
|
-
const indent = 5;
|
|
61
|
-
const columns =
|
|
62
|
-
(process.stderr.columns || 95) - CLOSE_SEQUENCE.length - indent;
|
|
63
|
-
const validLength = !inSpinnies || result.length < columns;
|
|
64
|
-
|
|
65
|
-
if (validLength) {
|
|
66
|
-
return terminalUISupport.color ? chalk.cyan(result) : result;
|
|
67
|
-
}
|
|
59
|
+
return terminalUISupport.color ? chalk.cyan(result) : result;
|
|
68
60
|
}
|
|
69
61
|
|
|
70
62
|
return terminalUISupport.color
|
|
@@ -95,7 +87,15 @@ const uiInfoSection = (title, logContent) => {
|
|
|
95
87
|
};
|
|
96
88
|
|
|
97
89
|
const uiCommandReference = command => {
|
|
98
|
-
|
|
90
|
+
const terminalUISupport = getTerminalUISupport();
|
|
91
|
+
|
|
92
|
+
const commandReference = `\`${command}\``;
|
|
93
|
+
|
|
94
|
+
return chalk.bold(
|
|
95
|
+
terminalUISupport.color
|
|
96
|
+
? chalk.hex(UI_COLORS.MARIGOLD_DARK)(commandReference)
|
|
97
|
+
: commandReference
|
|
98
|
+
);
|
|
99
99
|
};
|
|
100
100
|
|
|
101
101
|
const uiFeatureHighlight = (commands, title) => {
|
|
@@ -105,7 +105,7 @@ const uiFeatureHighlight = (commands, title) => {
|
|
|
105
105
|
commands.forEach((c, i) => {
|
|
106
106
|
const commandKey = `${i18nKey}.commandKeys.${c}`;
|
|
107
107
|
const message = i18n(`${commandKey}.message`, {
|
|
108
|
-
command:
|
|
108
|
+
command: uiCommandReference(i18n(`${commandKey}.command`)),
|
|
109
109
|
});
|
|
110
110
|
if (i !== 0) {
|
|
111
111
|
logger.log('');
|
|
@@ -115,26 +115,28 @@ const uiFeatureHighlight = (commands, title) => {
|
|
|
115
115
|
});
|
|
116
116
|
};
|
|
117
117
|
|
|
118
|
-
const
|
|
118
|
+
const uiBetaTag = (message, log = true) => {
|
|
119
119
|
const i18nKey = 'cli.lib.ui';
|
|
120
120
|
|
|
121
|
-
|
|
122
|
-
};
|
|
121
|
+
const terminalUISupport = getTerminalUISupport();
|
|
122
|
+
const tag = i18n(`${i18nKey}.betaTag`);
|
|
123
123
|
|
|
124
|
-
const
|
|
125
|
-
|
|
124
|
+
const result = `${
|
|
125
|
+
terminalUISupport.color ? chalk.hex(UI_COLORS.SORBET)(tag) : tag
|
|
126
|
+
} ${message}`;
|
|
126
127
|
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
128
|
+
if (log) {
|
|
129
|
+
logger.log(result);
|
|
130
|
+
} else {
|
|
131
|
+
return result;
|
|
132
|
+
}
|
|
130
133
|
};
|
|
131
134
|
|
|
132
135
|
module.exports = {
|
|
133
136
|
UI_COLORS,
|
|
134
137
|
uiAccountDescription,
|
|
135
138
|
uiCommandReference,
|
|
136
|
-
|
|
137
|
-
uiBetaWarning,
|
|
139
|
+
uiBetaTag,
|
|
138
140
|
uiFeatureHighlight,
|
|
139
141
|
uiInfoSection,
|
|
140
142
|
uiLine,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@hubspot/cli",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "5.0.0",
|
|
4
4
|
"description": "CLI for working with HubSpot",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"repository": {
|
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
"dependencies": {
|
|
11
11
|
"@hubspot/cli-lib": "^4.2.2",
|
|
12
12
|
"@hubspot/serverless-dev-runtime": "4.2.1-beta.3",
|
|
13
|
-
"@hubspot/ui-extensions-dev-server": "^0.7.
|
|
13
|
+
"@hubspot/ui-extensions-dev-server": "^0.7.2",
|
|
14
14
|
"archiver": "^5.3.0",
|
|
15
15
|
"chalk": "^4.1.2",
|
|
16
16
|
"chokidar": "^3.0.1",
|
|
@@ -42,5 +42,5 @@
|
|
|
42
42
|
"publishConfig": {
|
|
43
43
|
"access": "public"
|
|
44
44
|
},
|
|
45
|
-
"gitHead": "
|
|
45
|
+
"gitHead": "c84420be1abb52575cf159de243d41542653d0bb"
|
|
46
46
|
}
|