@hubspot/cli 5.2.1-beta.1 → 5.2.1-beta.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bin/cli.js +1 -1
- package/bin/hs +1 -1
- package/commands/accounts/clean.js +7 -7
- package/commands/accounts/info.js +3 -3
- package/commands/accounts/list.js +7 -18
- package/commands/accounts/remove.js +1 -1
- package/commands/accounts/rename.js +3 -3
- package/commands/accounts/use.js +1 -1
- package/commands/accounts.js +3 -3
- package/commands/auth.js +7 -9
- package/commands/cms/convertFields.js +1 -1
- package/commands/cms/lighthouseScore.js +4 -4
- package/commands/cms/reactModules.js +1 -1
- package/commands/cms.js +3 -3
- package/commands/config/set/allowUsageTracking.js +1 -2
- package/commands/config/set/defaultMode.js +1 -1
- package/commands/config/set/httpTimeout.js +1 -1
- package/commands/config/set.js +1 -1
- package/commands/config.js +3 -3
- package/commands/create/api-sample.js +1 -1
- package/commands/create/module.js +1 -1
- package/commands/create/template.js +1 -1
- package/commands/create.js +1 -1
- package/commands/customObject/create.js +1 -1
- package/commands/customObject/schema/create.js +2 -3
- package/commands/customObject/schema/delete.js +1 -2
- package/commands/customObject/schema/fetch-all.js +1 -2
- package/commands/customObject/schema/fetch.js +1 -2
- package/commands/customObject/schema/list.js +1 -1
- package/commands/customObject/schema/update.js +2 -3
- package/commands/customObject/schema.js +1 -1
- package/commands/customObject.js +3 -3
- package/commands/feedback.js +4 -6
- package/commands/fetch.js +6 -6
- package/commands/filemanager/fetch.js +4 -4
- package/commands/filemanager/upload.js +4 -4
- package/commands/filemanager.js +4 -4
- package/commands/functions/deploy.js +7 -23
- package/commands/functions/list.js +4 -4
- package/commands/functions/server.js +4 -4
- package/commands/functions.js +3 -3
- package/commands/hubdb/clear.js +4 -4
- package/commands/hubdb/create.js +4 -4
- package/commands/hubdb/delete.js +4 -4
- package/commands/hubdb/fetch.js +4 -4
- package/commands/hubdb.js +3 -3
- package/commands/init.js +6 -8
- package/commands/lint.js +3 -3
- package/commands/list.js +4 -4
- package/commands/logs.js +4 -4
- package/commands/module/marketplace-validate.js +5 -5
- package/commands/module.js +3 -3
- package/commands/mv.js +4 -4
- package/commands/open.js +4 -4
- package/commands/project/add.js +1 -1
- package/commands/project/create.js +4 -4
- package/commands/project/deploy.js +4 -4
- package/commands/project/dev.js +70 -27
- package/commands/project/download.js +11 -7
- package/commands/project/listBuilds.js +4 -4
- package/commands/project/logs.js +4 -4
- package/commands/project/migrateApp.js +227 -0
- package/commands/project/open.js +12 -8
- package/commands/project/upload.js +13 -8
- package/commands/project/watch.js +4 -4
- package/commands/project.js +5 -3
- package/commands/remove.js +4 -4
- package/commands/sandbox/create.js +16 -16
- package/commands/sandbox/delete.js +5 -5
- package/commands/sandbox/sync.js +6 -6
- package/commands/sandbox.js +3 -3
- package/commands/secrets/addSecret.js +4 -4
- package/commands/secrets/deleteSecret.js +4 -4
- package/commands/secrets/listSecrets.js +4 -4
- package/commands/secrets/updateSecret.js +4 -4
- package/commands/secrets.js +3 -3
- package/commands/theme/generate-selectors.js +1 -1
- package/commands/theme/marketplace-validate.js +5 -5
- package/commands/theme/preview.js +52 -17
- package/commands/theme.js +1 -1
- package/commands/upload.js +5 -5
- package/commands/watch.js +61 -18
- package/jest.config.js +1 -0
- package/lang/en.lyaml +1425 -1371
- package/lib/DevServerManager.js +3 -2
- package/lib/LocalDevManager.js +165 -7
- package/lib/__tests__/{commonOpts.js → commonOpts.test.js} +3 -0
- package/lib/__tests__/downloadProjectPrompt.test.js +31 -0
- package/lib/__tests__/projects.test.js +13 -17
- package/lib/__tests__/{serverlessLogs.js → serverlessLogs.test.js} +1 -0
- package/lib/buildAccount.js +197 -0
- package/lib/commonOpts.js +1 -1
- package/lib/constants.js +10 -0
- package/lib/developerTestAccounts.js +52 -4
- package/lib/errorHandlers/apiErrors.js +1 -1
- package/lib/errorHandlers/overrideErrors.js +1 -1
- package/lib/errorHandlers/standardErrors.js +1 -1
- package/lib/generate-selectors.js +1 -1
- package/lib/localDev.js +102 -52
- package/lib/marketplace-validate.js +11 -3
- package/lib/polling.js +26 -0
- package/lib/process.js +1 -1
- package/lib/projectStructure.js +5 -2
- package/lib/projects.js +65 -12
- package/lib/projectsWatch.js +1 -1
- package/lib/prompts/accountNamePrompt.js +81 -0
- package/lib/prompts/accountsPrompt.js +1 -1
- package/lib/prompts/activeInstallConfirmationPrompt.js +20 -0
- package/lib/prompts/buildIdPrompt.js +1 -1
- package/lib/prompts/cleanUploadPrompt.js +1 -1
- package/lib/prompts/cmsFieldPrompt.js +1 -1
- package/lib/prompts/createApiSamplePrompt.js +1 -1
- package/lib/prompts/createFunctionPrompt.js +1 -1
- package/lib/prompts/createModulePrompt.js +1 -1
- package/lib/prompts/createProjectPrompt.js +32 -10
- package/lib/prompts/createTemplatePrompt.js +1 -1
- package/lib/prompts/downloadProjectPrompt.js +5 -6
- package/lib/prompts/feedbackPrompt.js +1 -1
- package/lib/prompts/folderOverwritePrompt.js +1 -1
- package/lib/prompts/installPublicAppPrompt.js +42 -0
- package/lib/prompts/personalAccessKeyPrompt.js +3 -3
- package/lib/prompts/previewPrompt.js +19 -1
- package/lib/prompts/projectAddPrompt.js +1 -1
- package/lib/prompts/projectDevTargetAccountPrompt.js +48 -6
- package/lib/prompts/projectNamePrompt.js +2 -2
- package/lib/prompts/projectsLogsPrompt.js +1 -1
- package/lib/prompts/sandboxesPrompt.js +13 -42
- package/lib/prompts/secretPrompt.js +1 -1
- package/lib/prompts/selectPublicAppPrompt.js +69 -0
- package/lib/prompts/setAsDefaultAccountPrompt.js +1 -1
- package/lib/prompts/uploadPrompt.js +1 -1
- package/lib/sandboxSync.js +1 -1
- package/lib/sandboxes.js +167 -14
- package/lib/ui/git.js +1 -1
- package/lib/ui/index.js +5 -22
- package/lib/ui/serverlessFunctionLogs.js +1 -1
- package/package.json +6 -6
- package/lib/developerTestAccountCreate.js +0 -186
- package/lib/prompts/developerTestAccountNamePrompt.js +0 -29
- package/lib/prompts/enterAccountNamePrompt.js +0 -33
- package/lib/sandboxCreate.js +0 -319
- /package/lib/__tests__/{validation.js → validation.test.js} +0 -0
package/lib/projects.js
CHANGED
|
@@ -17,6 +17,7 @@ const {
|
|
|
17
17
|
PROJECT_DEPLOY_TEXT,
|
|
18
18
|
PROJECT_CONFIG_FILE,
|
|
19
19
|
PROJECT_TASK_TYPES,
|
|
20
|
+
PROJECT_ERROR_TYPES,
|
|
20
21
|
} = require('./constants');
|
|
21
22
|
const {
|
|
22
23
|
createProject,
|
|
@@ -47,7 +48,7 @@ const {
|
|
|
47
48
|
} = require('./errorHandlers/apiErrors');
|
|
48
49
|
const { HUBSPOT_PROJECT_COMPONENTS_GITHUB_PATH } = require('./constants');
|
|
49
50
|
|
|
50
|
-
const i18nKey = '
|
|
51
|
+
const i18nKey = 'lib.projects';
|
|
51
52
|
|
|
52
53
|
const SPINNER_STATUS = {
|
|
53
54
|
SPINNING: 'spinning',
|
|
@@ -252,7 +253,7 @@ const ensureProjectExists = async (
|
|
|
252
253
|
const project = withPolling
|
|
253
254
|
? await pollFetchProject(accountId, projectName)
|
|
254
255
|
: await fetchProject(accountId, projectName);
|
|
255
|
-
return !!project;
|
|
256
|
+
return { projectExists: !!project, project };
|
|
256
257
|
} catch (err) {
|
|
257
258
|
if (isSpecifiedError(err, { statusCode: 404 })) {
|
|
258
259
|
let shouldCreateProject = forceCreate;
|
|
@@ -273,14 +274,14 @@ const ensureProjectExists = async (
|
|
|
273
274
|
|
|
274
275
|
if (shouldCreateProject) {
|
|
275
276
|
try {
|
|
276
|
-
await createProject(accountId, projectName);
|
|
277
|
+
const project = await createProject(accountId, projectName);
|
|
277
278
|
logger.success(
|
|
278
279
|
i18n(`${i18nKey}.ensureProjectExists.createSuccess`, {
|
|
279
280
|
projectName,
|
|
280
281
|
accountIdentifier,
|
|
281
282
|
})
|
|
282
283
|
);
|
|
283
|
-
return true;
|
|
284
|
+
return { projectExists: true, project };
|
|
284
285
|
} catch (err) {
|
|
285
286
|
return logApiErrorInstance(
|
|
286
287
|
err,
|
|
@@ -296,7 +297,7 @@ const ensureProjectExists = async (
|
|
|
296
297
|
})
|
|
297
298
|
);
|
|
298
299
|
}
|
|
299
|
-
return false;
|
|
300
|
+
return { projectExists: false };
|
|
300
301
|
}
|
|
301
302
|
}
|
|
302
303
|
if (
|
|
@@ -698,9 +699,51 @@ const makePollTaskStatusFunc = ({
|
|
|
698
699
|
|
|
699
700
|
return new Promise((resolve, reject) => {
|
|
700
701
|
const pollInterval = setInterval(async () => {
|
|
701
|
-
|
|
702
|
-
|
|
703
|
-
|
|
702
|
+
let taskStatus;
|
|
703
|
+
try {
|
|
704
|
+
taskStatus = await statusFn(accountId, taskName, taskId);
|
|
705
|
+
} catch (e) {
|
|
706
|
+
logApiErrorInstance(
|
|
707
|
+
e,
|
|
708
|
+
new ApiErrorContext({
|
|
709
|
+
accountId,
|
|
710
|
+
projectName: taskName,
|
|
711
|
+
})
|
|
712
|
+
);
|
|
713
|
+
return reject(
|
|
714
|
+
new Error(
|
|
715
|
+
i18n(
|
|
716
|
+
`${i18nKey}.makePollTaskStatusFunc.errorFetchingTaskStatus`,
|
|
717
|
+
{
|
|
718
|
+
taskType:
|
|
719
|
+
statusText.TYPE_KEY === PROJECT_BUILD_TEXT.TYPE_KEY
|
|
720
|
+
? 'build'
|
|
721
|
+
: 'deploy',
|
|
722
|
+
}
|
|
723
|
+
)
|
|
724
|
+
)
|
|
725
|
+
);
|
|
726
|
+
}
|
|
727
|
+
|
|
728
|
+
if (
|
|
729
|
+
!taskStatus ||
|
|
730
|
+
!taskStatus.status ||
|
|
731
|
+
!taskStatus[statusText.SUBTASK_KEY]
|
|
732
|
+
) {
|
|
733
|
+
return reject(
|
|
734
|
+
new Error(
|
|
735
|
+
i18n(
|
|
736
|
+
`${i18nKey}.makePollTaskStatusFunc.errorFetchingTaskStatus`,
|
|
737
|
+
{
|
|
738
|
+
taskType:
|
|
739
|
+
statusText.TYPE_KEY === PROJECT_BUILD_TEXT.TYPE_KEY
|
|
740
|
+
? 'build'
|
|
741
|
+
: 'deploy',
|
|
742
|
+
}
|
|
743
|
+
)
|
|
744
|
+
)
|
|
745
|
+
);
|
|
746
|
+
}
|
|
704
747
|
|
|
705
748
|
const { status, [statusText.SUBTASK_KEY]: subTaskStatus } = taskStatus;
|
|
706
749
|
|
|
@@ -772,7 +815,9 @@ const makePollTaskStatusFunc = ({
|
|
|
772
815
|
const displayErrors = failedSubtasks.filter(
|
|
773
816
|
subtask =>
|
|
774
817
|
subtask.standardError.subCategory !==
|
|
775
|
-
|
|
818
|
+
PROJECT_ERROR_TYPES.SUBBUILD_FAILED &&
|
|
819
|
+
subtask.standardError.subCategory !==
|
|
820
|
+
PROJECT_ERROR_TYPES.SUBDEPLOY_FAILED
|
|
776
821
|
);
|
|
777
822
|
|
|
778
823
|
displayErrors.forEach(subTask => {
|
|
@@ -859,7 +904,7 @@ const createProjectComponent = async (
|
|
|
859
904
|
name,
|
|
860
905
|
projectComponentsVersion
|
|
861
906
|
) => {
|
|
862
|
-
const i18nKey = '
|
|
907
|
+
const i18nKey = 'commands.project.subcommands.add';
|
|
863
908
|
let componentName = name;
|
|
864
909
|
|
|
865
910
|
const configInfo = await getProjectConfig();
|
|
@@ -893,9 +938,17 @@ const displayWarnLogs = async (
|
|
|
893
938
|
let result;
|
|
894
939
|
|
|
895
940
|
if (isDeploy) {
|
|
896
|
-
|
|
941
|
+
try {
|
|
942
|
+
result = await fetchDeployWarnLogs(accountId, projectName, taskId);
|
|
943
|
+
} catch (e) {
|
|
944
|
+
logApiErrorInstance(e);
|
|
945
|
+
}
|
|
897
946
|
} else {
|
|
898
|
-
|
|
947
|
+
try {
|
|
948
|
+
result = await fetchBuildWarnLogs(accountId, projectName, taskId);
|
|
949
|
+
} catch (e) {
|
|
950
|
+
logApiErrorInstance(e);
|
|
951
|
+
}
|
|
899
952
|
}
|
|
900
953
|
|
|
901
954
|
if (result && result.logs.length) {
|
package/lib/projectsWatch.js
CHANGED
|
@@ -20,7 +20,7 @@ const {
|
|
|
20
20
|
const { isSpecifiedError } = require('@hubspot/local-dev-lib/errors/apiErrors');
|
|
21
21
|
const { PROJECT_ERROR_TYPES } = require('./constants');
|
|
22
22
|
|
|
23
|
-
const i18nKey = '
|
|
23
|
+
const i18nKey = 'commands.project.subcommands.watch';
|
|
24
24
|
|
|
25
25
|
const queue = new PQueue({
|
|
26
26
|
concurrency: 10,
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
const { accountNameExistsInConfig } = require('@hubspot/local-dev-lib/config');
|
|
2
|
+
const { STRING_WITH_NO_SPACES_REGEX } = require('../regex');
|
|
3
|
+
const { promptUser } = require('./promptUtils');
|
|
4
|
+
const { i18n } = require('../lang');
|
|
5
|
+
const {
|
|
6
|
+
HUBSPOT_ACCOUNT_TYPES,
|
|
7
|
+
} = require('@hubspot/local-dev-lib/constants/config');
|
|
8
|
+
|
|
9
|
+
const i18nKey = 'lib.prompts.accountNamePrompt';
|
|
10
|
+
|
|
11
|
+
const getCliAccountNamePromptConfig = defaultName => ({
|
|
12
|
+
name: 'name',
|
|
13
|
+
message: i18n(`${i18nKey}.enterAccountName`),
|
|
14
|
+
default: defaultName,
|
|
15
|
+
validate(val) {
|
|
16
|
+
if (typeof val !== 'string') {
|
|
17
|
+
return i18n(`${i18nKey}.errors.invalidName`);
|
|
18
|
+
} else if (!val.length) {
|
|
19
|
+
return i18n(`${i18nKey}.errors.nameRequired`);
|
|
20
|
+
} else if (!STRING_WITH_NO_SPACES_REGEX.test(val)) {
|
|
21
|
+
return i18n(`${i18nKey}.errors.spacesInName`);
|
|
22
|
+
}
|
|
23
|
+
return accountNameExistsInConfig(val)
|
|
24
|
+
? i18n(`${i18nKey}.errors.accountNameExists`, { name: val })
|
|
25
|
+
: true;
|
|
26
|
+
},
|
|
27
|
+
});
|
|
28
|
+
|
|
29
|
+
const cliAccountNamePrompt = defaultName => {
|
|
30
|
+
return promptUser(getCliAccountNamePromptConfig(defaultName));
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
const hubspotAccountNamePrompt = ({ accountType, currentPortalCount = 0 }) => {
|
|
34
|
+
const isDevelopmentSandbox =
|
|
35
|
+
accountType === HUBSPOT_ACCOUNT_TYPES.DEVELOPMENT_SANDBOX;
|
|
36
|
+
const isSandbox =
|
|
37
|
+
accountType === HUBSPOT_ACCOUNT_TYPES.STANDARD_SANDBOX ||
|
|
38
|
+
isDevelopmentSandbox;
|
|
39
|
+
const isDeveloperTestAccount =
|
|
40
|
+
accountType === HUBSPOT_ACCOUNT_TYPES.DEVELOPER_TEST;
|
|
41
|
+
|
|
42
|
+
let promptMessageString;
|
|
43
|
+
let defaultName;
|
|
44
|
+
if (isSandbox) {
|
|
45
|
+
promptMessageString = isDevelopmentSandbox
|
|
46
|
+
? i18n(`${i18nKey}.enterDevelopmentSandboxName`)
|
|
47
|
+
: i18n(`${i18nKey}.enterStandardSandboxName`);
|
|
48
|
+
defaultName = i18n(`${i18nKey}.sandboxDefaultName`, {
|
|
49
|
+
sandboxType: isDevelopmentSandbox ? 'development' : 'standard',
|
|
50
|
+
});
|
|
51
|
+
} else if (isDeveloperTestAccount) {
|
|
52
|
+
promptMessageString = i18n(`${i18nKey}.enterDeveloperTestAccountName`);
|
|
53
|
+
defaultName = i18n(`${i18nKey}.developerTestAccountDefaultName`, {
|
|
54
|
+
count: currentPortalCount + 1,
|
|
55
|
+
});
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
return promptUser([
|
|
59
|
+
{
|
|
60
|
+
name: 'name',
|
|
61
|
+
message: promptMessageString,
|
|
62
|
+
validate(val) {
|
|
63
|
+
if (typeof val !== 'string') {
|
|
64
|
+
return i18n(`${i18nKey}.errors.invalidName`);
|
|
65
|
+
} else if (!val.length) {
|
|
66
|
+
return i18n(`${i18nKey}.errors.nameRequired`);
|
|
67
|
+
}
|
|
68
|
+
return accountNameExistsInConfig(val)
|
|
69
|
+
? i18n(`${i18nKey}.errors.accountNameExists`, { name: val })
|
|
70
|
+
: true;
|
|
71
|
+
},
|
|
72
|
+
default: defaultName,
|
|
73
|
+
},
|
|
74
|
+
]);
|
|
75
|
+
};
|
|
76
|
+
|
|
77
|
+
module.exports = {
|
|
78
|
+
getCliAccountNamePromptConfig,
|
|
79
|
+
cliAccountNamePrompt,
|
|
80
|
+
hubspotAccountNamePrompt,
|
|
81
|
+
};
|
|
@@ -9,7 +9,7 @@ const mapAccountChoices = portals =>
|
|
|
9
9
|
value: p.name || p.portalId,
|
|
10
10
|
}));
|
|
11
11
|
|
|
12
|
-
const i18nKey = '
|
|
12
|
+
const i18nKey = 'commands.accounts.subcommands.use';
|
|
13
13
|
|
|
14
14
|
const selectAccountFromConfig = async (config, prompt) => {
|
|
15
15
|
const { default: selectedDefault } = await promptUser([
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
const { promptUser } = require('./promptUtils');
|
|
2
|
+
const { i18n } = require('../lang');
|
|
3
|
+
|
|
4
|
+
const i18nKey = 'lib.prompts.activeInstallConfirmationPrompt';
|
|
5
|
+
|
|
6
|
+
const activeInstallConfirmationPrompt = async () => {
|
|
7
|
+
const { proceed } = await promptUser([
|
|
8
|
+
{
|
|
9
|
+
name: 'proceed',
|
|
10
|
+
message: i18n(`${i18nKey}.message`),
|
|
11
|
+
type: 'confirm',
|
|
12
|
+
default: false,
|
|
13
|
+
},
|
|
14
|
+
]);
|
|
15
|
+
return proceed;
|
|
16
|
+
};
|
|
17
|
+
|
|
18
|
+
module.exports = {
|
|
19
|
+
activeInstallConfirmationPrompt,
|
|
20
|
+
};
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
const { promptUser } = require('./promptUtils');
|
|
2
2
|
const { i18n } = require('../lang');
|
|
3
3
|
|
|
4
|
-
const i18nKey = '
|
|
4
|
+
const i18nKey = 'lib.prompts.buildIdPrompt';
|
|
5
5
|
|
|
6
6
|
const buildIdPrompt = (latestBuildId, deployedBuildId, projectName) => {
|
|
7
7
|
return promptUser({
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
const { promptUser } = require('./promptUtils');
|
|
2
2
|
const { i18n } = require('../lang');
|
|
3
3
|
|
|
4
|
-
const i18nKey = '
|
|
4
|
+
const i18nKey = 'lib.prompts.cleanUploadPrompt';
|
|
5
5
|
|
|
6
6
|
const cleanUploadPrompt = async (accountId, filePath) => {
|
|
7
7
|
const promptAnswer = await promptUser([
|
|
@@ -3,7 +3,7 @@ const fs = require('fs');
|
|
|
3
3
|
const { promptUser } = require('./promptUtils');
|
|
4
4
|
const { i18n } = require('../lang');
|
|
5
5
|
const escapeRegExp = require('@hubspot/local-dev-lib/escapeRegExp');
|
|
6
|
-
const i18nKey = '
|
|
6
|
+
const i18nKey = 'lib.prompts.uploadPrompt';
|
|
7
7
|
const FIELDS_FILES = ['fields.json', 'fields.js', 'fields.cjs', 'fields.mjs'];
|
|
8
8
|
|
|
9
9
|
const fieldsJsPrompt = async (filePath, projectDir, skipFiles = []) => {
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
const { promptUser } = require('./promptUtils');
|
|
2
2
|
const { i18n } = require('../lang');
|
|
3
3
|
|
|
4
|
-
const i18nKey = '
|
|
4
|
+
const i18nKey = 'lib.prompts.createApiSamplePrompt';
|
|
5
5
|
|
|
6
6
|
const getSampleTypesPrompt = choices => ({
|
|
7
7
|
type: 'rawlist',
|
|
@@ -3,7 +3,7 @@ const { i18n } = require('../lang');
|
|
|
3
3
|
|
|
4
4
|
const { STRING_WITH_NO_SPACES_REGEX } = require('../regex');
|
|
5
5
|
|
|
6
|
-
const i18nKey = '
|
|
6
|
+
const i18nKey = 'lib.prompts.createFunctionPrompt';
|
|
7
7
|
|
|
8
8
|
const FUNCTIONS_FOLDER_PROMPT = {
|
|
9
9
|
name: 'functionsFolder',
|
|
@@ -1,5 +1,10 @@
|
|
|
1
|
+
const fs = require('fs');
|
|
1
2
|
const path = require('path');
|
|
2
|
-
const {
|
|
3
|
+
const {
|
|
4
|
+
getCwd,
|
|
5
|
+
sanitizeFileName,
|
|
6
|
+
isValidPath,
|
|
7
|
+
} = require('@hubspot/local-dev-lib/path');
|
|
3
8
|
const { PROJECT_COMPONENT_TYPES } = require('../../lib/constants');
|
|
4
9
|
const { promptUser } = require('./promptUtils');
|
|
5
10
|
const { fetchFileFromRepository } = require('@hubspot/local-dev-lib/github');
|
|
@@ -11,7 +16,7 @@ const {
|
|
|
11
16
|
DEFAULT_PROJECT_TEMPLATE_BRANCH,
|
|
12
17
|
} = require('../constants');
|
|
13
18
|
|
|
14
|
-
const i18nKey = '
|
|
19
|
+
const i18nKey = 'lib.prompts.createProjectPrompt';
|
|
15
20
|
|
|
16
21
|
const PROJECT_PROPERTIES = ['name', 'label', 'path', 'insertPath'];
|
|
17
22
|
|
|
@@ -48,11 +53,18 @@ const createTemplateOptions = async (templateSource, githubRef) => {
|
|
|
48
53
|
return config[PROJECT_COMPONENT_TYPES.PROJECTS];
|
|
49
54
|
};
|
|
50
55
|
|
|
51
|
-
const createProjectPrompt = async (
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
+
const createProjectPrompt = async (
|
|
57
|
+
githubRef,
|
|
58
|
+
promptOptions = {},
|
|
59
|
+
skipTemplatePrompt = false
|
|
60
|
+
) => {
|
|
61
|
+
let projectTemplates = [];
|
|
62
|
+
if (!skipTemplatePrompt) {
|
|
63
|
+
projectTemplates = await createTemplateOptions(
|
|
64
|
+
promptOptions.templateSource,
|
|
65
|
+
githubRef
|
|
66
|
+
);
|
|
67
|
+
}
|
|
56
68
|
|
|
57
69
|
return promptUser([
|
|
58
70
|
{
|
|
@@ -71,12 +83,21 @@ const createProjectPrompt = async (githubRef, promptOptions = {}) => {
|
|
|
71
83
|
message: i18n(`${i18nKey}.enterLocation`),
|
|
72
84
|
when: !promptOptions.location,
|
|
73
85
|
default: answers => {
|
|
74
|
-
|
|
86
|
+
const projectName = sanitizeFileName(
|
|
87
|
+
answers.name || promptOptions.name
|
|
88
|
+
);
|
|
89
|
+
return path.resolve(getCwd(), projectName);
|
|
75
90
|
},
|
|
76
91
|
validate: input => {
|
|
77
92
|
if (!input) {
|
|
78
93
|
return i18n(`${i18nKey}.errors.locationRequired`);
|
|
79
94
|
}
|
|
95
|
+
if (fs.existsSync(input)) {
|
|
96
|
+
return i18n(`${i18nKey}.errors.invalidLocation`);
|
|
97
|
+
}
|
|
98
|
+
if (!isValidPath(input)) {
|
|
99
|
+
return i18n(`${i18nKey}.errors.invalidCharacters`);
|
|
100
|
+
}
|
|
80
101
|
return true;
|
|
81
102
|
},
|
|
82
103
|
},
|
|
@@ -91,8 +112,9 @@ const createProjectPrompt = async (githubRef, promptOptions = {}) => {
|
|
|
91
112
|
: i18n(`${i18nKey}.selectTemplate`);
|
|
92
113
|
},
|
|
93
114
|
when:
|
|
94
|
-
!
|
|
95
|
-
!
|
|
115
|
+
!skipTemplatePrompt &&
|
|
116
|
+
(!promptOptions.template ||
|
|
117
|
+
!projectTemplates.find(t => t.name === promptOptions.template)),
|
|
96
118
|
type: 'list',
|
|
97
119
|
choices: projectTemplates.map(template => {
|
|
98
120
|
return {
|
|
@@ -8,11 +8,9 @@ const {
|
|
|
8
8
|
const { EXIT_CODES } = require('../enums/exitCodes');
|
|
9
9
|
const { i18n } = require('../lang');
|
|
10
10
|
|
|
11
|
-
const i18nKey = '
|
|
12
|
-
|
|
13
|
-
const createProjectsList = async () => {
|
|
14
|
-
const accountId = getAccountId();
|
|
11
|
+
const i18nKey = 'lib.prompts.downloadProjectPrompt';
|
|
15
12
|
|
|
13
|
+
const createProjectsList = async accountId => {
|
|
16
14
|
try {
|
|
17
15
|
const projects = await fetchProjects(accountId);
|
|
18
16
|
return projects.results;
|
|
@@ -23,7 +21,8 @@ const createProjectsList = async () => {
|
|
|
23
21
|
};
|
|
24
22
|
|
|
25
23
|
const downloadProjectPrompt = async (promptOptions = {}) => {
|
|
26
|
-
const
|
|
24
|
+
const accountId = getAccountId(promptOptions.account);
|
|
25
|
+
const projectsList = await createProjectsList(accountId);
|
|
27
26
|
|
|
28
27
|
return promptUser([
|
|
29
28
|
{
|
|
@@ -33,7 +32,7 @@ const downloadProjectPrompt = async (promptOptions = {}) => {
|
|
|
33
32
|
!projectsList.find(p => p.name === promptOptions.name)
|
|
34
33
|
? i18n(`${i18nKey}.errors.projectNotFound`, {
|
|
35
34
|
projectName: promptOptions.project,
|
|
36
|
-
accountId
|
|
35
|
+
accountId,
|
|
37
36
|
})
|
|
38
37
|
: i18n(`${i18nKey}.selectProject`);
|
|
39
38
|
},
|
|
@@ -2,7 +2,7 @@ const { promptUser } = require('./promptUtils');
|
|
|
2
2
|
const { i18n } = require('../lang');
|
|
3
3
|
const { FEEDBACK_OPTIONS } = require('../constants');
|
|
4
4
|
|
|
5
|
-
const i18nKey = '
|
|
5
|
+
const i18nKey = 'lib.prompts.feedbackPrompt';
|
|
6
6
|
|
|
7
7
|
const feedbackTypePrompt = bypassPrompt => {
|
|
8
8
|
return promptUser([
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
const { promptUser } = require('./promptUtils');
|
|
2
2
|
const { i18n } = require('../lang');
|
|
3
3
|
|
|
4
|
-
const i18nKey = '
|
|
4
|
+
const i18nKey = 'lib.prompts.folderOverwritePrompt';
|
|
5
5
|
|
|
6
6
|
const folderOverwritePrompt = folderName => {
|
|
7
7
|
return promptUser({
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
const open = require('open');
|
|
2
|
+
const { getHubSpotWebsiteOrigin } = require('@hubspot/local-dev-lib/urls');
|
|
3
|
+
const { logger } = require('@hubspot/local-dev-lib/logger');
|
|
4
|
+
const { promptUser } = require('./promptUtils');
|
|
5
|
+
const { i18n } = require('../lang');
|
|
6
|
+
const { EXIT_CODES } = require('../enums/exitCodes');
|
|
7
|
+
|
|
8
|
+
const i18nKey = 'lib.prompts.installPublicAppPrompt';
|
|
9
|
+
|
|
10
|
+
const installPublicAppPrompt = async (
|
|
11
|
+
env,
|
|
12
|
+
targetAccountId,
|
|
13
|
+
clientId,
|
|
14
|
+
scopes,
|
|
15
|
+
redirectUrls
|
|
16
|
+
) => {
|
|
17
|
+
logger.log('');
|
|
18
|
+
logger.log(i18n(`${i18nKey}.explanation`));
|
|
19
|
+
|
|
20
|
+
const { shouldOpenBrowser } = await promptUser({
|
|
21
|
+
name: 'shouldOpenBrowser',
|
|
22
|
+
type: 'confirm',
|
|
23
|
+
message: i18n(`${i18nKey}.prompt`),
|
|
24
|
+
});
|
|
25
|
+
|
|
26
|
+
if (!shouldOpenBrowser) {
|
|
27
|
+
logger.log(i18n(`${i18nKey}.decline`));
|
|
28
|
+
process.exit(EXIT_CODES.SUCCESS);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
const websiteOrigin = getHubSpotWebsiteOrigin(env);
|
|
32
|
+
|
|
33
|
+
const url =
|
|
34
|
+
`${websiteOrigin}/oauth/${targetAccountId}/authorize` +
|
|
35
|
+
`?client_id=${encodeURIComponent(clientId)}` +
|
|
36
|
+
`&scope=${encodeURIComponent(scopes.join(' '))}` +
|
|
37
|
+
`&redirect_uri=${encodeURIComponent(redirectUrls[0])}`;
|
|
38
|
+
|
|
39
|
+
open(url);
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
module.exports = { installPublicAppPrompt };
|
|
@@ -7,12 +7,12 @@ const { deleteEmptyConfigFile } = require('@hubspot/local-dev-lib/config');
|
|
|
7
7
|
const { getHubSpotWebsiteOrigin } = require('@hubspot/local-dev-lib/urls');
|
|
8
8
|
const { logger } = require('@hubspot/local-dev-lib/logger');
|
|
9
9
|
const { promptUser } = require('./promptUtils');
|
|
10
|
-
const {
|
|
10
|
+
const { getCliAccountNamePromptConfig } = require('./accountNamePrompt');
|
|
11
11
|
const { i18n } = require('../lang');
|
|
12
12
|
const { uiInfoSection } = require('../ui');
|
|
13
13
|
const { EXIT_CODES } = require('../enums/exitCodes');
|
|
14
14
|
|
|
15
|
-
const i18nKey = '
|
|
15
|
+
const i18nKey = 'lib.prompts.personalAccessKeyPrompt';
|
|
16
16
|
|
|
17
17
|
/**
|
|
18
18
|
* Displays notification to user that we are about to open the browser,
|
|
@@ -124,7 +124,7 @@ const SCOPES = {
|
|
|
124
124
|
};
|
|
125
125
|
|
|
126
126
|
const OAUTH_FLOW = [
|
|
127
|
-
|
|
127
|
+
getCliAccountNamePromptConfig(),
|
|
128
128
|
ACCOUNT_ID,
|
|
129
129
|
CLIENT_ID,
|
|
130
130
|
CLIENT_SECRET,
|
|
@@ -3,7 +3,7 @@ const { getCwd } = require('@hubspot/local-dev-lib/path');
|
|
|
3
3
|
const { promptUser } = require('./promptUtils');
|
|
4
4
|
const { i18n } = require('../lang');
|
|
5
5
|
|
|
6
|
-
const i18nKey = '
|
|
6
|
+
const i18nKey = 'lib.prompts.previewPrompt';
|
|
7
7
|
|
|
8
8
|
const previewPrompt = (promptOptions = {}) => {
|
|
9
9
|
return promptUser([
|
|
@@ -34,6 +34,24 @@ const previewPrompt = (promptOptions = {}) => {
|
|
|
34
34
|
]);
|
|
35
35
|
};
|
|
36
36
|
|
|
37
|
+
const previewProjectPrompt = async themeComponents => {
|
|
38
|
+
return promptUser([
|
|
39
|
+
{
|
|
40
|
+
name: 'themeComponentPath',
|
|
41
|
+
message: i18n(`${i18nKey}.themeProjectSelect`),
|
|
42
|
+
type: 'list',
|
|
43
|
+
choices: themeComponents.map(t => {
|
|
44
|
+
const themeName = path.basename(t.path);
|
|
45
|
+
return {
|
|
46
|
+
name: themeName,
|
|
47
|
+
value: t.path,
|
|
48
|
+
};
|
|
49
|
+
}),
|
|
50
|
+
},
|
|
51
|
+
]);
|
|
52
|
+
};
|
|
53
|
+
|
|
37
54
|
module.exports = {
|
|
38
55
|
previewPrompt,
|
|
56
|
+
previewProjectPrompt,
|
|
39
57
|
};
|
|
@@ -4,7 +4,7 @@ const { i18n } = require('../lang');
|
|
|
4
4
|
const { HUBSPOT_PROJECT_COMPONENTS_GITHUB_PATH } = require('../constants');
|
|
5
5
|
const { PROJECT_COMPONENT_TYPES } = require('../constants');
|
|
6
6
|
|
|
7
|
-
const i18nKey = '
|
|
7
|
+
const i18nKey = 'lib.prompts.projectAddPrompt';
|
|
8
8
|
|
|
9
9
|
const createTypeOptions = async projectComponentsVersion => {
|
|
10
10
|
const config = await fetchFileFromRepository(
|
|
@@ -13,7 +13,7 @@ const {
|
|
|
13
13
|
fetchDeveloperTestAccounts,
|
|
14
14
|
} = require('@hubspot/local-dev-lib/developerTestAccounts');
|
|
15
15
|
|
|
16
|
-
const i18nKey = '
|
|
16
|
+
const i18nKey = 'lib.prompts.projectDevTargetAccountPrompt';
|
|
17
17
|
|
|
18
18
|
const mapNestedAccount = accountConfig => ({
|
|
19
19
|
name: uiAccountDescription(accountConfig.portalId, false),
|
|
@@ -24,6 +24,12 @@ const mapNestedAccount = accountConfig => ({
|
|
|
24
24
|
},
|
|
25
25
|
});
|
|
26
26
|
|
|
27
|
+
const getNonConfigDeveloperTestAccountName = account => {
|
|
28
|
+
return `${account.accountName} [${
|
|
29
|
+
HUBSPOT_ACCOUNT_TYPE_STRINGS[HUBSPOT_ACCOUNT_TYPES.DEVELOPER_TEST]
|
|
30
|
+
}] (${account.id})`;
|
|
31
|
+
};
|
|
32
|
+
|
|
27
33
|
const selectSandboxTargetAccountPrompt = async (
|
|
28
34
|
accounts,
|
|
29
35
|
defaultAccountConfig
|
|
@@ -94,9 +100,11 @@ const selectDeveloperTestTargetAccountPrompt = async (
|
|
|
94
100
|
) => {
|
|
95
101
|
const defaultAccountId = getAccountId(defaultAccountConfig.name);
|
|
96
102
|
let choices = [];
|
|
97
|
-
let
|
|
103
|
+
let devTestAccountsResponse = undefined;
|
|
98
104
|
try {
|
|
99
|
-
|
|
105
|
+
devTestAccountsResponse = await fetchDeveloperTestAccounts(
|
|
106
|
+
defaultAccountId
|
|
107
|
+
);
|
|
100
108
|
} catch (err) {
|
|
101
109
|
logger.debug('Unable to fetch developer test account usage limits: ', err);
|
|
102
110
|
}
|
|
@@ -110,17 +118,37 @@ const selectDeveloperTestTargetAccountPrompt = async (
|
|
|
110
118
|
);
|
|
111
119
|
let disabledMessage = false;
|
|
112
120
|
if (
|
|
113
|
-
|
|
114
|
-
|
|
121
|
+
devTestAccountsResponse &&
|
|
122
|
+
devTestAccountsResponse.results.length >=
|
|
123
|
+
devTestAccountsResponse.maxTestPortals
|
|
115
124
|
) {
|
|
116
125
|
disabledMessage = i18n(`${i18nKey}.developerTestAccountLimit`, {
|
|
117
126
|
authCommand: uiCommandReference('hs auth'),
|
|
118
|
-
limit:
|
|
127
|
+
limit: devTestAccountsResponse.maxTestPortals,
|
|
128
|
+
});
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
let devTestAccountsNotInConfig = [];
|
|
132
|
+
if (devTestAccountsResponse && devTestAccountsResponse.results) {
|
|
133
|
+
const inConfigIds = devTestAccounts.map(d => d.portalId);
|
|
134
|
+
devTestAccountsResponse.results.forEach(acct => {
|
|
135
|
+
if (inConfigIds.indexOf(acct.id) < 0) {
|
|
136
|
+
devTestAccountsNotInConfig.push({
|
|
137
|
+
name: getNonConfigDeveloperTestAccountName(acct),
|
|
138
|
+
value: {
|
|
139
|
+
targetAccountId: acct.id,
|
|
140
|
+
createdNestedAccount: false,
|
|
141
|
+
parentAccountId: defaultAccountId,
|
|
142
|
+
notInConfigAccount: acct,
|
|
143
|
+
},
|
|
144
|
+
});
|
|
145
|
+
}
|
|
119
146
|
});
|
|
120
147
|
}
|
|
121
148
|
|
|
122
149
|
choices = [
|
|
123
150
|
...devTestAccounts.map(mapNestedAccount),
|
|
151
|
+
...devTestAccountsNotInConfig,
|
|
124
152
|
{
|
|
125
153
|
name: i18n(`${i18nKey}.createNewDeveloperTestAccountOption`),
|
|
126
154
|
value: {
|
|
@@ -172,8 +200,22 @@ const confirmDefaultAccountPrompt = async (accountName, accountType) => {
|
|
|
172
200
|
return useDefaultAccount;
|
|
173
201
|
};
|
|
174
202
|
|
|
203
|
+
const confirmUseExistingDeveloperTestAccountPrompt = async account => {
|
|
204
|
+
const { confirmUseExistingDeveloperTestAccount } = await promptUser([
|
|
205
|
+
{
|
|
206
|
+
name: 'confirmUseExistingDeveloperTestAccount',
|
|
207
|
+
type: 'confirm',
|
|
208
|
+
message: i18n(`${i18nKey}.confirmUseExistingDeveloperTestAccount`, {
|
|
209
|
+
accountName: getNonConfigDeveloperTestAccountName(account),
|
|
210
|
+
}),
|
|
211
|
+
},
|
|
212
|
+
]);
|
|
213
|
+
return confirmUseExistingDeveloperTestAccount;
|
|
214
|
+
};
|
|
215
|
+
|
|
175
216
|
module.exports = {
|
|
176
217
|
selectSandboxTargetAccountPrompt,
|
|
177
218
|
selectDeveloperTestTargetAccountPrompt,
|
|
178
219
|
confirmDefaultAccountPrompt,
|
|
220
|
+
confirmUseExistingDeveloperTestAccountPrompt,
|
|
179
221
|
};
|