@hubspot/cli 7.8.0-beta.0 → 7.8.0-beta.2
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/commands/__tests__/project.test.js +2 -0
- package/commands/account/auth.js +1 -0
- package/commands/auth.js +1 -0
- package/commands/feedback.js +1 -1
- package/commands/project/__tests__/add.test.js +12 -12
- package/commands/project/__tests__/list.test.js +31 -0
- package/commands/project/__tests__/migrate.test.js +1 -0
- package/commands/project/add.d.ts +2 -2
- package/commands/project/add.js +3 -2
- package/commands/project/create.js +1 -1
- package/commands/project/dev/deprecatedFlow.js +2 -2
- package/commands/project/dev/index.js +5 -5
- package/commands/project/dev/unifiedFlow.js +6 -3
- package/commands/project/download.js +5 -2
- package/commands/project/installDeps.d.ts +2 -2
- package/commands/project/installDeps.js +1 -0
- package/commands/project/list.d.ts +4 -0
- package/commands/project/list.js +62 -0
- package/commands/project/migrate.js +5 -2
- package/commands/project.js +2 -0
- package/commands/sandbox/delete.js +5 -2
- package/commands/testAccount/create.js +2 -2
- package/commands/theme/preview.js +1 -4
- package/lang/en.d.ts +49 -14
- package/lang/en.js +121 -86
- package/lang/en.lyaml +2 -2
- package/lib/__tests__/buildAccount.test.js +2 -2
- package/lib/app/migrate.js +1 -1
- package/lib/buildAccount.d.ts +2 -2
- package/lib/buildAccount.js +7 -7
- package/lib/configMigrate.js +88 -9
- package/lib/constants.d.ts +8 -1
- package/lib/constants.js +8 -1
- package/lib/doctor/Doctor.js +2 -2
- package/lib/errorHandlers/suppressError.js +2 -2
- package/lib/middleware/commandTargetingUtils.d.ts +1 -1
- package/lib/middleware/commandTargetingUtils.js +16 -20
- package/lib/projects/__tests__/AppDevModeInterface.test.js +85 -90
- package/lib/projects/__tests__/LocalDevProcess.test.js +6 -5
- package/lib/projects/__tests__/LocalDevWebsocketServer.test.js +6 -6
- package/lib/projects/__tests__/deploy.test.js +9 -9
- package/lib/projects/__tests__/upload.test.js +2 -2
- package/lib/projects/add/__tests__/{v3AddComponent.test.js → v2AddComponent.test.js} +35 -35
- package/lib/projects/add/{v3AddComponent.d.ts → v2AddComponent.d.ts} +1 -1
- package/lib/projects/add/{v3AddComponent.js → v2AddComponent.js} +5 -5
- package/lib/projects/create/__tests__/v2.test.d.ts +1 -0
- package/lib/projects/create/__tests__/{v3.test.js → v2.test.js} +2 -2
- package/lib/projects/create/index.js +2 -2
- package/lib/projects/create/{v3.d.ts → v2.d.ts} +3 -3
- package/lib/projects/create/{v3.js → v2.js} +3 -3
- package/lib/projects/deploy.d.ts +1 -1
- package/lib/projects/deploy.js +2 -2
- package/lib/projects/localDev/AppDevModeInterface.d.ts +8 -1
- package/lib/projects/localDev/AppDevModeInterface.js +106 -86
- package/lib/projects/localDev/DevServerManager.d.ts +11 -29
- package/lib/projects/localDev/DevServerManager.js +19 -61
- package/lib/projects/localDev/DevServerManager_DEPRECATED.d.ts +40 -0
- package/lib/projects/localDev/DevServerManager_DEPRECATED.js +120 -0
- package/lib/projects/localDev/{LocalDevManager.js → LocalDevManager_DEPRECATED.js} +6 -6
- package/lib/projects/localDev/LocalDevProcess.js +3 -2
- package/lib/projects/localDev/LocalDevState.d.ts +3 -0
- package/lib/projects/localDev/LocalDevState.js +9 -0
- package/lib/projects/localDev/LocalDevWebsocketServer.d.ts +4 -0
- package/lib/projects/localDev/LocalDevWebsocketServer.js +34 -2
- package/lib/projects/localDev/helpers/account.d.ts +1 -1
- package/lib/projects/localDev/helpers/account.js +2 -2
- package/lib/projects/localDev/helpers/project.js +2 -3
- package/lib/projects/localDev/localDevWebsocketServerUtils.d.ts +3 -0
- package/lib/projects/localDev/localDevWebsocketServerUtils.js +9 -0
- package/lib/projects/urls.d.ts +0 -1
- package/lib/projects/urls.js +0 -3
- package/lib/prompts/__tests__/downloadProjectPrompt.test.js +1 -0
- package/lib/prompts/__tests__/projectAddPrompt.test.js +10 -10
- package/lib/prompts/installAppPrompt.d.ts +1 -6
- package/lib/prompts/installAppPrompt.js +1 -6
- package/lib/prompts/projectAddPrompt.d.ts +2 -2
- package/lib/prompts/projectAddPrompt.js +1 -1
- package/lib/prompts/projectDevTargetAccountPrompt.js +1 -1
- package/lib/theme/__tests__/migrate.test.js +4 -4
- package/lib/ui/index.d.ts +4 -0
- package/lib/ui/index.js +9 -1
- package/lib/ui/uiMessages.d.ts +4 -0
- package/lib/ui/uiMessages.js +4 -0
- package/mcp-server/tools/project/__tests__/CreateProjectTool.test.js +1 -1
- package/package.json +7 -6
- package/lib/projects/localDev/DevServerManagerV2.d.ts +0 -22
- package/lib/projects/localDev/DevServerManagerV2.js +0 -81
- /package/{lib/projects/add/__tests__/v3AddComponent.test.d.ts → commands/project/__tests__/list.test.d.ts} +0 -0
- /package/lib/projects/{create/__tests__/v3.test.d.ts → add/__tests__/v2AddComponent.test.d.ts} +0 -0
- /package/lib/projects/localDev/{LocalDevManager.d.ts → LocalDevManager_DEPRECATED.d.ts} +0 -0
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { commands, lib } from '../../../lang/en.js';
|
|
2
2
|
import { getConfigForPlatformVersion } from '../create/legacy.js';
|
|
3
|
-
import { calculateComponentTemplateChoices,
|
|
3
|
+
import { calculateComponentTemplateChoices, createV2App, } from '../create/v2.js';
|
|
4
4
|
import { PROJECT_WITH_APP } from '../../constants.js';
|
|
5
5
|
import path from 'path';
|
|
6
6
|
import fs from 'fs';
|
|
7
|
-
import {
|
|
7
|
+
import { projectAddPromptV2 } from '../../prompts/projectAddPrompt.js';
|
|
8
8
|
import { HUBSPOT_PROJECT_COMPONENTS_GITHUB_PATH, DEFAULT_PROJECT_TEMPLATE_BRANCH, } from '../../constants.js';
|
|
9
9
|
import { updateHsMetaFilesWithAutoGeneratedFields, handleComponentCollision, } from '../components.js';
|
|
10
10
|
import { getProjectMetadata, } from '@hubspot/project-parsing-lib/src/lib/project.js';
|
|
@@ -13,7 +13,7 @@ import { cloneGithubRepo } from '@hubspot/local-dev-lib/github';
|
|
|
13
13
|
import { debugError } from '../../errorHandlers/index.js';
|
|
14
14
|
import { uiLogger } from '../../ui/logger.js';
|
|
15
15
|
import { trackCommandUsage } from '../../usageTracking.js';
|
|
16
|
-
export async function
|
|
16
|
+
export async function v2AddComponent(args, projectDir, projectConfig, accountId) {
|
|
17
17
|
uiLogger.log(commands.project.add.creatingComponent(projectConfig.name));
|
|
18
18
|
const config = await getConfigForPlatformVersion(projectConfig.platformVersion);
|
|
19
19
|
const { components, parentComponents } = config;
|
|
@@ -27,7 +27,7 @@ export async function v3AddComponent(args, projectDir, projectConfig, accountId)
|
|
|
27
27
|
const appsMetadata = currentProjectMetadata.components[AppKey];
|
|
28
28
|
const shouldCreateApp = appsMetadata.count === 0;
|
|
29
29
|
if (shouldCreateApp) {
|
|
30
|
-
const { authType, distribution } = await
|
|
30
|
+
const { authType, distribution } = await createV2App(args.auth, args.distribution);
|
|
31
31
|
derivedDistribution = distribution;
|
|
32
32
|
derivedAuthType = authType;
|
|
33
33
|
}
|
|
@@ -47,7 +47,7 @@ export async function v3AddComponent(args, projectDir, projectConfig, accountId)
|
|
|
47
47
|
derivedAuthType = apps[0].config?.auth?.type;
|
|
48
48
|
}
|
|
49
49
|
const componentTemplateChoices = await calculateComponentTemplateChoices(components, derivedAuthType, derivedDistribution, args.derivedAccountId, currentProjectMetadata);
|
|
50
|
-
const projectAddPromptResponse = await
|
|
50
|
+
const projectAddPromptResponse = await projectAddPromptV2(componentTemplateChoices, args.features);
|
|
51
51
|
const componentTypes = projectAddPromptResponse.componentTemplate?.map(componentTemplate => componentTemplate.cliSelector || componentTemplate.type);
|
|
52
52
|
await trackCommandUsage('project-add', {
|
|
53
53
|
type: componentTypes?.join(','),
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
import { calculateComponentTemplateChoices } from '../
|
|
1
|
+
import { calculateComponentTemplateChoices } from '../v2.js';
|
|
2
2
|
import { hasFeature } from '../../../hasFeature.js';
|
|
3
3
|
vi.mock('../../ui/logger.js');
|
|
4
4
|
vi.mock('@hubspot/local-dev-lib/api/github');
|
|
5
5
|
vi.mock('../../../hasFeature.js');
|
|
6
6
|
const mockHasFeature = vi.mocked(hasFeature);
|
|
7
|
-
describe('lib/projects/create/
|
|
7
|
+
describe('lib/projects/create/v2', () => {
|
|
8
8
|
beforeEach(() => {
|
|
9
9
|
mockHasFeature.mockResolvedValue(true);
|
|
10
10
|
});
|
|
@@ -2,7 +2,7 @@ import { selectProjectTemplatePrompt, } from '../../prompts/selectProjectTemplat
|
|
|
2
2
|
import { projectNameAndDestPrompt } from '../../prompts/projectNameAndDestPrompt.js';
|
|
3
3
|
import { DEFAULT_PROJECT_TEMPLATE_BRANCH, HUBSPOT_PROJECT_COMPONENTS_GITHUB_PATH, EMPTY_PROJECT, } from '../../constants.js';
|
|
4
4
|
import { isV2Project } from '../platformVersion.js';
|
|
5
|
-
import {
|
|
5
|
+
import { v2ComponentFlow } from './v2.js';
|
|
6
6
|
import { getProjectTemplateListFromRepo } from './legacy.js';
|
|
7
7
|
import { uiLogger } from '../../ui/logger.js';
|
|
8
8
|
import { commands } from '../../../lang/en.js';
|
|
@@ -12,7 +12,7 @@ export async function handleProjectCreationFlow(args) {
|
|
|
12
12
|
const repo = templateSource || HUBSPOT_PROJECT_COMPONENTS_GITHUB_PATH;
|
|
13
13
|
const projectNameAndDestPromptResponse = await projectNameAndDestPrompt(args);
|
|
14
14
|
if (isV2Project(platformVersion)) {
|
|
15
|
-
const { componentTemplateChoices, authType, distribution, repoConfig, projectContents, } = await
|
|
15
|
+
const { componentTemplateChoices, authType, distribution, repoConfig, projectContents, } = await v2ComponentFlow(platformVersion, projectBase, providedAuth, providedDistribution, args.derivedAccountId);
|
|
16
16
|
const selectProjectTemplatePromptResponse = await selectProjectTemplatePrompt(args, undefined, projectContents !== EMPTY_PROJECT ? componentTemplateChoices : undefined);
|
|
17
17
|
return {
|
|
18
18
|
authType,
|
|
@@ -2,19 +2,19 @@ import { Separator } from '@inquirer/prompts';
|
|
|
2
2
|
import { ComponentTemplate, ComponentTemplateChoice, ProjectTemplateRepoConfig } from '../../../types/Projects.js';
|
|
3
3
|
import { ProjectMetadata } from '@hubspot/project-parsing-lib/src/lib/project.js';
|
|
4
4
|
import { SelectProjectTemplatePromptResponse } from '../../prompts/selectProjectTemplatePrompt.js';
|
|
5
|
-
export declare function
|
|
5
|
+
export declare function createV2App(providedAuth: string | undefined, providedDistribution: string | undefined): Promise<{
|
|
6
6
|
authType: string;
|
|
7
7
|
distribution: string;
|
|
8
8
|
}>;
|
|
9
9
|
export declare function calculateComponentTemplateChoices(components: ComponentTemplate[], authType: string | undefined, distribution: string | undefined, accountId: number, projectMetadata?: ProjectMetadata): Promise<(ComponentTemplateChoice | Separator)[]>;
|
|
10
|
-
type
|
|
10
|
+
type V2ComponentInfo = {
|
|
11
11
|
authType?: string;
|
|
12
12
|
distribution?: string;
|
|
13
13
|
repoConfig?: ProjectTemplateRepoConfig;
|
|
14
14
|
projectContents?: string;
|
|
15
15
|
componentTemplateChoices?: (ComponentTemplateChoice | Separator)[];
|
|
16
16
|
};
|
|
17
|
-
export declare function
|
|
17
|
+
export declare function v2ComponentFlow(platformVersion: string, projectBase: string | undefined, providedAuth: string | undefined, providedDistribution: string | undefined, accountId: number): Promise<V2ComponentInfo>;
|
|
18
18
|
export declare function generateComponentPaths({ selectProjectTemplatePromptResponse, platformVersion, repoConfig, projectContents, authType, distribution, }: {
|
|
19
19
|
selectProjectTemplatePromptResponse: SelectProjectTemplatePromptResponse;
|
|
20
20
|
platformVersion: string;
|
|
@@ -10,7 +10,7 @@ import { logError } from '../../errorHandlers/index.js';
|
|
|
10
10
|
import { EXIT_CODES } from '../../enums/exitCodes.js';
|
|
11
11
|
import { hasFeature } from '../../hasFeature.js';
|
|
12
12
|
import { AppEventsKey, PagesKey, } from '@hubspot/project-parsing-lib/src/lib/constants.js';
|
|
13
|
-
export async function
|
|
13
|
+
export async function createV2App(providedAuth, providedDistribution) {
|
|
14
14
|
let authType;
|
|
15
15
|
if (providedAuth &&
|
|
16
16
|
providedDistribution === marketplaceDistribution &&
|
|
@@ -112,7 +112,7 @@ export async function calculateComponentTemplateChoices(components, authType, di
|
|
|
112
112
|
]
|
|
113
113
|
: [...enabledComponents];
|
|
114
114
|
}
|
|
115
|
-
export async function
|
|
115
|
+
export async function v2ComponentFlow(platformVersion, projectBase, providedAuth, providedDistribution, accountId) {
|
|
116
116
|
let repoConfig = undefined;
|
|
117
117
|
let authType;
|
|
118
118
|
let distribution;
|
|
@@ -134,7 +134,7 @@ export async function v3ComponentFlow(platformVersion, projectBase, providedAuth
|
|
|
134
134
|
],
|
|
135
135
|
}));
|
|
136
136
|
if (projectContentsChoice === PROJECT_WITH_APP) {
|
|
137
|
-
const { authType: selectedAuthType, distribution: selectedDistribution } = await
|
|
137
|
+
const { authType: selectedAuthType, distribution: selectedDistribution } = await createV2App(providedAuth, providedDistribution);
|
|
138
138
|
authType = selectedAuthType;
|
|
139
139
|
distribution = selectedDistribution;
|
|
140
140
|
}
|
package/lib/projects/deploy.d.ts
CHANGED
|
@@ -10,4 +10,4 @@ export declare function logDeployErrors(errorData: {
|
|
|
10
10
|
};
|
|
11
11
|
}>;
|
|
12
12
|
}): void;
|
|
13
|
-
export declare function handleProjectDeploy(targetAccountId: number, projectName: string, buildId: number,
|
|
13
|
+
export declare function handleProjectDeploy(targetAccountId: number, projectName: string, buildId: number, isV2Project: boolean, force: boolean): Promise<Deploy | undefined>;
|
package/lib/projects/deploy.js
CHANGED
|
@@ -47,8 +47,8 @@ function handleBlockedDeploy(deployResp) {
|
|
|
47
47
|
uiLogger.log('');
|
|
48
48
|
});
|
|
49
49
|
}
|
|
50
|
-
export async function handleProjectDeploy(targetAccountId, projectName, buildId,
|
|
51
|
-
const { data: deployResp } = await deployProject(targetAccountId, projectName, buildId,
|
|
50
|
+
export async function handleProjectDeploy(targetAccountId, projectName, buildId, isV2Project, force) {
|
|
51
|
+
const { data: deployResp } = await deployProject(targetAccountId, projectName, buildId, isV2Project, force);
|
|
52
52
|
if (!deployResp || deployResp.buildResultType !== 'DEPLOY_QUEUED') {
|
|
53
53
|
if (deployResp?.buildResultType === 'DEPLOY_BLOCKED') {
|
|
54
54
|
handleBlockedDeploy(deployResp);
|
|
@@ -10,6 +10,7 @@ declare class AppDevModeInterface {
|
|
|
10
10
|
localDevLogger: LocalDevLogger;
|
|
11
11
|
_appNode?: AppIRNode | null;
|
|
12
12
|
marketplaceAppInstalls?: number;
|
|
13
|
+
private appInstallResolve?;
|
|
13
14
|
constructor(options: AppDevModeInterfaceConstructorOptions);
|
|
14
15
|
private getAppNodeFromProjectNodes;
|
|
15
16
|
private get appNode();
|
|
@@ -17,14 +18,20 @@ declare class AppDevModeInterface {
|
|
|
17
18
|
private set appData(value);
|
|
18
19
|
private isStaticAuthApp;
|
|
19
20
|
private isOAuthApp;
|
|
21
|
+
private isAutomaticallyInstallable;
|
|
20
22
|
private getAppInstallUrl;
|
|
21
23
|
private fetchAppData;
|
|
22
24
|
private checkMarketplaceAppInstalls;
|
|
25
|
+
private waitUntilAppIsInstalled;
|
|
26
|
+
private autoInstallStaticAuthApp;
|
|
23
27
|
private installAppOrOpenInstallUrl;
|
|
24
28
|
private checkTestAccountAppInstallation;
|
|
29
|
+
private resolveAppInstallPromise;
|
|
30
|
+
private handleAppInstallSuccessDevServerMessage;
|
|
31
|
+
private handleAppInstallInitiatedDevServerMessage;
|
|
32
|
+
private handleAppInstallFailureDevServerMessage;
|
|
25
33
|
private onDevServerMessage;
|
|
26
34
|
private onChangeProjectNodes;
|
|
27
|
-
private setUpStateListeners;
|
|
28
35
|
private removeStateListeners;
|
|
29
36
|
setup(args: any): Promise<void>;
|
|
30
37
|
start(): Promise<void>;
|
|
@@ -1,27 +1,26 @@
|
|
|
1
1
|
import { fetchAppInstallationData } from '@hubspot/local-dev-lib/api/localDevAuth';
|
|
2
|
-
import {
|
|
3
|
-
// installStaticAuthAppOnTestAccount,
|
|
4
|
-
} from '@hubspot/local-dev-lib/api/appsDev';
|
|
2
|
+
import { fetchAppMetadataByUid, fetchPublicAppProductionInstallCounts, installStaticAuthAppOnTestAccount, } from '@hubspot/local-dev-lib/api/appsDev';
|
|
5
3
|
import { DevModeUnifiedInterface as UIEDevModeInterface } from '@hubspot/ui-extensions-dev-server';
|
|
6
4
|
import { requestPorts } from '@hubspot/local-dev-lib/portManager';
|
|
5
|
+
import { getAccountConfig } from '@hubspot/local-dev-lib/config';
|
|
7
6
|
import { APP_AUTH_TYPES, APP_DISTRIBUTION_TYPES, APP_INSTALLATION_STATES, LOCAL_DEV_SERVER_MESSAGE_TYPES, } from '../../constants.js';
|
|
8
7
|
import { EXIT_CODES } from '../../enums/exitCodes.js';
|
|
9
8
|
import { isAppIRNode } from '../../projects/structure.js';
|
|
10
9
|
import { uiLine } from '../../ui/index.js';
|
|
11
10
|
import { logError } from '../../errorHandlers/index.js';
|
|
12
|
-
import {
|
|
13
|
-
// installAppAutoPrompt,
|
|
14
|
-
installAppBrowserPrompt, } from '../../prompts/installAppPrompt.js';
|
|
11
|
+
import { installAppAutoPrompt, installAppBrowserPrompt, } from '../../prompts/installAppPrompt.js';
|
|
15
12
|
import { confirmPrompt } from '../../prompts/promptUtils.js';
|
|
16
13
|
import { lib } from '../../../lang/en.js';
|
|
17
14
|
import { uiLogger } from '../../ui/logger.js';
|
|
18
15
|
import { getOauthAppInstallUrl, getStaticAuthAppInstallUrl, } from '../../app/urls.js';
|
|
16
|
+
import { isDeveloperTestAccount, isSandbox } from '../../accountTypes.js';
|
|
19
17
|
import SpinniesManager from '../../ui/SpinniesManager.js';
|
|
20
18
|
class AppDevModeInterface {
|
|
21
19
|
localDevState;
|
|
22
20
|
localDevLogger;
|
|
23
21
|
_appNode;
|
|
24
22
|
marketplaceAppInstalls;
|
|
23
|
+
appInstallResolve;
|
|
25
24
|
constructor(options) {
|
|
26
25
|
this.localDevState = options.localDevState;
|
|
27
26
|
this.localDevLogger = options.localDevLogger;
|
|
@@ -60,26 +59,17 @@ class AppDevModeInterface {
|
|
|
60
59
|
isOAuthApp() {
|
|
61
60
|
return (this.appNode?.config.auth.type.toLowerCase() === APP_AUTH_TYPES.OAUTH);
|
|
62
61
|
}
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
// const hasCorrectParent =
|
|
75
|
-
// targetTestingAccount.parentAccountId ===
|
|
76
|
-
// this.localDevState.targetProjectAccountId;
|
|
77
|
-
// return (
|
|
78
|
-
// isTestAccount &&
|
|
79
|
-
// hasCorrectParent &&
|
|
80
|
-
// this.isStaticAuthApp()
|
|
81
|
-
// );
|
|
82
|
-
// }
|
|
62
|
+
isAutomaticallyInstallable() {
|
|
63
|
+
const targetTestingAccount = getAccountConfig(this.localDevState.targetTestingAccountId);
|
|
64
|
+
if (!targetTestingAccount) {
|
|
65
|
+
return false;
|
|
66
|
+
}
|
|
67
|
+
const isTestAccount = isDeveloperTestAccount(targetTestingAccount) ||
|
|
68
|
+
isSandbox(targetTestingAccount);
|
|
69
|
+
const hasCorrectParent = targetTestingAccount.parentAccountId ===
|
|
70
|
+
this.localDevState.targetProjectAccountId;
|
|
71
|
+
return isTestAccount && hasCorrectParent && this.isStaticAuthApp();
|
|
72
|
+
}
|
|
83
73
|
async getAppInstallUrl() {
|
|
84
74
|
if (this.appNode && this.isOAuthApp()) {
|
|
85
75
|
return getOauthAppInstallUrl({
|
|
@@ -90,26 +80,20 @@ class AppDevModeInterface {
|
|
|
90
80
|
redirectUrls: this.appNode.config.auth.redirectUrls,
|
|
91
81
|
});
|
|
92
82
|
}
|
|
93
|
-
const { data: { results }, } = await fetchPublicAppsForPortal(this.localDevState.targetProjectAccountId);
|
|
94
|
-
const app = results.find(app => app.sourceId === this.appNode?.uid);
|
|
95
|
-
if (!app) {
|
|
96
|
-
uiLogger.error(lib.LocalDevManager.appNotFound(this.localDevState.targetProjectAccountId, this.appNode?.uid));
|
|
97
|
-
process.exit(EXIT_CODES.ERROR);
|
|
98
|
-
}
|
|
99
83
|
return getStaticAuthAppInstallUrl({
|
|
100
84
|
targetAccountId: this.localDevState.targetTestingAccountId,
|
|
101
85
|
env: this.localDevState.env,
|
|
102
|
-
appId:
|
|
86
|
+
appId: this.appData.id,
|
|
103
87
|
});
|
|
104
88
|
}
|
|
105
89
|
async fetchAppData() {
|
|
106
90
|
SpinniesManager.add('fetchAppData', {
|
|
107
91
|
text: lib.AppDevModeInterface.fetchAppData.checking(this.appNode?.config.name || ''),
|
|
108
92
|
});
|
|
109
|
-
let
|
|
93
|
+
let appData;
|
|
110
94
|
try {
|
|
111
|
-
const { data
|
|
112
|
-
|
|
95
|
+
const { data } = await fetchAppMetadataByUid(this.appNode.uid, this.localDevState.targetProjectAccountId);
|
|
96
|
+
appData = data;
|
|
113
97
|
}
|
|
114
98
|
catch (e) {
|
|
115
99
|
SpinniesManager.fail('fetchAppData', {
|
|
@@ -118,7 +102,6 @@ class AppDevModeInterface {
|
|
|
118
102
|
logError(e);
|
|
119
103
|
process.exit(EXIT_CODES.ERROR);
|
|
120
104
|
}
|
|
121
|
-
const appData = portalApps.find(({ sourceId }) => sourceId === this.appNode?.uid);
|
|
122
105
|
if (!appData) {
|
|
123
106
|
return;
|
|
124
107
|
}
|
|
@@ -127,7 +110,7 @@ class AppDevModeInterface {
|
|
|
127
110
|
id: appData.id,
|
|
128
111
|
clientId: appData.clientId,
|
|
129
112
|
name: appData.name,
|
|
130
|
-
installationState: APP_INSTALLATION_STATES.
|
|
113
|
+
installationState: APP_INSTALLATION_STATES.UNKNOWN,
|
|
131
114
|
scopeGroupIds: appData.scopeGroupIds,
|
|
132
115
|
};
|
|
133
116
|
this.marketplaceAppInstalls = uniquePortalInstallCount;
|
|
@@ -149,50 +132,55 @@ class AppDevModeInterface {
|
|
|
149
132
|
}
|
|
150
133
|
this.localDevState.addUploadWarning(lib.AppDevModeInterface.defaultMarketplaceAppWarning(this.marketplaceAppInstalls));
|
|
151
134
|
}
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
135
|
+
async waitUntilAppIsInstalled(installUrl) {
|
|
136
|
+
uiLogger.log(lib.AppDevModeInterface.waitUntilAppIsInstalled.link(installUrl));
|
|
137
|
+
SpinniesManager.add('waitUntilAppIsInstalled', {
|
|
138
|
+
text: lib.AppDevModeInterface.waitUntilAppIsInstalled.waiting,
|
|
139
|
+
});
|
|
140
|
+
await new Promise(resolve => {
|
|
141
|
+
this.appInstallResolve = resolve;
|
|
142
|
+
});
|
|
143
|
+
SpinniesManager.succeed('waitUntilAppIsInstalled', {
|
|
144
|
+
text: lib.AppDevModeInterface.waitUntilAppIsInstalled.success(this.appNode?.config.name || '', this.localDevState.targetTestingAccountId),
|
|
145
|
+
});
|
|
146
|
+
}
|
|
147
|
+
async autoInstallStaticAuthApp() {
|
|
148
|
+
const shouldInstall = await installAppAutoPrompt();
|
|
149
|
+
if (!shouldInstall) {
|
|
150
|
+
uiLogger.log(lib.AppDevModeInterface.autoInstallDeclined);
|
|
151
|
+
process.exit(EXIT_CODES.SUCCESS);
|
|
152
|
+
}
|
|
153
|
+
uiLogger.log('');
|
|
154
|
+
SpinniesManager.add('autoInstallStaticAuthApp', {
|
|
155
|
+
text: lib.AppDevModeInterface.autoInstallStaticAuthApp.installing(this.appData.name, this.localDevState.targetTestingAccountId),
|
|
156
|
+
});
|
|
157
|
+
try {
|
|
158
|
+
await installStaticAuthAppOnTestAccount(this.appData.id, this.localDevState.targetTestingAccountId, this.appData.scopeGroupIds);
|
|
159
|
+
SpinniesManager.succeed('autoInstallStaticAuthApp', {
|
|
160
|
+
text: lib.AppDevModeInterface.autoInstallStaticAuthApp.success(this.appData.name, this.localDevState.targetTestingAccountId),
|
|
161
|
+
});
|
|
162
|
+
return true;
|
|
163
|
+
}
|
|
164
|
+
catch (e) {
|
|
165
|
+
SpinniesManager.fail('autoInstallStaticAuthApp', {
|
|
166
|
+
text: lib.AppDevModeInterface.autoInstallStaticAuthApp.error(this.appData.name, this.localDevState.targetTestingAccountId),
|
|
167
|
+
failColor: 'white',
|
|
168
|
+
});
|
|
169
|
+
return false;
|
|
170
|
+
}
|
|
171
|
+
}
|
|
165
172
|
async installAppOrOpenInstallUrl(isReinstall) {
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
// uiLogger.success(
|
|
171
|
-
// lib.AppDevModeInterface.autoInstallSuccess(
|
|
172
|
-
// this.appData!.name,
|
|
173
|
-
// this.localDevState.targetTestingAccountId
|
|
174
|
-
// )
|
|
175
|
-
// );
|
|
176
|
-
// return;
|
|
177
|
-
// } catch (e) {
|
|
178
|
-
// uiLogger.error(
|
|
179
|
-
// lib.AppDevModeInterface.autoInstallError(
|
|
180
|
-
// this.appData!.name,
|
|
181
|
-
// this.localDevState.targetTestingAccountId
|
|
182
|
-
// )
|
|
183
|
-
// );
|
|
184
|
-
// }
|
|
185
|
-
// }
|
|
186
|
-
const staticAuthInstallOptions = this.isStaticAuthApp()
|
|
187
|
-
? {
|
|
188
|
-
testingAccountId: this.localDevState.targetTestingAccountId,
|
|
189
|
-
projectAccountId: this.localDevState.targetProjectAccountId,
|
|
190
|
-
projectName: this.localDevState.projectConfig.name,
|
|
191
|
-
appUid: this.appNode.uid,
|
|
173
|
+
if (this.isAutomaticallyInstallable()) {
|
|
174
|
+
const installSuccess = await this.autoInstallStaticAuthApp();
|
|
175
|
+
if (installSuccess) {
|
|
176
|
+
return;
|
|
192
177
|
}
|
|
193
|
-
|
|
178
|
+
}
|
|
194
179
|
const installUrl = await this.getAppInstallUrl();
|
|
195
|
-
await installAppBrowserPrompt(installUrl, isReinstall
|
|
180
|
+
await installAppBrowserPrompt(installUrl, isReinstall);
|
|
181
|
+
if (!isReinstall) {
|
|
182
|
+
await this.waitUntilAppIsInstalled(installUrl);
|
|
183
|
+
}
|
|
196
184
|
}
|
|
197
185
|
async checkTestAccountAppInstallation() {
|
|
198
186
|
if (!this.appNode || !this.appData) {
|
|
@@ -212,11 +200,46 @@ class AppDevModeInterface {
|
|
|
212
200
|
installationState: APP_INSTALLATION_STATES.INSTALLED_WITH_OUTDATED_SCOPES,
|
|
213
201
|
};
|
|
214
202
|
}
|
|
203
|
+
else {
|
|
204
|
+
this.appData = {
|
|
205
|
+
...this.appData,
|
|
206
|
+
installationState: APP_INSTALLATION_STATES.NOT_INSTALLED,
|
|
207
|
+
};
|
|
208
|
+
}
|
|
215
209
|
return { needsInstall: !isInstalledWithScopeGroups, isReinstall };
|
|
216
210
|
}
|
|
217
|
-
|
|
211
|
+
resolveAppInstallPromise() {
|
|
212
|
+
if (this.appInstallResolve) {
|
|
213
|
+
this.appInstallResolve();
|
|
214
|
+
this.appInstallResolve = undefined;
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
handleAppInstallSuccessDevServerMessage() {
|
|
218
|
+
this.resolveAppInstallPromise();
|
|
219
|
+
this.appData = {
|
|
220
|
+
...this.appData,
|
|
221
|
+
installationState: APP_INSTALLATION_STATES.INSTALLED,
|
|
222
|
+
};
|
|
223
|
+
}
|
|
224
|
+
handleAppInstallInitiatedDevServerMessage() {
|
|
225
|
+
this.resolveAppInstallPromise();
|
|
226
|
+
}
|
|
227
|
+
handleAppInstallFailureDevServerMessage() {
|
|
228
|
+
uiLogger.error(lib.AppDevModeInterface.installationFailed);
|
|
229
|
+
process.exit(EXIT_CODES.ERROR);
|
|
230
|
+
}
|
|
231
|
+
onDevServerMessage = async (message) => {
|
|
218
232
|
if (message === LOCAL_DEV_SERVER_MESSAGE_TYPES.WEBSOCKET_SERVER_CONNECTED) {
|
|
219
|
-
this.checkTestAccountAppInstallation();
|
|
233
|
+
await this.checkTestAccountAppInstallation();
|
|
234
|
+
}
|
|
235
|
+
else if (message === LOCAL_DEV_SERVER_MESSAGE_TYPES.STATIC_AUTH_APP_INSTALL_SUCCESS) {
|
|
236
|
+
this.handleAppInstallSuccessDevServerMessage();
|
|
237
|
+
}
|
|
238
|
+
else if (message === LOCAL_DEV_SERVER_MESSAGE_TYPES.STATIC_AUTH_APP_INSTALL_FAILURE) {
|
|
239
|
+
this.handleAppInstallFailureDevServerMessage();
|
|
240
|
+
}
|
|
241
|
+
else if (message === LOCAL_DEV_SERVER_MESSAGE_TYPES.OAUTH_APP_INSTALL_INITIATED) {
|
|
242
|
+
this.handleAppInstallInitiatedDevServerMessage();
|
|
220
243
|
}
|
|
221
244
|
};
|
|
222
245
|
onChangeProjectNodes = (nodes) => {
|
|
@@ -234,10 +257,6 @@ class AppDevModeInterface {
|
|
|
234
257
|
this.localDevState.addUploadWarning(lib.AppDevModeInterface.authTypeChanged);
|
|
235
258
|
}
|
|
236
259
|
};
|
|
237
|
-
setUpStateListeners() {
|
|
238
|
-
this.localDevState.addListener('devServerMessage', this.onDevServerMessage);
|
|
239
|
-
this.localDevState.addListener('projectNodes', this.onChangeProjectNodes);
|
|
240
|
-
}
|
|
241
260
|
removeStateListeners() {
|
|
242
261
|
this.localDevState.removeListener('devServerMessage', this.onDevServerMessage);
|
|
243
262
|
this.localDevState.removeListener('projectNodes', this.onChangeProjectNodes);
|
|
@@ -261,6 +280,7 @@ class AppDevModeInterface {
|
|
|
261
280
|
failColor: 'white',
|
|
262
281
|
});
|
|
263
282
|
}
|
|
283
|
+
this.localDevState.addListener('devServerMessage', this.onDevServerMessage);
|
|
264
284
|
await this.installAppOrOpenInstallUrl(isReinstall || false);
|
|
265
285
|
}
|
|
266
286
|
else {
|
|
@@ -275,7 +295,7 @@ class AppDevModeInterface {
|
|
|
275
295
|
catch (e) {
|
|
276
296
|
logError(e);
|
|
277
297
|
}
|
|
278
|
-
this.
|
|
298
|
+
this.localDevState.addListener('projectNodes', this.onChangeProjectNodes);
|
|
279
299
|
return UIEDevModeInterface.setup(args);
|
|
280
300
|
}
|
|
281
301
|
async start() {
|
|
@@ -1,40 +1,22 @@
|
|
|
1
|
-
import
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
cleanup?: () => Promise<void>;
|
|
7
|
-
};
|
|
8
|
-
type ComponentsByType = {
|
|
9
|
-
[key in ComponentTypes]?: {
|
|
10
|
-
[key: string]: Component;
|
|
11
|
-
};
|
|
1
|
+
import LocalDevState from './LocalDevState.js';
|
|
2
|
+
import LocalDevLogger from './LocalDevLogger.js';
|
|
3
|
+
type DevServerManagerConstructorOptions = {
|
|
4
|
+
localDevState: LocalDevState;
|
|
5
|
+
logger: LocalDevLogger;
|
|
12
6
|
};
|
|
13
7
|
declare class DevServerManager {
|
|
14
8
|
private initialized;
|
|
15
9
|
private started;
|
|
16
|
-
private componentsByType;
|
|
17
10
|
private devServers;
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
setup({ components, onUploadRequired, accountId, setActiveApp, }: {
|
|
24
|
-
components: Component[];
|
|
25
|
-
onUploadRequired: () => void;
|
|
26
|
-
accountId: number;
|
|
27
|
-
setActiveApp: (appUid: string | undefined) => Promise<void>;
|
|
28
|
-
}): Promise<void>;
|
|
29
|
-
start({ accountId, projectConfig, }: {
|
|
30
|
-
accountId: number;
|
|
31
|
-
projectConfig: ProjectConfig;
|
|
32
|
-
}): Promise<void>;
|
|
11
|
+
private localDevState;
|
|
12
|
+
constructor(options: DevServerManagerConstructorOptions);
|
|
13
|
+
private iterateDevServers;
|
|
14
|
+
setup(): Promise<void>;
|
|
15
|
+
start(): Promise<void>;
|
|
33
16
|
fileChange({ filePath, event, }: {
|
|
34
17
|
filePath: string;
|
|
35
18
|
event: string;
|
|
36
19
|
}): Promise<void>;
|
|
37
20
|
cleanup(): Promise<void>;
|
|
38
21
|
}
|
|
39
|
-
|
|
40
|
-
export default Manager;
|
|
22
|
+
export default DevServerManager;
|
|
@@ -1,93 +1,53 @@
|
|
|
1
1
|
import { logger } from '@hubspot/local-dev-lib/logger';
|
|
2
|
-
import { DevModeInterface as UIEDevModeInterface } from '@hubspot/ui-extensions-dev-server';
|
|
3
|
-
import { startPortManagerServer, stopPortManagerServer, requestPorts, } from '@hubspot/local-dev-lib/portManager';
|
|
4
2
|
import { getHubSpotApiOrigin, getHubSpotWebsiteOrigin, } from '@hubspot/local-dev-lib/urls';
|
|
5
3
|
import { getAccountConfig } from '@hubspot/local-dev-lib/config';
|
|
6
|
-
import
|
|
4
|
+
import AppDevModeInterface from './AppDevModeInterface.js';
|
|
7
5
|
import { lib } from '../../../lang/en.js';
|
|
8
|
-
import { uiLogger } from '../../ui/logger.js';
|
|
9
|
-
const SERVER_KEYS = {
|
|
10
|
-
privateApp: 'privateApp',
|
|
11
|
-
publicApp: 'publicApp',
|
|
12
|
-
};
|
|
13
6
|
class DevServerManager {
|
|
14
7
|
initialized;
|
|
15
8
|
started;
|
|
16
|
-
componentsByType;
|
|
17
9
|
devServers;
|
|
18
|
-
|
|
10
|
+
localDevState;
|
|
11
|
+
constructor(options) {
|
|
19
12
|
this.initialized = false;
|
|
20
13
|
this.started = false;
|
|
21
|
-
this.
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
[SERVER_KEYS.publicApp]: {
|
|
28
|
-
componentType: ComponentTypes.PublicApp,
|
|
29
|
-
serverInterface: UIEDevModeInterface,
|
|
30
|
-
},
|
|
31
|
-
};
|
|
14
|
+
this.localDevState = options.localDevState;
|
|
15
|
+
const AppsDevServer = new AppDevModeInterface({
|
|
16
|
+
localDevState: options.localDevState,
|
|
17
|
+
localDevLogger: options.logger,
|
|
18
|
+
});
|
|
19
|
+
this.devServers = [AppsDevServer];
|
|
32
20
|
}
|
|
33
21
|
async iterateDevServers(callback) {
|
|
34
|
-
|
|
35
|
-
for (let i = 0; i < serverKeys.length; i++) {
|
|
36
|
-
const serverKey = serverKeys[i];
|
|
37
|
-
const devServer = this.devServers[serverKey];
|
|
38
|
-
const compatibleComponents = this.componentsByType[devServer.componentType] || {};
|
|
39
|
-
if (Object.keys(compatibleComponents).length) {
|
|
40
|
-
await callback(devServer.serverInterface, compatibleComponents);
|
|
41
|
-
}
|
|
42
|
-
else {
|
|
43
|
-
uiLogger.debug(lib.DevServerManager.noCompatibleComponents(serverKey));
|
|
44
|
-
}
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
arrangeComponentsByType(components) {
|
|
48
|
-
return components.reduce((acc, component) => {
|
|
49
|
-
if (!acc[component.type]) {
|
|
50
|
-
acc[component.type] = {};
|
|
51
|
-
}
|
|
52
|
-
if ('name' in component.config && component.config.name) {
|
|
53
|
-
acc[component.type][component.config.name] = component;
|
|
54
|
-
}
|
|
55
|
-
return acc;
|
|
56
|
-
}, {});
|
|
22
|
+
await Promise.all(this.devServers.map(devServer => callback(devServer)));
|
|
57
23
|
}
|
|
58
|
-
async setup(
|
|
59
|
-
this.componentsByType = this.arrangeComponentsByType(components);
|
|
24
|
+
async setup() {
|
|
60
25
|
let env;
|
|
61
|
-
const accountConfig = getAccountConfig(
|
|
26
|
+
const accountConfig = getAccountConfig(this.localDevState.targetTestingAccountId);
|
|
62
27
|
if (accountConfig) {
|
|
63
28
|
env = accountConfig.env;
|
|
64
29
|
}
|
|
65
|
-
await
|
|
66
|
-
await this.iterateDevServers(async (serverInterface, compatibleComponents) => {
|
|
30
|
+
await this.iterateDevServers(async (serverInterface) => {
|
|
67
31
|
if (serverInterface.setup) {
|
|
32
|
+
// @TODO: In the future, update UIE Dev Server to use LocalDevState
|
|
68
33
|
await serverInterface.setup({
|
|
69
|
-
components:
|
|
70
|
-
|
|
34
|
+
components: this.localDevState.projectNodes,
|
|
35
|
+
profileData: this.localDevState.projectProfileData,
|
|
71
36
|
logger,
|
|
72
37
|
urls: {
|
|
73
38
|
api: getHubSpotApiOrigin(env),
|
|
74
39
|
web: getHubSpotWebsiteOrigin(env),
|
|
75
40
|
},
|
|
76
|
-
setActiveApp,
|
|
77
41
|
});
|
|
78
42
|
}
|
|
79
43
|
});
|
|
80
44
|
this.initialized = true;
|
|
81
45
|
}
|
|
82
|
-
async start(
|
|
46
|
+
async start() {
|
|
83
47
|
if (this.initialized) {
|
|
84
48
|
await this.iterateDevServers(async (serverInterface) => {
|
|
85
49
|
if (serverInterface.start) {
|
|
86
|
-
await serverInterface.start(
|
|
87
|
-
accountId,
|
|
88
|
-
projectConfig,
|
|
89
|
-
requestPorts,
|
|
90
|
-
});
|
|
50
|
+
await serverInterface.start();
|
|
91
51
|
}
|
|
92
52
|
});
|
|
93
53
|
}
|
|
@@ -112,9 +72,7 @@ class DevServerManager {
|
|
|
112
72
|
await serverInterface.cleanup();
|
|
113
73
|
}
|
|
114
74
|
});
|
|
115
|
-
await stopPortManagerServer();
|
|
116
75
|
}
|
|
117
76
|
}
|
|
118
77
|
}
|
|
119
|
-
|
|
120
|
-
export default Manager;
|
|
78
|
+
export default DevServerManager;
|