@hubspot/cli 7.10.0 → 7.10.1-experimental.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 -4
- package/commands/__tests__/getStarted.test.js +10 -0
- package/commands/__tests__/project.test.js +3 -0
- package/commands/account/__tests__/rename.test.js +10 -3
- package/commands/account/auth.js +10 -14
- package/commands/account/clean.js +11 -19
- package/commands/account/createOverride.js +15 -11
- package/commands/account/info.js +8 -5
- package/commands/account/list.js +15 -19
- package/commands/account/remove.js +23 -22
- package/commands/account/removeOverride.js +6 -6
- package/commands/account/rename.js +2 -2
- package/commands/account/use.js +19 -8
- package/commands/app/__tests__/migrate.test.js +8 -4
- package/commands/app/migrate.js +2 -2
- package/commands/auth.js +18 -14
- package/commands/config/migrate.js +5 -5
- package/commands/customObject/createSchema.js +2 -3
- package/commands/customObject/updateSchema.js +2 -3
- package/commands/getStarted.js +2 -3
- package/commands/hubdb/__tests__/list.test.js +1 -0
- package/commands/hubdb/list.js +2 -2
- package/commands/init.js +36 -32
- package/commands/project/__tests__/deploy.test.js +10 -5
- package/commands/project/__tests__/devUnifiedFlow.test.js +6 -4
- package/commands/project/__tests__/lint.test.js +709 -0
- package/commands/project/__tests__/logs.test.js +4 -0
- package/commands/project/__tests__/validate.test.js +286 -28
- package/commands/project/cloneApp.js +2 -2
- package/commands/project/deploy.js +16 -8
- package/commands/project/dev/deprecatedFlow.js +4 -5
- package/commands/project/dev/index.js +19 -7
- package/commands/project/dev/unifiedFlow.js +4 -5
- package/commands/project/lint.d.ts +6 -0
- package/commands/project/lint.js +178 -0
- package/commands/project/logs.js +2 -3
- package/commands/project/migrate.js +4 -13
- package/commands/project/profile/add.js +6 -7
- package/commands/project/profile/delete.js +2 -2
- package/commands/project/upload.js +10 -4
- package/commands/project/validate.js +73 -13
- package/commands/project.js +2 -0
- package/commands/sandbox/__tests__/create.test.js +14 -5
- package/commands/sandbox/create.js +4 -5
- package/commands/sandbox/delete.js +23 -20
- package/commands/testAccount/create.js +2 -2
- package/commands/testAccount/delete.js +9 -8
- package/lang/en.d.ts +48 -11
- package/lang/en.js +58 -15
- package/lib/__tests__/buildAccount.test.js +22 -30
- package/lib/__tests__/commonOpts.test.js +9 -13
- package/lib/__tests__/developerTestAccounts.test.js +29 -17
- package/lib/__tests__/importData.test.js +20 -10
- package/lib/__tests__/oauth.test.js +19 -8
- package/lib/__tests__/projectProfiles.test.js +273 -32
- package/lib/__tests__/sandboxSync.test.js +33 -11
- package/lib/__tests__/sandboxes.test.js +30 -19
- package/lib/__tests__/usageTracking.test.js +10 -10
- package/lib/__tests__/validation.test.js +32 -32
- package/lib/accountTypes.d.ts +9 -9
- package/lib/accountTypes.js +2 -4
- package/lib/app/__tests__/migrate.test.js +15 -0
- package/lib/app/__tests__/migrate_legacy.test.js +9 -0
- package/lib/app/migrate_legacy.d.ts +2 -2
- package/lib/buildAccount.d.ts +4 -4
- package/lib/buildAccount.js +7 -14
- package/lib/commonOpts.js +3 -3
- package/lib/configMigrate.d.ts +2 -2
- package/lib/configMigrate.js +42 -18
- package/lib/configOptions.js +3 -2
- package/lib/developerTestAccounts.d.ts +3 -3
- package/lib/developerTestAccounts.js +4 -7
- package/lib/doctor/DiagnosticInfoBuilder.d.ts +1 -1
- package/lib/doctor/DiagnosticInfoBuilder.js +9 -6
- package/lib/doctor/Doctor.js +4 -3
- package/lib/doctor/__tests__/Diagnosis.test.js +4 -3
- package/lib/doctor/__tests__/DiagnosticInfoBuilder.test.js +17 -9
- package/lib/doctor/__tests__/Doctor.test.js +14 -0
- package/lib/importData.js +8 -7
- package/lib/links.js +5 -5
- package/lib/middleware/{__test__ → __tests__}/commandTargetingUtils.test.js +3 -3
- package/lib/middleware/{__test__ → __tests__}/configMiddleware.test.js +23 -22
- package/lib/middleware/{__test__ → __tests__}/gitMiddleware.test.js +9 -7
- package/lib/middleware/autoUpdateMiddleware.js +34 -23
- package/lib/middleware/commandTargetingUtils.js +3 -2
- package/lib/middleware/configMiddleware.d.ts +6 -1
- package/lib/middleware/configMiddleware.js +36 -15
- package/lib/middleware/fireAlarmMiddleware.js +4 -15
- package/lib/middleware/gitMiddleware.js +8 -4
- package/lib/oauth.d.ts +2 -2
- package/lib/oauth.js +8 -10
- package/lib/projectProfiles.d.ts +4 -3
- package/lib/projectProfiles.js +78 -32
- package/lib/projects/__tests__/AppDevModeInterface.test.js +17 -6
- package/lib/projects/__tests__/DevServerManager.test.js +1 -0
- package/lib/projects/__tests__/LocalDevProcess.test.js +1 -0
- package/lib/projects/__tests__/deploy.test.js +1 -0
- package/lib/projects/__tests__/uieLinting.test.js +640 -0
- package/lib/projects/create/__tests__/v2.test.js +11 -0
- package/lib/projects/localDev/AppDevModeInterface.js +2 -2
- package/lib/projects/localDev/DevServerManager_DEPRECATED.js +2 -2
- package/lib/projects/localDev/LocalDevLogger.js +4 -4
- package/lib/projects/localDev/LocalDevManager_DEPRECATED.js +3 -3
- package/lib/projects/localDev/helpers/account.d.ts +10 -10
- package/lib/projects/localDev/helpers/account.js +6 -11
- package/lib/projects/uieLinting.d.ts +33 -0
- package/lib/projects/uieLinting.js +222 -0
- package/lib/projects/urls.js +5 -6
- package/lib/prompts/__tests__/downloadProjectPrompt.test.js +7 -5
- package/lib/prompts/accountNamePrompt.js +3 -3
- package/lib/prompts/accountsPrompt.d.ts +1 -1
- package/lib/prompts/accountsPrompt.js +6 -7
- package/lib/prompts/confirmImportDataPrompt.js +2 -2
- package/lib/prompts/downloadProjectPrompt.d.ts +1 -0
- package/lib/prompts/downloadProjectPrompt.js +5 -2
- package/lib/prompts/importDataTestAccountSelectPrompt.js +4 -5
- package/lib/prompts/personalAccessKeyPrompt.js +2 -2
- package/lib/prompts/projectDevTargetAccountPrompt.d.ts +3 -3
- package/lib/prompts/projectDevTargetAccountPrompt.js +5 -7
- package/lib/prompts/sandboxesPrompt.js +7 -8
- package/lib/prompts/setAsDefaultAccountPrompt.js +7 -6
- package/lib/sandboxSync.d.ts +2 -2
- package/lib/sandboxSync.js +3 -9
- package/lib/sandboxes.d.ts +4 -4
- package/lib/sandboxes.js +6 -11
- package/lib/serverlessLogs.js +2 -2
- package/lib/theme/__tests__/migrate.test.js +15 -0
- package/lib/ui/index.js +6 -3
- package/lib/usageTracking.js +15 -8
- package/lib/validation.js +13 -11
- package/mcp-server/tools/cms/HsCreateFunctionTool.js +4 -2
- package/mcp-server/tools/cms/HsCreateModuleTool.js +4 -2
- package/mcp-server/tools/cms/HsCreateTemplateTool.js +4 -2
- package/mcp-server/tools/cms/HsFunctionLogsTool.js +4 -2
- package/mcp-server/tools/cms/HsListFunctionsTool.js +3 -1
- package/mcp-server/tools/cms/HsListTool.js +3 -1
- package/mcp-server/tools/cms/__tests__/HsCreateFunctionTool.test.js +1 -0
- package/mcp-server/tools/index.js +4 -0
- package/mcp-server/tools/project/AddFeatureToProjectTool.js +4 -2
- package/mcp-server/tools/project/CreateProjectTool.js +4 -2
- package/mcp-server/tools/project/CreateTestAccountTool.js +17 -7
- package/mcp-server/tools/project/DeployProjectTool.js +3 -1
- package/mcp-server/tools/project/DocFetchTool.js +6 -4
- package/mcp-server/tools/project/DocsSearchTool.d.ts +1 -1
- package/mcp-server/tools/project/DocsSearchTool.js +10 -8
- package/mcp-server/tools/project/GetApiUsagePatternsByAppIdTool.d.ts +1 -1
- package/mcp-server/tools/project/GetApiUsagePatternsByAppIdTool.js +9 -7
- package/mcp-server/tools/project/GetApplicationInfoTool.js +8 -6
- package/mcp-server/tools/project/GetBuildLogsTool.d.ts +26 -0
- package/mcp-server/tools/project/GetBuildLogsTool.js +125 -0
- package/mcp-server/tools/project/GetBuildStatusTool.d.ts +26 -0
- package/mcp-server/tools/project/GetBuildStatusTool.js +166 -0
- package/mcp-server/tools/project/GetConfigValuesTool.d.ts +1 -1
- package/mcp-server/tools/project/GetConfigValuesTool.js +9 -7
- package/mcp-server/tools/project/GuidedWalkthroughTool.d.ts +1 -1
- package/mcp-server/tools/project/GuidedWalkthroughTool.js +5 -3
- package/mcp-server/tools/project/UploadProjectTools.js +3 -1
- package/mcp-server/tools/project/ValidateProjectTool.js +4 -2
- package/mcp-server/tools/project/__tests__/CreateTestAccountTool.test.js +12 -2
- package/mcp-server/tools/project/__tests__/DocFetchTool.test.js +5 -1
- package/mcp-server/tools/project/__tests__/DocsSearchTool.test.js +23 -11
- package/mcp-server/tools/project/__tests__/GetApiUsagePatternsByAppIdTool.test.js +7 -5
- package/mcp-server/tools/project/__tests__/GetApplicationInfoTool.test.js +7 -5
- package/mcp-server/tools/project/__tests__/GetBuildLogsTool.test.d.ts +1 -0
- package/mcp-server/tools/project/__tests__/GetBuildLogsTool.test.js +305 -0
- package/mcp-server/tools/project/__tests__/GetBuildStatusTool.test.d.ts +1 -0
- package/mcp-server/tools/project/__tests__/GetBuildStatusTool.test.js +240 -0
- package/mcp-server/tools/project/__tests__/GetConfigValuesTool.test.js +8 -6
- package/mcp-server/utils/__tests__/content.test.js +21 -20
- package/mcp-server/utils/__tests__/feedbackTracking.test.js +34 -28
- package/mcp-server/utils/config.d.ts +1 -0
- package/mcp-server/utils/config.js +10 -0
- package/mcp-server/utils/content.d.ts +1 -1
- package/mcp-server/utils/content.js +2 -2
- package/mcp-server/utils/feedbackTracking.d.ts +1 -1
- package/mcp-server/utils/feedbackTracking.js +3 -3
- package/mcp-server/utils/toolUsageTracking.js +4 -3
- package/package.json +9 -9
- package/ui/components/BoxWithTitle.d.ts +2 -1
- package/ui/components/BoxWithTitle.js +2 -2
- package/ui/components/StatusMessageBoxes.d.ts +5 -4
- package/ui/components/StatusMessageBoxes.js +8 -8
- package/lib/middleware/__test__/notificationsMiddleware.test.js +0 -8
- package/lib/middleware/notificationsMiddleware.d.ts +0 -1
- package/lib/middleware/notificationsMiddleware.js +0 -28
- package/lib/ui/boxen.d.ts +0 -5
- package/lib/ui/boxen.js +0 -26
- package/mcp-server/utils/__tests__/cliConfig.test.js +0 -110
- package/mcp-server/utils/cliConfig.d.ts +0 -1
- package/mcp-server/utils/cliConfig.js +0 -12
- /package/{lib/middleware/__test__/commandTargetingUtils.test.d.ts → commands/project/__tests__/lint.test.d.ts} +0 -0
- /package/lib/middleware/{__test__/configMiddleware.test.d.ts → __tests__/commandTargetingUtils.test.d.ts} +0 -0
- /package/lib/middleware/{__test__/gitMiddleware.test.d.ts → __tests__/configMiddleware.test.d.ts} +0 -0
- /package/lib/middleware/{__test__/notificationsMiddleware.test.d.ts → __tests__/gitMiddleware.test.d.ts} +0 -0
- /package/lib/middleware/{__test__ → __tests__}/requestMiddleware.test.d.ts +0 -0
- /package/lib/middleware/{__test__ → __tests__}/requestMiddleware.test.js +0 -0
- /package/lib/middleware/{__test__ → __tests__}/yargsChecksMiddleware.test.d.ts +0 -0
- /package/lib/middleware/{__test__ → __tests__}/yargsChecksMiddleware.test.js +0 -0
- /package/{mcp-server/utils/__tests__/cliConfig.test.d.ts → lib/projects/__tests__/uieLinting.test.d.ts} +0 -0
|
@@ -1,8 +1,7 @@
|
|
|
1
1
|
import { uiLogger } from '../../lib/ui/logger.js';
|
|
2
2
|
import { isSpecifiedError } from '@hubspot/local-dev-lib/errors/index';
|
|
3
3
|
import { deleteSandbox } from '@hubspot/local-dev-lib/api/sandboxHubs';
|
|
4
|
-
import {
|
|
5
|
-
import { getAccountIdentifier } from '@hubspot/local-dev-lib/config/getAccountIdentifier';
|
|
4
|
+
import { getConfigAccountEnvironment, removeAccountFromConfig, setConfigAccountAsDefault, getAllConfigAccounts, getConfigAccountIfExists, getConfigDefaultAccountIfExists, } from '@hubspot/local-dev-lib/config';
|
|
6
5
|
import { getHubSpotWebsiteOrigin } from '@hubspot/local-dev-lib/urls';
|
|
7
6
|
import { getValidEnv } from '@hubspot/local-dev-lib/environment';
|
|
8
7
|
import { trackCommandUsage } from '../../lib/usageTracking.js';
|
|
@@ -36,17 +35,20 @@ async function handler(args) {
|
|
|
36
35
|
process.exit(EXIT_CODES.ERROR);
|
|
37
36
|
}
|
|
38
37
|
}
|
|
39
|
-
const
|
|
40
|
-
|
|
38
|
+
const accountIdentifier = userProvidedAccount || accountPrompt.account;
|
|
39
|
+
const sandboxAccount = getConfigAccountIfExists(accountIdentifier);
|
|
40
|
+
if (!sandboxAccount) {
|
|
41
41
|
uiLogger.error(commands.sandbox.subcommands.delete.failure.noSandboxAccountId);
|
|
42
42
|
process.exit(EXIT_CODES.ERROR);
|
|
43
43
|
}
|
|
44
|
-
const
|
|
45
|
-
const
|
|
44
|
+
const sandboxAccountId = sandboxAccount.accountId;
|
|
45
|
+
const defaultAccount = getConfigDefaultAccountIfExists();
|
|
46
|
+
const isDefaultAccount = sandboxAccountId === defaultAccount?.accountId;
|
|
47
|
+
const baseUrl = getHubSpotWebsiteOrigin(getValidEnv(getConfigAccountEnvironment(sandboxAccountId)));
|
|
46
48
|
let parentAccountId;
|
|
47
|
-
const accountsList =
|
|
49
|
+
const accountsList = getAllConfigAccounts() || [];
|
|
48
50
|
for (const portal of accountsList) {
|
|
49
|
-
if (
|
|
51
|
+
if (portal.accountId === sandboxAccountId) {
|
|
50
52
|
if (portal.parentAccountId) {
|
|
51
53
|
parentAccountId = portal.parentAccountId;
|
|
52
54
|
}
|
|
@@ -56,7 +58,8 @@ async function handler(args) {
|
|
|
56
58
|
uiLogger.error(commands.sandbox.subcommands.delete.failure.noParentAccount);
|
|
57
59
|
process.exit(EXIT_CODES.ERROR);
|
|
58
60
|
}
|
|
59
|
-
|
|
61
|
+
const parentAccount = getConfigAccountIfExists(parentAccountPrompt.account);
|
|
62
|
+
parentAccountId = parentAccount?.accountId;
|
|
60
63
|
}
|
|
61
64
|
else {
|
|
62
65
|
uiLogger.error(commands.sandbox.subcommands.delete.failure.noParentAccount);
|
|
@@ -67,9 +70,9 @@ async function handler(args) {
|
|
|
67
70
|
const url = `${baseUrl}/sandboxes/${parentAccountId}`;
|
|
68
71
|
const command = uiAuthCommandReference({
|
|
69
72
|
accountId: parentAccountId || undefined,
|
|
70
|
-
qa:
|
|
73
|
+
qa: getConfigAccountEnvironment(sandboxAccountId) === 'qa',
|
|
71
74
|
});
|
|
72
|
-
if (parentAccountId && !
|
|
75
|
+
if (parentAccountId && !getConfigAccountIfExists(parentAccountId)) {
|
|
73
76
|
uiLogger.log('');
|
|
74
77
|
uiLogger.error(commands.sandbox.subcommands.delete.failure.noParentPortalAvailable(command, url));
|
|
75
78
|
uiLogger.log('');
|
|
@@ -99,14 +102,14 @@ async function handler(args) {
|
|
|
99
102
|
? commands.sandbox.subcommands.delete.success.deleteDefault(userProvidedAccount || accountPrompt.account, sandboxAccountId)
|
|
100
103
|
: commands.sandbox.subcommands.delete.success.delete(userProvidedAccount || accountPrompt.account, sandboxAccountId));
|
|
101
104
|
uiLogger.log('');
|
|
102
|
-
|
|
103
|
-
if (
|
|
105
|
+
removeAccountFromConfig(sandboxAccountId);
|
|
106
|
+
if (isDefaultAccount && !force) {
|
|
104
107
|
const newDefaultAccount = await selectAccountFromConfig();
|
|
105
|
-
|
|
108
|
+
setConfigAccountAsDefault(newDefaultAccount);
|
|
106
109
|
}
|
|
107
110
|
else if (isDefaultAccount && force) {
|
|
108
111
|
// If force is specified, skip prompt and set the parent account id as the default account
|
|
109
|
-
|
|
112
|
+
setConfigAccountAsDefault(parentAccountId);
|
|
110
113
|
}
|
|
111
114
|
process.exit(EXIT_CODES.SUCCESS);
|
|
112
115
|
}
|
|
@@ -135,14 +138,14 @@ async function handler(args) {
|
|
|
135
138
|
uiLogger.log('');
|
|
136
139
|
uiLogger.warn(commands.sandbox.subcommands.delete.failure.objectNotFound(sandboxAccountId));
|
|
137
140
|
uiLogger.log('');
|
|
138
|
-
|
|
139
|
-
if (
|
|
141
|
+
removeAccountFromConfig(sandboxAccountId);
|
|
142
|
+
if (isDefaultAccount && !force) {
|
|
140
143
|
const newDefaultAccount = await selectAccountFromConfig();
|
|
141
|
-
|
|
144
|
+
setConfigAccountAsDefault(newDefaultAccount);
|
|
142
145
|
}
|
|
143
|
-
else {
|
|
146
|
+
else if (isDefaultAccount) {
|
|
144
147
|
// If force is specified, skip prompt and set the parent account id as the default account
|
|
145
|
-
|
|
148
|
+
setConfigAccountAsDefault(parentAccountId);
|
|
146
149
|
}
|
|
147
150
|
process.exit(EXIT_CODES.SUCCESS);
|
|
148
151
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import fs from 'fs-extra';
|
|
2
2
|
import path from 'path';
|
|
3
3
|
import { getValidEnv } from '@hubspot/local-dev-lib/environment';
|
|
4
|
-
import {
|
|
4
|
+
import { getConfigAccountEnvironment } from '@hubspot/local-dev-lib/config';
|
|
5
5
|
import { getCwd } from '@hubspot/local-dev-lib/path';
|
|
6
6
|
import { makeYargsBuilder } from '../../lib/yargsUtils.js';
|
|
7
7
|
import { promptUser, listPrompt } from '../../lib/prompts/promptUtils.js';
|
|
@@ -89,7 +89,7 @@ async function buildTestAccountConfig(args) {
|
|
|
89
89
|
async function handler(args) {
|
|
90
90
|
const { derivedAccountId, formatOutputAsJson } = args;
|
|
91
91
|
trackCommandUsage('test-account-create', {}, derivedAccountId);
|
|
92
|
-
const env = getValidEnv(
|
|
92
|
+
const env = getValidEnv(getConfigAccountEnvironment(derivedAccountId));
|
|
93
93
|
const testAccountConfig = await buildTestAccountConfig(args);
|
|
94
94
|
const resultJson = {};
|
|
95
95
|
SpinniesManager.init({
|
|
@@ -4,7 +4,7 @@ import { EXIT_CODES } from '../../lib/enums/exitCodes.js';
|
|
|
4
4
|
import { uiLogger } from '../../lib/ui/logger.js';
|
|
5
5
|
import { trackCommandUsage } from '../../lib/usageTracking.js';
|
|
6
6
|
import { commands } from '../../lang/en.js';
|
|
7
|
-
import {
|
|
7
|
+
import { removeAccountFromConfig, getConfigAccountById, getConfigAccountIfExists, setConfigAccountAsDefault, getConfigDefaultAccountIfExists, } from '@hubspot/local-dev-lib/config';
|
|
8
8
|
import { promptUser } from '../../lib/prompts/promptUtils.js';
|
|
9
9
|
import { debugError } from '../../lib/errorHandlers/index.js';
|
|
10
10
|
const command = 'delete [test-account]';
|
|
@@ -64,12 +64,12 @@ async function deleteTestAccountFromConfig(testAccountId, parentAccountName, acc
|
|
|
64
64
|
// If the account isn't in the local config then it wasn't auth'd on the local machine
|
|
65
65
|
if (account && account.name && account.accountType) {
|
|
66
66
|
// If the deleted test account was the default account, replace the default account with the parent account
|
|
67
|
-
|
|
68
|
-
const defaultAccountId =
|
|
69
|
-
|
|
67
|
+
const defaultAccount = getConfigDefaultAccountIfExists();
|
|
68
|
+
const defaultAccountId = defaultAccount?.accountId;
|
|
69
|
+
removeAccountFromConfig(account.accountId);
|
|
70
70
|
uiLogger.success(commands.testAccount.delete.success.testAccountDeletedFromConfig(testAccountId));
|
|
71
71
|
if (testAccountId === defaultAccountId) {
|
|
72
|
-
|
|
72
|
+
setConfigAccountAsDefault(parentAccountName);
|
|
73
73
|
uiLogger.info(commands.testAccount.delete.info.replaceDefaultAccount(testAccountId, parentAccountName));
|
|
74
74
|
}
|
|
75
75
|
}
|
|
@@ -84,12 +84,12 @@ async function validateTestAccountConfigs(testAccountId) {
|
|
|
84
84
|
uiLogger.error(commands.testAccount.delete.errors.testAccountNotFound(testAccountId));
|
|
85
85
|
process.exit(EXIT_CODES.ERROR);
|
|
86
86
|
}
|
|
87
|
-
const testAccountConfig =
|
|
87
|
+
const testAccountConfig = getConfigAccountById(testAccountId);
|
|
88
88
|
if (!testAccountConfig) {
|
|
89
89
|
uiLogger.error(commands.testAccount.delete.errors.testAccountNotFound(testAccountId));
|
|
90
90
|
process.exit(EXIT_CODES.ERROR);
|
|
91
91
|
}
|
|
92
|
-
const parentAccountConfig =
|
|
92
|
+
const parentAccountConfig = getConfigAccountById(testAccountConfig.parentAccountId);
|
|
93
93
|
if (!parentAccountConfig) {
|
|
94
94
|
uiLogger.error(commands.testAccount.delete.errors.parentAccountNotFound(testAccountId));
|
|
95
95
|
process.exit(EXIT_CODES.ERROR);
|
|
@@ -103,7 +103,8 @@ async function handler(args) {
|
|
|
103
103
|
let testAccountIdToDelete = 0;
|
|
104
104
|
// See if the account exists
|
|
105
105
|
if (testAccount) {
|
|
106
|
-
const
|
|
106
|
+
const account = getConfigAccountIfExists(testAccount);
|
|
107
|
+
const accountId = account?.accountId || null;
|
|
107
108
|
await validateTestAccountConfigs(accountId);
|
|
108
109
|
if (accountId) {
|
|
109
110
|
testAccountIdToDelete = accountId;
|
package/lang/en.d.ts
CHANGED
|
@@ -1,12 +1,13 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { HubSpotConfigAccount } from '@hubspot/local-dev-lib/types/Accounts';
|
|
2
2
|
export declare const commands: {
|
|
3
3
|
generalErrors: {
|
|
4
4
|
srcIsProject: (src: string, command: string) => string;
|
|
5
5
|
handleDeprecatedEnvVariables: {
|
|
6
6
|
portalEnvVarDeprecated: string;
|
|
7
7
|
};
|
|
8
|
-
|
|
9
|
-
|
|
8
|
+
validateConfigMiddleware: {
|
|
9
|
+
missingConfigFile: string;
|
|
10
|
+
configValidationFailed: (errors: string[]) => string;
|
|
10
11
|
};
|
|
11
12
|
};
|
|
12
13
|
getStarted: {
|
|
@@ -86,12 +87,11 @@ export declare const commands: {
|
|
|
86
87
|
list: {
|
|
87
88
|
accounts: string;
|
|
88
89
|
defaultAccountTitle: string;
|
|
89
|
-
|
|
90
|
+
currentResolvedDefaultAccount: (accountId: number) => string;
|
|
90
91
|
describe: string;
|
|
91
92
|
configPath: (configPath: string) => string;
|
|
92
93
|
overrideFilePathTitle: string;
|
|
93
94
|
overrideFilePath: (overrideFilePath: string) => string;
|
|
94
|
-
overrideAccount: (account: string) => string;
|
|
95
95
|
labels: {
|
|
96
96
|
accountId: string;
|
|
97
97
|
authType: string;
|
|
@@ -1752,6 +1752,32 @@ export declare const commands: {
|
|
|
1752
1752
|
noPackageJsonInProject: (projectName: string) => string;
|
|
1753
1753
|
packageManagerNotInstalled: (packageManager: string) => string;
|
|
1754
1754
|
};
|
|
1755
|
+
lint: {
|
|
1756
|
+
help: {
|
|
1757
|
+
describe: string;
|
|
1758
|
+
lintProjectExample: string;
|
|
1759
|
+
lintProjectWithInstallExample: string;
|
|
1760
|
+
lintProjectWithoutInstallExample: string;
|
|
1761
|
+
installMissingDeps: string;
|
|
1762
|
+
};
|
|
1763
|
+
loading: {
|
|
1764
|
+
checking: string;
|
|
1765
|
+
creatingConfig: string;
|
|
1766
|
+
linting: string;
|
|
1767
|
+
};
|
|
1768
|
+
noProjectConfig: string;
|
|
1769
|
+
failedToReadPackageJson: (packageJsonPath: string) => string;
|
|
1770
|
+
installLintPackagesPrompt: (directories: string[], missingPackages: string[]) => string;
|
|
1771
|
+
skippingDirectoriesWarning: (directories: string[]) => string;
|
|
1772
|
+
deprecatedEslintConfigWarning: (details: {
|
|
1773
|
+
path: string;
|
|
1774
|
+
files: string[];
|
|
1775
|
+
}[]) => string;
|
|
1776
|
+
createEslintConfigPrompt: (directories: string[]) => string;
|
|
1777
|
+
eslintConfigCreated: (configPath: string) => string;
|
|
1778
|
+
failedToCreateEslintConfig: (configPath: string) => string;
|
|
1779
|
+
eslintConfigRequired: string;
|
|
1780
|
+
};
|
|
1755
1781
|
updateDeps: {
|
|
1756
1782
|
help: {
|
|
1757
1783
|
describe: string;
|
|
@@ -1776,7 +1802,16 @@ export declare const commands: {
|
|
|
1776
1802
|
default: string;
|
|
1777
1803
|
};
|
|
1778
1804
|
success: (projectName: string) => string;
|
|
1779
|
-
failure: (projectName: string) => string;
|
|
1805
|
+
failure: (projectName: string, profileName?: string) => string;
|
|
1806
|
+
spinners: {
|
|
1807
|
+
validatingProfile: (profileName: string) => string;
|
|
1808
|
+
profileValidationFailed: (profileName: string) => string;
|
|
1809
|
+
profileValidationSucceeded: (profileName: string) => string;
|
|
1810
|
+
invalidWithProfile: (profileName: string, projectName: string) => string;
|
|
1811
|
+
validatingAllProfiles: string;
|
|
1812
|
+
allProfilesValidationSucceeded: string;
|
|
1813
|
+
allProfilesValidationFailed: string;
|
|
1814
|
+
};
|
|
1780
1815
|
options: {
|
|
1781
1816
|
profile: {
|
|
1782
1817
|
describe: string;
|
|
@@ -2930,7 +2965,7 @@ export declare const lib: {
|
|
|
2930
2965
|
updateNotification: {
|
|
2931
2966
|
notifyTitle: string;
|
|
2932
2967
|
cmsUpdateNotification: (packageName: string) => string;
|
|
2933
|
-
cliUpdateNotification: string;
|
|
2968
|
+
cliUpdateNotification: (currentVersion: string, updateCommand: string, latestVersion: string) => string;
|
|
2934
2969
|
};
|
|
2935
2970
|
autoUpdateCLI: {
|
|
2936
2971
|
updateAvailable: (latestVersion: string) => string;
|
|
@@ -2955,7 +2990,9 @@ export declare const lib: {
|
|
|
2955
2990
|
noProjectConfig: string;
|
|
2956
2991
|
profileNotFound: (profileName: string) => string;
|
|
2957
2992
|
missingAccountId: (profileName: string) => string;
|
|
2993
|
+
listedAccountNotFound: (accountId: number, profileName: string) => string;
|
|
2958
2994
|
failedToLoadProfile: (profileName: string) => string;
|
|
2995
|
+
profileNotValid: (profileName: string, errors: string[]) => string;
|
|
2959
2996
|
};
|
|
2960
2997
|
};
|
|
2961
2998
|
};
|
|
@@ -3046,9 +3083,6 @@ export declare const lib: {
|
|
|
3046
3083
|
legacyFileDetected: (filename: string, platformVersion: string) => string;
|
|
3047
3084
|
};
|
|
3048
3085
|
};
|
|
3049
|
-
boxen: {
|
|
3050
|
-
failedToLoad: string;
|
|
3051
|
-
};
|
|
3052
3086
|
importData: {
|
|
3053
3087
|
errors: {
|
|
3054
3088
|
incorrectAccountType: (derivedAccountId: number) => string;
|
|
@@ -3237,6 +3271,9 @@ export declare const lib: {
|
|
|
3237
3271
|
skippedExistingAccounts: (accountIds: (string | number)[]) => string;
|
|
3238
3272
|
success: string;
|
|
3239
3273
|
};
|
|
3274
|
+
errors: {
|
|
3275
|
+
archive: (deprecatedConfigPath: string) => string;
|
|
3276
|
+
};
|
|
3240
3277
|
};
|
|
3241
3278
|
prompts: {
|
|
3242
3279
|
promptUtils: {
|
|
@@ -3249,7 +3286,7 @@ export declare const lib: {
|
|
|
3249
3286
|
promptMessage: string;
|
|
3250
3287
|
};
|
|
3251
3288
|
confirmImportDataPrompt: {
|
|
3252
|
-
message: (dataFileNames: string[], cliAccount:
|
|
3289
|
+
message: (dataFileNames: string[], cliAccount: HubSpotConfigAccount | null) => string;
|
|
3253
3290
|
};
|
|
3254
3291
|
importDataTestAccountSelectPrompt: {
|
|
3255
3292
|
errors: {
|
package/lang/en.js
CHANGED
|
@@ -7,15 +7,15 @@ import { uiAccountDescription, uiBetaTag, uiCommandReference, uiLink, UI_COLORS,
|
|
|
7
7
|
import { getProjectDetailUrl, getProjectSettingsUrl, getLocalDevUiUrl, } from '../lib/projects/urls.js';
|
|
8
8
|
import { getProductUpdatesUrl } from '../lib/links.js';
|
|
9
9
|
import { APP_DISTRIBUTION_TYPES, APP_AUTH_TYPES, PROJECT_CONFIG_FILE, PROJECT_WITH_APP, LEGACY_PUBLIC_APP_FILE, } from '../lib/constants.js';
|
|
10
|
-
import { getAccountIdentifier } from '@hubspot/local-dev-lib/config/getAccountIdentifier';
|
|
11
10
|
export const commands = {
|
|
12
11
|
generalErrors: {
|
|
13
12
|
srcIsProject: (src, command) => `"${src}" is in a project folder. Did you mean "hs project ${command}"?`,
|
|
14
13
|
handleDeprecatedEnvVariables: {
|
|
15
14
|
portalEnvVarDeprecated: 'The HUBSPOT_PORTAL_ID environment variable is deprecated. Please use HUBSPOT_ACCOUNT_ID instead.',
|
|
16
15
|
},
|
|
17
|
-
|
|
18
|
-
|
|
16
|
+
validateConfigMiddleware: {
|
|
17
|
+
missingConfigFile: `A HubSpot config file is required to run this command, but none was found. To create a new config file and authenticate a HubSpot account, run ${uiCommandReference('hs account auth')}`,
|
|
18
|
+
configValidationFailed: (errors) => `Your HubSpot config file is invalid. Please fix the following errors:\n - ${errors.join('\n- ')}`,
|
|
19
19
|
},
|
|
20
20
|
},
|
|
21
21
|
getStarted: {
|
|
@@ -95,12 +95,11 @@ export const commands = {
|
|
|
95
95
|
list: {
|
|
96
96
|
accounts: `${chalk.bold('Accounts')}:`,
|
|
97
97
|
defaultAccountTitle: `${chalk.bold('Default Account')}`,
|
|
98
|
-
|
|
98
|
+
currentResolvedDefaultAccount: (accountId) => `Account: ${uiAccountDescription(accountId)}`,
|
|
99
99
|
describe: 'List names of accounts defined in config.',
|
|
100
100
|
configPath: (configPath) => `Source: ${configPath}`,
|
|
101
101
|
overrideFilePathTitle: `${chalk.bold('Default Account Override')}`,
|
|
102
102
|
overrideFilePath: (overrideFilePath) => `Source: ${overrideFilePath}`,
|
|
103
|
-
overrideAccount: (account) => `Account: ${account}`,
|
|
104
103
|
labels: {
|
|
105
104
|
accountId: 'Account ID',
|
|
106
105
|
authType: 'Auth Type',
|
|
@@ -1552,7 +1551,7 @@ export const commands = {
|
|
|
1552
1551
|
noBuilds: 'Deploy error: no builds for this project were found.',
|
|
1553
1552
|
noBuildId: 'You must specify a build to deploy',
|
|
1554
1553
|
projectNotFound: (accountId, projectName) => `The project ${chalk.bold(projectName)} does not exist in account ${uiAccountDescription(accountId)}. Run ${uiCommandReference('hs project upload')} to upload your project files to HubSpot.`,
|
|
1555
|
-
buildIdDoesNotExist: (accountId, buildId, projectName) => `Build ${buildId} does not exist for project ${chalk.bold(projectName)}. ${
|
|
1554
|
+
buildIdDoesNotExist: (accountId, buildId, projectName) => `Build ${buildId} does not exist for project ${chalk.bold(projectName)}. Run ${uiCommandReference('hs project list-builds')} to view existing builds for this project.`,
|
|
1556
1555
|
buildAlreadyDeployed: (accountId, buildId, projectName) => `Build ${buildId} is already deployed. ${uiLink('View project builds in HubSpot', getProjectDetailUrl(projectName, accountId))}`,
|
|
1557
1556
|
deployContainsRemovals: (componentName) => `- This deploy would remove the ${chalk.bold(componentName)} component. To proceed, run the deploy command with the ${uiCommandReference('--force')} flag`,
|
|
1558
1557
|
deployBlockedHeader: "This build couldn't be deployed because it will be too disruptive for existing users. Fix the following issues and try again:",
|
|
@@ -1768,6 +1767,39 @@ export const commands = {
|
|
|
1768
1767
|
noPackageJsonInProject: (projectName) => `No dependencies to install. The project ${projectName} folder might be missing component or subcomponent files. ${uiLink('Learn how to create a project from scratch', 'https://developers.hubspot.com/docs/apps/developer-platform/build-apps/create-an-app#customize-a-new-project-using-the-cli')}`,
|
|
1769
1768
|
packageManagerNotInstalled: (packageManager) => `This command depends on ${packageManager}, install ${uiLink(packageManager, 'https://docs.npmjs.com/downloading-and-installing-node-js-and-npm')}`,
|
|
1770
1769
|
},
|
|
1770
|
+
lint: {
|
|
1771
|
+
help: {
|
|
1772
|
+
describe: 'Lint the UI Extensions components in your project.',
|
|
1773
|
+
lintProjectExample: 'Lint the UI Extensions components in your project.',
|
|
1774
|
+
lintProjectWithInstallExample: 'Lint the UI Extensions components in the project and automatically install missing dependencies.',
|
|
1775
|
+
lintProjectWithoutInstallExample: 'Lint the UI Extensions components in the project without installing missing dependencies.',
|
|
1776
|
+
installMissingDeps: 'Automatically install missing linting dependencies for the UI Extensions components in the project without prompting.',
|
|
1777
|
+
},
|
|
1778
|
+
loading: {
|
|
1779
|
+
checking: 'Checking lint packages and configuration…',
|
|
1780
|
+
creatingConfig: 'Creating ESLint configuration files…',
|
|
1781
|
+
linting: 'Linting…',
|
|
1782
|
+
},
|
|
1783
|
+
noProjectConfig: 'No project detected. Run this command from a project directory.',
|
|
1784
|
+
failedToReadPackageJson: (packageJsonPath) => `Failed to read package.json at ${packageJsonPath}`,
|
|
1785
|
+
installLintPackagesPrompt: (directories, missingPackages) => {
|
|
1786
|
+
const uniquePackages = Array.from(new Set(missingPackages)).sort();
|
|
1787
|
+
return `The dependencies required for linting are missing or outdated.\n\nDependencies:\n${uniquePackages.map(p => ` - ${p}`).join('\n')}\n\n${directories.length === 1 ? 'Directory' : 'Directories'}:\n${directories.map(d => ` - ${d}`).join('\n')}\n\nWould you like to install the required dependencies?`;
|
|
1788
|
+
},
|
|
1789
|
+
skippingDirectoriesWarning: (directories) => `Skipping linting for the following ${directories.length === 1 ? 'directory' : 'directories'}:\n${directories.map(d => ` - ${d}`).join('\n')}`,
|
|
1790
|
+
deprecatedEslintConfigWarning: (details) => {
|
|
1791
|
+
const dirCount = details.length;
|
|
1792
|
+
const header = `Deprecated ESLint configuration file${dirCount === 1 ? '' : 's'} detected in the following ${dirCount === 1 ? 'directory' : 'directories'}:`;
|
|
1793
|
+
const dirList = details
|
|
1794
|
+
.map(d => ` - ${d.path}: ${d.files.join(', ')}`)
|
|
1795
|
+
.join('\n');
|
|
1796
|
+
return `${header}\n${dirList}\n`;
|
|
1797
|
+
},
|
|
1798
|
+
createEslintConfigPrompt: (directories) => `ESLint configuration file not found in the following ${directories.length === 1 ? 'directory' : 'directories'}:\n${directories.map(d => ` - ${d}`).join('\n')}\n\nWould you like to set up the required ESLint configuration?`,
|
|
1799
|
+
eslintConfigCreated: (configPath) => `ESLint configuration created at ${configPath}`,
|
|
1800
|
+
failedToCreateEslintConfig: (configPath) => `Failed to create ESLint configuration at ${configPath}`,
|
|
1801
|
+
eslintConfigRequired: 'ESLint configuration is required to run the lint command. Run the command again to create the configuration.',
|
|
1802
|
+
},
|
|
1771
1803
|
updateDeps: {
|
|
1772
1804
|
help: {
|
|
1773
1805
|
describe: 'Update the npm dependencies for your project, or update specific dependencies in a subcomponent of a project.',
|
|
@@ -1792,10 +1824,19 @@ export const commands = {
|
|
|
1792
1824
|
default: 'Validate the project before uploading',
|
|
1793
1825
|
},
|
|
1794
1826
|
success: (projectName) => `Project ${projectName} is valid and ready to upload`,
|
|
1795
|
-
failure: (projectName) => `Project ${projectName} is invalid`,
|
|
1827
|
+
failure: (projectName, profileName) => `Project ${projectName} is invalid${profileName ? `with profile ${profileName} applied` : ''}`,
|
|
1828
|
+
spinners: {
|
|
1829
|
+
validatingProfile: (profileName) => `Validating project with profile "${profileName}"`,
|
|
1830
|
+
profileValidationFailed: (profileName) => `Profile "${profileName}" failed validation`,
|
|
1831
|
+
profileValidationSucceeded: (profileName) => `Project valid with profile "${profileName}" applied`,
|
|
1832
|
+
invalidWithProfile: (profileName, projectName) => `Project is invalid with profile "${profileName}" applied \n ${commands.project.validate.failure(projectName)}`,
|
|
1833
|
+
validatingAllProfiles: 'Validating the project with all profiles',
|
|
1834
|
+
allProfilesValidationSucceeded: 'Project profile validation succeeded',
|
|
1835
|
+
allProfilesValidationFailed: 'Project profile validation failed',
|
|
1836
|
+
},
|
|
1796
1837
|
options: {
|
|
1797
1838
|
profile: {
|
|
1798
|
-
describe: 'The profile to target for this validation',
|
|
1839
|
+
describe: 'The profile to target for this validation. If no profile is provided, all profiles will be validated.',
|
|
1799
1840
|
},
|
|
1800
1841
|
},
|
|
1801
1842
|
},
|
|
@@ -2946,7 +2987,7 @@ export const lib = {
|
|
|
2946
2987
|
updateNotification: {
|
|
2947
2988
|
notifyTitle: chalk.bold('CLI update available'),
|
|
2948
2989
|
cmsUpdateNotification: (packageName) => `${chalk.bold('The CMS CLI is now the HubSpot CLI')}\n\nTo upgrade, uninstall ${chalk.bold(packageName)}\nand then run ${uiCommandReference('{updateCommand}')}`,
|
|
2949
|
-
cliUpdateNotification: `HubSpot CLI version ${chalk.cyan(chalk.bold(
|
|
2990
|
+
cliUpdateNotification: (currentVersion, updateCommand, latestVersion) => `HubSpot CLI version ${chalk.cyan(chalk.bold(`${currentVersion}`))} is outdated.\nRun ${uiCommandReference(`${updateCommand}`)} to upgrade to version ${chalk.cyan(chalk.bold(`${latestVersion}`))}`,
|
|
2950
2991
|
},
|
|
2951
2992
|
autoUpdateCLI: {
|
|
2952
2993
|
updateAvailable: (latestVersion) => `There's a new HubSpot CLI version available! Updating to version ${chalk.bold(latestVersion)}`,
|
|
@@ -2971,7 +3012,9 @@ export const lib = {
|
|
|
2971
3012
|
noProjectConfig: 'No project config found. Please run this command from a project directory.',
|
|
2972
3013
|
profileNotFound: (profileName) => `Profile ${chalk.bold(profileName)} not found.`,
|
|
2973
3014
|
missingAccountId: (profileName) => `Profile ${chalk.bold(profileName)} is missing an account id.`,
|
|
3015
|
+
listedAccountNotFound: (accountId, profileName) => `The account ${uiAccountDescription(accountId)} is defined in your profile ${chalk.bold(profileName)}, but is missing in your config file`,
|
|
2974
3016
|
failedToLoadProfile: (profileName) => `Failed to load profile ${chalk.bold(profileName)}.`,
|
|
3017
|
+
profileNotValid: (profileName, errors) => `Profile "${profileName}" is not valid:\n\t- ${errors.join('\n\t- ')}`,
|
|
2975
3018
|
},
|
|
2976
3019
|
},
|
|
2977
3020
|
},
|
|
@@ -3062,9 +3105,6 @@ export const lib = {
|
|
|
3062
3105
|
legacyFileDetected: (filename, platformVersion) => `The ${chalk.bold(filename)} file is not supported on platform version ${chalk.bold(platformVersion)} and will be ignored.`,
|
|
3063
3106
|
},
|
|
3064
3107
|
},
|
|
3065
|
-
boxen: {
|
|
3066
|
-
failedToLoad: 'Failed to load boxen util.',
|
|
3067
|
-
},
|
|
3068
3108
|
importData: {
|
|
3069
3109
|
errors: {
|
|
3070
3110
|
incorrectAccountType: (derivedAccountId) => `The account ${uiAccountDescription(derivedAccountId)} is not a standard account, developer test account, or app developer account.`,
|
|
@@ -3253,6 +3293,9 @@ export const lib = {
|
|
|
3253
3293
|
skippedExistingAccounts: (accountIds) => `The following accounts were not merged because they already exist in the global config:${accountIds.map(id => `\n- ${uiAccountDescription(Number(id))}`).join('')}`,
|
|
3254
3294
|
success: 'Your deprecated config file has been successfully merged with the global config file.',
|
|
3255
3295
|
},
|
|
3296
|
+
errors: {
|
|
3297
|
+
archive: (deprecatedConfigPath) => `The config migration was successful, but an error occurred when archiving config file at ${deprecatedConfigPath}. You may need to manually delete or rename this config file.`,
|
|
3298
|
+
},
|
|
3256
3299
|
},
|
|
3257
3300
|
prompts: {
|
|
3258
3301
|
promptUtils: {
|
|
@@ -3265,7 +3308,7 @@ export const lib = {
|
|
|
3265
3308
|
promptMessage: '[--file-path] Select the JSON file that will be used to import your data.',
|
|
3266
3309
|
},
|
|
3267
3310
|
confirmImportDataPrompt: {
|
|
3268
|
-
message: (dataFileNames, cliAccount) => `You are importing [${dataFileNames.join(', ')}] into ${uiAccountDescription(
|
|
3311
|
+
message: (dataFileNames, cliAccount) => `You are importing [${dataFileNames.join(', ')}] into ${uiAccountDescription(cliAccount?.accountId)}. Continue?`,
|
|
3269
3312
|
},
|
|
3270
3313
|
importDataTestAccountSelectPrompt: {
|
|
3271
3314
|
errors: {
|
|
@@ -3617,7 +3660,7 @@ export const lib = {
|
|
|
3617
3660
|
},
|
|
3618
3661
|
failure: {
|
|
3619
3662
|
syncTypeFetch: 'Unable to fetch available sandbox sync types. Please try again.',
|
|
3620
|
-
invalidUser: (accountName, parentAccountName) => `Couldn't sync ${chalk.bold(accountName)} because your account has been removed from ${chalk.bold(parentAccountName)} or your permission set doesn't allow you to sync the sandbox. To update your permissions, contact a super admin in ${chalk.bold(parentAccountName)}.`,
|
|
3663
|
+
invalidUser: (accountName, parentAccountName) => `Couldn't sync sandbox ${chalk.bold(accountName)} because your account has been removed from parent account${chalk.bold(parentAccountName)} or your permission set doesn't allow you to sync the sandbox. To update your permissions, contact a super admin in ${chalk.bold(parentAccountName)}.`,
|
|
3621
3664
|
syncInProgress: (url) => `Couldn't run the sync because there's another sync in progress. Wait for the current sync to finish and then try again. To check the sync status, visit the sync activity log: ${url}.`,
|
|
3622
3665
|
notSuperAdmin: (accountId) => `Couldn't run the sync because you are not a super admin in ${uiAccountDescription(accountId)}. Ask the account owner for super admin access to the sandbox.`,
|
|
3623
3666
|
objectNotFound: (accountId) => `Couldn't sync the sandbox because ${uiAccountDescription(accountId)} may have been deleted through the UI. Run ${uiCommandReference('hs sandbox delete')} to remove this account from the config.`,
|
|
@@ -3745,7 +3788,7 @@ export const lib = {
|
|
|
3745
3788
|
},
|
|
3746
3789
|
validation: {
|
|
3747
3790
|
accountNotFoundInConfig: (userProvidedAccount) => `The account "${userProvidedAccount}" could not be found in the config`,
|
|
3748
|
-
accountRequired: 'An account needs to be supplied either via "--account" or through setting a "
|
|
3791
|
+
accountRequired: 'An account needs to be supplied either via "--account" or through setting a "defaultAccount"',
|
|
3749
3792
|
userProvidedAccount: 'Cannot specify an account when environment variables are supplied. Please unset the environment variables or do not use the "--account" flag.',
|
|
3750
3793
|
accountNotConfigured: (accountId) => `The account ${uiAccountDescription(accountId)} has not been configured`,
|
|
3751
3794
|
invalidAuthType: (authType, accountId, configPath, validValues) => `Invalid "authType" value "${authType}" for account "${uiAccountDescription(accountId)}" in config file: ${configPath}. Valid values are ${validValues}.`,
|
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
import { getAccessToken, updateConfigWithAccessToken, } from '@hubspot/local-dev-lib/personalAccessKey';
|
|
2
|
-
import {
|
|
2
|
+
import { getConfigAccountIfExists, updateConfigAccount, } from '@hubspot/local-dev-lib/config';
|
|
3
3
|
import { createDeveloperTestAccount, fetchDeveloperTestAccountGateSyncStatus, generateDeveloperTestAccountPersonalAccessKey, } from '@hubspot/local-dev-lib/api/developerTestAccounts';
|
|
4
4
|
import { createSandbox, createV2Sandbox, getSandboxPersonalAccessKey, } from '@hubspot/local-dev-lib/api/sandboxHubs';
|
|
5
5
|
import { HUBSPOT_ACCOUNT_TYPES } from '@hubspot/local-dev-lib/constants/config';
|
|
6
6
|
import { personalAccessKeyPrompt } from '../prompts/personalAccessKeyPrompt.js';
|
|
7
7
|
import { cliAccountNamePrompt } from '../prompts/accountNamePrompt.js';
|
|
8
8
|
import * as buildAccount from '../buildAccount.js';
|
|
9
|
+
import { poll } from '../polling.js';
|
|
9
10
|
vi.mock('@hubspot/local-dev-lib/personalAccessKey');
|
|
10
11
|
vi.mock('@hubspot/local-dev-lib/config');
|
|
11
12
|
vi.mock('@hubspot/local-dev-lib/api/developerTestAccounts');
|
|
@@ -14,6 +15,7 @@ vi.mock('../ui/logger.js');
|
|
|
14
15
|
vi.mock('../errorHandlers/index.js');
|
|
15
16
|
vi.mock('../prompts/personalAccessKeyPrompt');
|
|
16
17
|
vi.mock('../prompts/accountNamePrompt');
|
|
18
|
+
vi.mock('../polling.js');
|
|
17
19
|
vi.mock('../ui/SpinniesManager', () => ({
|
|
18
20
|
default: {
|
|
19
21
|
init: vi.fn(),
|
|
@@ -25,17 +27,16 @@ vi.mock('../ui/SpinniesManager', () => ({
|
|
|
25
27
|
const mockedPersonalAccessKeyPrompt = personalAccessKeyPrompt;
|
|
26
28
|
const mockedGetAccessToken = getAccessToken;
|
|
27
29
|
const mockedUpdateConfigWithAccessToken = updateConfigWithAccessToken;
|
|
28
|
-
const
|
|
29
|
-
const
|
|
30
|
-
const mockedWriteConfig = writeConfig;
|
|
30
|
+
const mockedGetConfigAccountIfExists = getConfigAccountIfExists;
|
|
31
|
+
const mockedUpdateConfigAccount = updateConfigAccount;
|
|
31
32
|
const mockedCliAccountNamePrompt = cliAccountNamePrompt;
|
|
32
|
-
const mockedGetAccountId = getAccountId;
|
|
33
33
|
const mockedCreateDeveloperTestAccount = createDeveloperTestAccount;
|
|
34
34
|
const mockedFetchDeveloperTestAccountGateSyncStatus = fetchDeveloperTestAccountGateSyncStatus;
|
|
35
35
|
const mockedGenerateDeveloperTestAccountPersonalAccessKey = generateDeveloperTestAccountPersonalAccessKey;
|
|
36
36
|
const mockedCreateSandbox = createSandbox;
|
|
37
37
|
const mockedCreateV2Sandbox = createV2Sandbox;
|
|
38
38
|
const mockedGetPersonalAccessKey = getSandboxPersonalAccessKey;
|
|
39
|
+
const mockedPoll = poll;
|
|
39
40
|
describe('lib/buildAccount', () => {
|
|
40
41
|
describe('saveAccountToConfig()', () => {
|
|
41
42
|
const mockAccountConfig = {
|
|
@@ -61,9 +62,8 @@ describe('lib/buildAccount', () => {
|
|
|
61
62
|
});
|
|
62
63
|
mockedGetAccessToken.mockResolvedValue(accessToken);
|
|
63
64
|
mockedUpdateConfigWithAccessToken.mockResolvedValue(mockAccountConfig);
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
mockedWriteConfig.mockReturnValue(undefined);
|
|
65
|
+
mockedGetConfigAccountIfExists.mockResolvedValue(undefined);
|
|
66
|
+
mockedUpdateConfigAccount.mockReturnValue(undefined);
|
|
67
67
|
});
|
|
68
68
|
afterEach(() => {
|
|
69
69
|
vi.clearAllMocks();
|
|
@@ -72,8 +72,7 @@ describe('lib/buildAccount', () => {
|
|
|
72
72
|
const result = await buildAccount.saveAccountToConfig(mockAccountConfig.accountId, mockAccountConfig.name, mockAccountConfig.env, 'test-key');
|
|
73
73
|
expect(mockedPersonalAccessKeyPrompt).not.toHaveBeenCalled();
|
|
74
74
|
expect(mockedUpdateConfigWithAccessToken).toHaveBeenCalledWith(accessToken, 'test-key', mockAccountConfig.env);
|
|
75
|
-
expect(
|
|
76
|
-
expect(mockedWriteConfig).toHaveBeenCalled();
|
|
75
|
+
expect(mockedUpdateConfigAccount).toHaveBeenCalledWith(expect.objectContaining(mockAccountConfig));
|
|
77
76
|
expect(result).toBe(mockAccountConfig.name);
|
|
78
77
|
});
|
|
79
78
|
it('should prompt for personal access key if not provided', async () => {
|
|
@@ -83,8 +82,7 @@ describe('lib/buildAccount', () => {
|
|
|
83
82
|
account: mockAccountConfig.accountId,
|
|
84
83
|
});
|
|
85
84
|
expect(mockedUpdateConfigWithAccessToken).toHaveBeenCalledWith(accessToken, 'test-key', mockAccountConfig.env);
|
|
86
|
-
expect(
|
|
87
|
-
expect(mockedWriteConfig).toHaveBeenCalled();
|
|
85
|
+
expect(mockedUpdateConfigAccount).toHaveBeenCalledWith(expect.objectContaining(mockAccountConfig));
|
|
88
86
|
expect(result).toBe(mockAccountConfig.name);
|
|
89
87
|
});
|
|
90
88
|
it('should handle duplicate account names', async () => {
|
|
@@ -93,7 +91,7 @@ describe('lib/buildAccount', () => {
|
|
|
93
91
|
name: undefined,
|
|
94
92
|
};
|
|
95
93
|
mockedUpdateConfigWithAccessToken.mockResolvedValue(mockAccountConfigWithNoName);
|
|
96
|
-
|
|
94
|
+
mockedGetConfigAccountIfExists.mockResolvedValue({ accountId: 123 });
|
|
97
95
|
mockedCliAccountNamePrompt.mockResolvedValue({
|
|
98
96
|
name: 'test-account-with-new-name',
|
|
99
97
|
});
|
|
@@ -109,6 +107,7 @@ describe('lib/buildAccount', () => {
|
|
|
109
107
|
description: 'Test Account created by the HubSpot CLI',
|
|
110
108
|
};
|
|
111
109
|
beforeEach(() => {
|
|
110
|
+
vi.useFakeTimers();
|
|
112
111
|
mockedCreateDeveloperTestAccount.mockResolvedValue({
|
|
113
112
|
data: { id: 123456 },
|
|
114
113
|
});
|
|
@@ -118,15 +117,23 @@ describe('lib/buildAccount', () => {
|
|
|
118
117
|
mockedGenerateDeveloperTestAccountPersonalAccessKey.mockResolvedValue({
|
|
119
118
|
data: { personalAccessKey: 'test-key' },
|
|
120
119
|
});
|
|
120
|
+
// Mock poll to resolve immediately with the success status
|
|
121
|
+
mockedPoll.mockResolvedValue({ status: 'SUCCESS' });
|
|
122
|
+
});
|
|
123
|
+
afterEach(() => {
|
|
124
|
+
vi.useRealTimers();
|
|
121
125
|
});
|
|
122
126
|
it('should create a developer test account successfully', async () => {
|
|
123
|
-
const
|
|
127
|
+
const resultPromise = buildAccount.createDeveloperTestAccountV2(parentAccountId, mockDeveoperTestAccountConfig);
|
|
128
|
+
// Fast-forward the 5 second setTimeout
|
|
129
|
+
await vi.advanceTimersByTimeAsync(5000);
|
|
130
|
+
const result = await resultPromise;
|
|
124
131
|
expect(result).toEqual({
|
|
125
132
|
accountName: mockDeveoperTestAccountConfig.accountName,
|
|
126
133
|
accountId: 123456,
|
|
127
134
|
personalAccessKey: 'test-key',
|
|
128
135
|
});
|
|
129
|
-
}
|
|
136
|
+
});
|
|
130
137
|
});
|
|
131
138
|
describe('buildDeveloperTestAccount()', () => {
|
|
132
139
|
const mockParentAccountConfig = {
|
|
@@ -146,7 +153,6 @@ describe('lib/buildAccount', () => {
|
|
|
146
153
|
};
|
|
147
154
|
beforeEach(() => {
|
|
148
155
|
vi.spyOn(buildAccount, 'saveAccountToConfig').mockResolvedValue(mockParentAccountConfig.name);
|
|
149
|
-
mockedGetAccountId.mockReturnValue(mockParentAccountConfig.accountId);
|
|
150
156
|
mockedCreateDeveloperTestAccount.mockResolvedValue({
|
|
151
157
|
data: mockDeveloperTestAccount,
|
|
152
158
|
});
|
|
@@ -158,10 +164,6 @@ describe('lib/buildAccount', () => {
|
|
|
158
164
|
const result = await buildAccount.buildDeveloperTestAccount(mockDeveloperTestAccount.accountName, mockParentAccountConfig, mockParentAccountConfig.env, 10);
|
|
159
165
|
expect(result).toEqual(mockDeveloperTestAccount.id);
|
|
160
166
|
});
|
|
161
|
-
it('should throw error if account ID is not found', async () => {
|
|
162
|
-
mockedGetAccountId.mockReturnValue(null);
|
|
163
|
-
await expect(buildAccount.buildDeveloperTestAccount(mockDeveloperTestAccount.accountName, mockParentAccountConfig, mockParentAccountConfig.env, 10)).rejects.toThrow();
|
|
164
|
-
});
|
|
165
167
|
it('should handle API errors when creating developer test account', async () => {
|
|
166
168
|
mockedCreateDeveloperTestAccount.mockRejectedValue(new Error('test-error'));
|
|
167
169
|
await expect(buildAccount.buildDeveloperTestAccount(mockDeveloperTestAccount.accountName, mockParentAccountConfig, mockParentAccountConfig.env, 10)).rejects.toThrow();
|
|
@@ -192,7 +194,6 @@ describe('lib/buildAccount', () => {
|
|
|
192
194
|
};
|
|
193
195
|
beforeEach(() => {
|
|
194
196
|
vi.spyOn(buildAccount, 'saveAccountToConfig').mockResolvedValue(mockParentAccountConfig.name);
|
|
195
|
-
mockedGetAccountId.mockReturnValue(mockParentAccountConfig.accountId);
|
|
196
197
|
mockedCreateSandbox.mockResolvedValue({
|
|
197
198
|
data: { sandbox: mockSandbox, personalAccessKey: 'test-key' },
|
|
198
199
|
});
|
|
@@ -216,10 +217,6 @@ describe('lib/buildAccount', () => {
|
|
|
216
217
|
sandbox: mockSandbox,
|
|
217
218
|
});
|
|
218
219
|
});
|
|
219
|
-
it('should throw error if account ID is not found', async () => {
|
|
220
|
-
mockedGetAccountId.mockReturnValue(null);
|
|
221
|
-
await expect(buildAccount.buildSandbox(mockSandbox.name, mockParentAccountConfig, HUBSPOT_ACCOUNT_TYPES.STANDARD_SANDBOX, mockParentAccountConfig.env)).rejects.toThrow();
|
|
222
|
-
});
|
|
223
220
|
it('should handle API errors when creating sandbox', async () => {
|
|
224
221
|
mockedCreateSandbox.mockRejectedValue(new Error('test-error'));
|
|
225
222
|
await expect(buildAccount.buildSandbox(mockSandbox.name, mockParentAccountConfig, HUBSPOT_ACCOUNT_TYPES.STANDARD_SANDBOX, mockParentAccountConfig.env, false)).rejects.toThrow();
|
|
@@ -250,7 +247,6 @@ describe('lib/buildAccount', () => {
|
|
|
250
247
|
};
|
|
251
248
|
beforeEach(() => {
|
|
252
249
|
vi.spyOn(buildAccount, 'saveAccountToConfig').mockResolvedValue(mockParentAccountConfig.name);
|
|
253
|
-
mockedGetAccountId.mockReturnValue(mockParentAccountConfig.accountId);
|
|
254
250
|
mockedCreateV2Sandbox.mockResolvedValue({
|
|
255
251
|
data: mockSandbox,
|
|
256
252
|
});
|
|
@@ -271,10 +267,6 @@ describe('lib/buildAccount', () => {
|
|
|
271
267
|
expect(result).toEqual({ sandbox: mockSandbox });
|
|
272
268
|
expect(mockedGetPersonalAccessKey).toHaveBeenCalledWith(mockParentAccountConfig.accountId, mockSandbox.sandboxHubId);
|
|
273
269
|
});
|
|
274
|
-
it('should throw error if account ID is not found', async () => {
|
|
275
|
-
mockedGetAccountId.mockReturnValue(null);
|
|
276
|
-
await expect(buildAccount.buildV2Sandbox(mockSandbox.name, mockParentAccountConfig, HUBSPOT_ACCOUNT_TYPES.STANDARD_SANDBOX, false, mockParentAccountConfig.env, false)).rejects.toThrow();
|
|
277
|
-
});
|
|
278
270
|
it('should handle API errors when creating sandbox', async () => {
|
|
279
271
|
mockedCreateV2Sandbox.mockRejectedValue(new Error('test-error'));
|
|
280
272
|
await expect(buildAccount.buildV2Sandbox(mockSandbox.name, mockParentAccountConfig, HUBSPOT_ACCOUNT_TYPES.STANDARD_SANDBOX, false, mockParentAccountConfig.env, false)).rejects.toThrow();
|