@simplysm/sd-cli 12.4.2 → 12.5.1
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/dist/build-tools/SdCliNgRoutesFileGenerator.js +1 -1
- package/dist/build-tools/SdCliNgRoutesFileGenerator.js.map +1 -1
- package/dist/build-tools/SdLinter.js +16 -20
- package/dist/build-tools/SdLinter.js.map +1 -1
- package/dist/build-tools/SdNgBundler.d.ts +1 -0
- package/dist/build-tools/SdNgBundler.js +1 -1
- package/dist/build-tools/SdNgBundler.js.map +1 -1
- package/dist/builders/SdCliClientBuilder.js +2 -1
- package/dist/builders/SdCliClientBuilder.js.map +1 -1
- package/dist/commons.d.ts +3 -0
- package/dist/entry/SdCliProject.js +21 -16
- package/dist/entry/SdCliProject.js.map +1 -1
- package/lib/postinstall.js +1 -1
- package/package.json +14 -14
- package/src/build-tools/SdCliNgRoutesFileGenerator.ts +1 -1
- package/src/build-tools/SdLinter.ts +43 -40
- package/src/build-tools/SdNgBundler.ts +2 -1
- package/src/builders/SdCliClientBuilder.ts +2 -1
- package/src/commons.ts +4 -1
- package/src/entry/SdCliProject.ts +140 -105
- package/.eslintrc.cjs +0 -13
|
@@ -1,56 +1,59 @@
|
|
|
1
|
-
import {ISdCliPackageBuildResult} from "../commons";
|
|
2
|
-
import {ESLint} from "eslint";
|
|
1
|
+
import { ISdCliPackageBuildResult } from "../commons";
|
|
2
|
+
import { ESLint } from "eslint";
|
|
3
3
|
import ts from "typescript";
|
|
4
|
-
import {FsUtil} from "@simplysm/sd-core-node";
|
|
4
|
+
import { FsUtil } from "@simplysm/sd-core-node";
|
|
5
5
|
|
|
6
6
|
export abstract class SdLinter {
|
|
7
|
-
static async lintAsync(
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
7
|
+
static async lintAsync(
|
|
8
|
+
fileSet: Iterable<string>,
|
|
9
|
+
tsProgram: ts.Program | undefined
|
|
10
|
+
): Promise<ISdCliPackageBuildResult[]> {
|
|
11
|
+
const lintFilePaths = Array.from(fileSet)
|
|
12
|
+
.filter(
|
|
13
|
+
(item) =>
|
|
14
|
+
(!item.endsWith(".d.ts") && item.endsWith(".ts")) ||
|
|
15
|
+
item.endsWith(".js") ||
|
|
16
|
+
item.endsWith(".cjs") ||
|
|
17
|
+
item.endsWith(".mjs")
|
|
18
|
+
)
|
|
19
|
+
.filter((item) => FsUtil.exists(item));
|
|
14
20
|
|
|
15
21
|
if (lintFilePaths.length === 0) {
|
|
16
22
|
return [];
|
|
17
23
|
}
|
|
18
24
|
|
|
19
|
-
const linter = new ESLint(
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
project: null
|
|
29
|
-
}/*,
|
|
30
|
-
settings: {
|
|
31
|
-
"import/resolver": {
|
|
32
|
-
"typescript": {
|
|
25
|
+
const linter = new ESLint(
|
|
26
|
+
tsProgram != null
|
|
27
|
+
? {
|
|
28
|
+
cache: false,
|
|
29
|
+
overrideConfig: [
|
|
30
|
+
{
|
|
31
|
+
files: ["**/*.ts"],
|
|
32
|
+
languageOptions: {
|
|
33
|
+
parserOptions: {
|
|
33
34
|
programs: [tsProgram],
|
|
34
|
-
project: null
|
|
35
|
+
project: null,
|
|
36
|
+
tsconfigRootDir: null
|
|
35
37
|
}
|
|
36
38
|
}
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
39
|
+
}
|
|
40
|
+
]
|
|
41
|
+
}
|
|
42
|
+
: undefined
|
|
43
|
+
);
|
|
43
44
|
|
|
44
45
|
const lintResults = await linter.lintFiles(lintFilePaths);
|
|
45
46
|
|
|
46
|
-
return lintResults.mapMany((lintResult) =>
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
47
|
+
return lintResults.mapMany((lintResult) =>
|
|
48
|
+
lintResult.messages.map((msg) => ({
|
|
49
|
+
filePath: lintResult.filePath,
|
|
50
|
+
line: msg.line,
|
|
51
|
+
char: msg.column,
|
|
52
|
+
code: msg.messageId,
|
|
53
|
+
severity: msg.severity === 1 ? ("warning" as const) : ("error" as const),
|
|
54
|
+
message: msg.message + (msg.ruleId != null ? ` (${msg.ruleId})` : ``),
|
|
55
|
+
type: "lint" as const
|
|
56
|
+
}))
|
|
57
|
+
);
|
|
55
58
|
}
|
|
56
59
|
}
|
|
@@ -74,7 +74,7 @@ export class SdNgBundler {
|
|
|
74
74
|
this.#mainFilePath = path.resolve(opt.pkgPath, "src/main.ts");
|
|
75
75
|
this.#tsConfigFilePath = path.resolve(opt.pkgPath, "tsconfig.json");
|
|
76
76
|
this.#swConfFilePath = path.resolve(opt.pkgPath, "ngsw-config.json");
|
|
77
|
-
this.#browserTarget = transformSupportedBrowsersToTargets(browserslist(["last 2 Chrome versions", "last 2 Edge versions"]));
|
|
77
|
+
this.#browserTarget = transformSupportedBrowsersToTargets(browserslist(opt.browserslist ?? ["last 2 Chrome versions", "last 2 Edge versions"]));
|
|
78
78
|
this.#indexHtmlFilePath = path.resolve(opt.pkgPath, "src/index.html");
|
|
79
79
|
this.#pkgName = path.basename(opt.pkgPath);
|
|
80
80
|
this.#baseHref = opt.builderType === "web" ? `/${this.#pkgName}/` : opt.dev ? `/${this.#pkgName}/${opt.builderType}/` : ``;
|
|
@@ -606,4 +606,5 @@ interface IOptions {
|
|
|
606
606
|
builderType: string;
|
|
607
607
|
env: Record<string, string> | undefined;
|
|
608
608
|
cordovaConfig: ISdCliClientBuilderCordovaConfig | undefined;
|
|
609
|
+
browserslist: string[] | undefined;
|
|
609
610
|
}
|
|
@@ -142,6 +142,7 @@ export class SdCliClientBuilder extends EventEmitter {
|
|
|
142
142
|
...this._pkgConf.env,
|
|
143
143
|
...this._pkgConf.builder?.[builderType]?.env
|
|
144
144
|
},
|
|
145
|
+
browserslist: this._pkgConf.builder?.[builderType]?.browserslist,
|
|
145
146
|
cordovaConfig: builderType === "cordova" ? this._pkgConf.builder!.cordova : undefined,
|
|
146
147
|
}));
|
|
147
148
|
}
|
|
@@ -187,7 +188,7 @@ export class SdCliClientBuilder extends EventEmitter {
|
|
|
187
188
|
return {
|
|
188
189
|
watchFileSet: currWatchFileSet,
|
|
189
190
|
affectedFileSet,
|
|
190
|
-
buildResults: [...results, ...lintResults]
|
|
191
|
+
buildResults: [...results, ...lintResults].filter(item => item.filePath !== path.resolve(this._pkgPath, "src/routes.ts"))
|
|
191
192
|
};
|
|
192
193
|
}
|
|
193
194
|
|
package/src/commons.ts
CHANGED
|
@@ -122,12 +122,14 @@ export interface ISdCliClientBuilderElectronConfig {
|
|
|
122
122
|
// devServerPort?: number;
|
|
123
123
|
reinstallDependencies?: string[];
|
|
124
124
|
env?: Record<string, string>;
|
|
125
|
+
browserslist?: string[];
|
|
125
126
|
}
|
|
126
127
|
|
|
127
128
|
export interface ISdCliClientBuilderWebConfig {
|
|
128
129
|
// devServerHost?: string;
|
|
129
130
|
// devServerPort?: number;
|
|
130
131
|
env?: Record<string, string>;
|
|
132
|
+
browserslist?: string[];
|
|
131
133
|
}
|
|
132
134
|
|
|
133
135
|
export interface ISdCliClientBuilderCordovaConfig {
|
|
@@ -153,8 +155,9 @@ export interface ISdCliClientBuilderCordovaConfig {
|
|
|
153
155
|
maxSdkVersion?: number;
|
|
154
156
|
}[];
|
|
155
157
|
}
|
|
156
|
-
}
|
|
158
|
+
};
|
|
157
159
|
env?: Record<string, string>;
|
|
160
|
+
browserslist?: string[];
|
|
158
161
|
}
|
|
159
162
|
|
|
160
163
|
export type TSdCliPostPublishConfig = ISdCliPostPublishScriptConfig;
|
|
@@ -1,20 +1,20 @@
|
|
|
1
1
|
import path from "path";
|
|
2
|
-
import {FsUtil, Logger, PathUtil, SdProcess} from "@simplysm/sd-core-node";
|
|
2
|
+
import { FsUtil, Logger, PathUtil, SdProcess } from "@simplysm/sd-core-node";
|
|
3
3
|
import {
|
|
4
4
|
INpmConfig,
|
|
5
5
|
ISdCliBuildClusterResMessage,
|
|
6
6
|
ISdCliConfig,
|
|
7
7
|
ISdCliPackageBuildResult,
|
|
8
8
|
ISdCliServerPackageConfig,
|
|
9
|
-
TSdCliPackageConfig
|
|
9
|
+
TSdCliPackageConfig,
|
|
10
10
|
} from "../commons";
|
|
11
11
|
import cp from "child_process";
|
|
12
|
-
import {fileURLToPath, pathToFileURL} from "url";
|
|
13
|
-
import {SdCliBuildResultUtil} from "../utils/SdCliBuildResultUtil";
|
|
12
|
+
import { fileURLToPath, pathToFileURL } from "url";
|
|
13
|
+
import { SdCliBuildResultUtil } from "../utils/SdCliBuildResultUtil";
|
|
14
14
|
import semver from "semver";
|
|
15
|
-
import {JsonConvert, NeverEntryError, StringUtil, Wait} from "@simplysm/sd-core-common";
|
|
16
|
-
import {SdStorage} from "@simplysm/sd-storage";
|
|
17
|
-
import {SdCliLocalUpdate} from "./SdCliLocalUpdate";
|
|
15
|
+
import { JsonConvert, NeverEntryError, StringUtil, Wait } from "@simplysm/sd-core-common";
|
|
16
|
+
import { SdStorage } from "@simplysm/sd-storage";
|
|
17
|
+
import { SdCliLocalUpdate } from "./SdCliLocalUpdate";
|
|
18
18
|
import xml2js from "xml2js";
|
|
19
19
|
|
|
20
20
|
export class SdCliProject {
|
|
@@ -27,13 +27,16 @@ export class SdCliProject {
|
|
|
27
27
|
const logger = Logger.get(["simplysm", "sd-cli", "SdCliProject", "watchAsync"]);
|
|
28
28
|
|
|
29
29
|
logger.debug("프로젝트 설정 가져오기...");
|
|
30
|
-
const projConf = (await import(pathToFileURL(path.resolve(process.cwd(), opt.confFileRelPath)).href)).default(
|
|
30
|
+
const projConf = (await import(pathToFileURL(path.resolve(process.cwd(), opt.confFileRelPath)).href)).default(
|
|
31
|
+
true,
|
|
32
|
+
opt.optNames,
|
|
33
|
+
) as ISdCliConfig;
|
|
31
34
|
|
|
32
35
|
if (projConf.localUpdates) {
|
|
33
36
|
logger.debug("로컬 라이브러리 업데이트 변경감지 시작...");
|
|
34
37
|
await SdCliLocalUpdate.watchAsync({
|
|
35
38
|
confFileRelPath: opt.confFileRelPath,
|
|
36
|
-
optNames: opt.optNames
|
|
39
|
+
optNames: opt.optNames,
|
|
37
40
|
});
|
|
38
41
|
}
|
|
39
42
|
|
|
@@ -51,7 +54,9 @@ export class SdCliProject {
|
|
|
51
54
|
}
|
|
52
55
|
|
|
53
56
|
logger.debug("패키지 존재 확인...");
|
|
54
|
-
const notExistsPkgs = Object.keys(projConf.packages).filter((pkgConfKey) =>
|
|
57
|
+
const notExistsPkgs = Object.keys(projConf.packages).filter((pkgConfKey) =>
|
|
58
|
+
allPkgPaths.every((pkgPath) => path.basename(pkgPath) !== pkgConfKey),
|
|
59
|
+
);
|
|
55
60
|
if (notExistsPkgs.length > 0) {
|
|
56
61
|
throw new Error("패키지를 찾을 수 없습니다. (" + notExistsPkgs.join(", ") + ")");
|
|
57
62
|
}
|
|
@@ -62,29 +67,31 @@ export class SdCliProject {
|
|
|
62
67
|
logger.debug("빌드 프로세스 이벤트 준비...");
|
|
63
68
|
const resultCache = new Map<string, ISdCliPackageBuildResult[]>();
|
|
64
69
|
let busyReqCntMap = new Map<string, number>();
|
|
65
|
-
const serverInfoMap = new Map<
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
70
|
+
const serverInfoMap = new Map<
|
|
71
|
+
string,
|
|
72
|
+
{
|
|
73
|
+
// server
|
|
74
|
+
pkgOrOpt?: { path: string; conf: ISdCliServerPackageConfig } | { port: number }; // persist
|
|
75
|
+
worker?: cp.ChildProcess; // persist
|
|
76
|
+
port?: number;
|
|
77
|
+
hasChanges: boolean;
|
|
78
|
+
hasClientChanges: boolean;
|
|
79
|
+
|
|
80
|
+
//client
|
|
81
|
+
pathProxy: Record<string, string | number | undefined>; // persist
|
|
82
|
+
// changeFilePaths: string[];
|
|
83
|
+
}
|
|
84
|
+
>();
|
|
77
85
|
cluster.on("message", (message: ISdCliBuildClusterResMessage) => {
|
|
78
86
|
if (message.type === "change") {
|
|
79
|
-
if (Array.from(busyReqCntMap.values()).every(v => v === 0)) {
|
|
87
|
+
if (Array.from(busyReqCntMap.values()).every((v) => v === 0)) {
|
|
80
88
|
logger.log("빌드를 시작합니다...");
|
|
81
89
|
}
|
|
82
90
|
busyReqCntMap.set(
|
|
83
91
|
message.req.cmd + "|" + message.req.pkgPath,
|
|
84
|
-
(busyReqCntMap.get(message.req.cmd + "|" + message.req.pkgPath) ?? 0) + 1
|
|
92
|
+
(busyReqCntMap.get(message.req.cmd + "|" + message.req.pkgPath) ?? 0) + 1,
|
|
85
93
|
);
|
|
86
|
-
}
|
|
87
|
-
else if (message.type === "complete") {
|
|
94
|
+
} else if (message.type === "complete") {
|
|
88
95
|
resultCache.delete("none");
|
|
89
96
|
for (const affectedFilePath of message.result!.affectedFilePaths) {
|
|
90
97
|
if (PathUtil.isChildPath(affectedFilePath, message.req.pkgPath)) {
|
|
@@ -111,7 +118,7 @@ export class SdCliProject {
|
|
|
111
118
|
const serverPkgConf = projConf.packages[pkgName] as ISdCliServerPackageConfig;
|
|
112
119
|
serverInfo.pkgOrOpt = {
|
|
113
120
|
path: message.req.pkgPath,
|
|
114
|
-
conf: serverPkgConf
|
|
121
|
+
conf: serverPkgConf,
|
|
115
122
|
};
|
|
116
123
|
|
|
117
124
|
serverInfo.hasChanges = true;
|
|
@@ -121,12 +128,15 @@ export class SdCliProject {
|
|
|
121
128
|
const pkgName = path.basename(message.req.pkgPath);
|
|
122
129
|
|
|
123
130
|
if (pkgConf.server !== undefined) {
|
|
124
|
-
const serverInfo = serverInfoMap.getOrCreate(
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
131
|
+
const serverInfo = serverInfoMap.getOrCreate(
|
|
132
|
+
typeof pkgConf.server === "string" ? pkgConf.server : pkgConf.server.port.toString(),
|
|
133
|
+
{
|
|
134
|
+
hasChanges: true,
|
|
135
|
+
hasClientChanges: false,
|
|
136
|
+
pathProxy: {},
|
|
137
|
+
// changeFilePaths: []
|
|
138
|
+
},
|
|
139
|
+
);
|
|
130
140
|
|
|
131
141
|
if (typeof pkgConf.server !== "string") {
|
|
132
142
|
serverInfo.pkgOrOpt = pkgConf.server;
|
|
@@ -137,8 +147,7 @@ export class SdCliProject {
|
|
|
137
147
|
|
|
138
148
|
serverInfo.hasClientChanges = true;
|
|
139
149
|
// serverInfo.worker?.send({type: "broadcastReload"});
|
|
140
|
-
}
|
|
141
|
-
else {
|
|
150
|
+
} else {
|
|
142
151
|
const serverInfo = serverInfoMap.getOrCreate(pkgName, {
|
|
143
152
|
hasChanges: true,
|
|
144
153
|
hasClientChanges: false,
|
|
@@ -156,24 +165,20 @@ export class SdCliProject {
|
|
|
156
165
|
setTimeout(async () => {
|
|
157
166
|
busyReqCntMap.set(
|
|
158
167
|
message.req.cmd + "|" + message.req.pkgPath,
|
|
159
|
-
(busyReqCntMap.get(message.req.cmd + "|" + message.req.pkgPath) ?? 0) - 1
|
|
168
|
+
(busyReqCntMap.get(message.req.cmd + "|" + message.req.pkgPath) ?? 0) - 1,
|
|
160
169
|
);
|
|
161
170
|
logger.debug("남아있는 예약 빌드", busyReqCntMap);
|
|
162
|
-
if (Array.from(busyReqCntMap.values()).every(v => v === 0)) {
|
|
171
|
+
if (Array.from(busyReqCntMap.values()).every((v) => v === 0)) {
|
|
163
172
|
for (const serverPkgNameOrPort of serverInfoMap.keys()) {
|
|
164
173
|
const serverInfo = serverInfoMap.get(serverPkgNameOrPort)!;
|
|
165
174
|
if (serverInfo.pkgOrOpt && serverInfo.hasChanges) {
|
|
166
175
|
logger.debug("서버 재시작...");
|
|
167
176
|
try {
|
|
168
|
-
const restartServerResult = await this._restartServerAsync(
|
|
169
|
-
serverInfo.pkgOrOpt,
|
|
170
|
-
serverInfo.worker
|
|
171
|
-
);
|
|
177
|
+
const restartServerResult = await this._restartServerAsync(serverInfo.pkgOrOpt, serverInfo.worker);
|
|
172
178
|
serverInfo.worker = restartServerResult.worker;
|
|
173
179
|
serverInfo.port = restartServerResult.port;
|
|
174
180
|
serverInfo.hasChanges = false;
|
|
175
|
-
}
|
|
176
|
-
catch (err) {
|
|
181
|
+
} catch (err) {
|
|
177
182
|
logger.error(err);
|
|
178
183
|
}
|
|
179
184
|
}
|
|
@@ -182,12 +187,12 @@ export class SdCliProject {
|
|
|
182
187
|
logger.debug("클라이언트 설정...");
|
|
183
188
|
serverInfo.worker.send({
|
|
184
189
|
type: "setPathProxy",
|
|
185
|
-
pathProxy: serverInfo.pathProxy
|
|
190
|
+
pathProxy: serverInfo.pathProxy,
|
|
186
191
|
});
|
|
187
192
|
|
|
188
193
|
if (serverInfo.hasClientChanges) {
|
|
189
194
|
logger.debug("클라이언트 새로고침...");
|
|
190
|
-
serverInfo.worker.send({type: "broadcastReload"});
|
|
195
|
+
serverInfo.worker.send({ type: "broadcastReload" });
|
|
191
196
|
}
|
|
192
197
|
}
|
|
193
198
|
}
|
|
@@ -198,8 +203,7 @@ export class SdCliProject {
|
|
|
198
203
|
for (const proxyPath of Object.keys(serverInfo.pathProxy)) {
|
|
199
204
|
clientPaths.push(`http://localhost:${serverInfo.port}/${proxyPath}/`);
|
|
200
205
|
}
|
|
201
|
-
}
|
|
202
|
-
else {
|
|
206
|
+
} else {
|
|
203
207
|
clientPaths.push(`http://localhost:${serverInfo.port}/`);
|
|
204
208
|
}
|
|
205
209
|
}
|
|
@@ -215,21 +219,21 @@ export class SdCliProject {
|
|
|
215
219
|
});
|
|
216
220
|
|
|
217
221
|
logger.debug("빌드 프로세스 명령 전송...");
|
|
218
|
-
busyReqCntMap.set(
|
|
219
|
-
"all",
|
|
220
|
-
(busyReqCntMap.get("all") ?? 0) + 1
|
|
221
|
-
);
|
|
222
|
+
busyReqCntMap.set("all", (busyReqCntMap.get("all") ?? 0) + 1);
|
|
222
223
|
logger.log("빌드를 시작합니다...");
|
|
223
224
|
|
|
224
225
|
await pkgPaths.parallelAsync(async (pkgPath) => {
|
|
225
|
-
await this._runCommandAsync(
|
|
226
|
+
await this._runCommandAsync(
|
|
227
|
+
cluster,
|
|
228
|
+
"watch",
|
|
229
|
+
projConf,
|
|
230
|
+
pkgPath,
|
|
231
|
+
opt.inspectNames.includes(path.basename(pkgPath)) ? ["--inspect"] : [],
|
|
232
|
+
);
|
|
226
233
|
});
|
|
227
234
|
|
|
228
|
-
busyReqCntMap.set(
|
|
229
|
-
|
|
230
|
-
(busyReqCntMap.get("all") ?? 0) - 1
|
|
231
|
-
);
|
|
232
|
-
if (Array.from(busyReqCntMap.values()).every(v => v === 0)) {
|
|
235
|
+
busyReqCntMap.set("all", (busyReqCntMap.get("all") ?? 0) - 1);
|
|
236
|
+
if (Array.from(busyReqCntMap.values()).every((v) => v === 0)) {
|
|
233
237
|
const buildResults = Array.from(resultCache.values()).mapMany();
|
|
234
238
|
this._logging(buildResults, logger);
|
|
235
239
|
}
|
|
@@ -243,7 +247,10 @@ export class SdCliProject {
|
|
|
243
247
|
const logger = Logger.get(["simplysm", "sd-cli", "SdCliProject", "buildAsync"]);
|
|
244
248
|
|
|
245
249
|
logger.debug("프로젝트 설정 가져오기...");
|
|
246
|
-
const projConf = (await import(pathToFileURL(path.resolve(process.cwd(), opt.confFileRelPath)).href)).default(
|
|
250
|
+
const projConf = (await import(pathToFileURL(path.resolve(process.cwd(), opt.confFileRelPath)).href)).default(
|
|
251
|
+
false,
|
|
252
|
+
opt.optNames,
|
|
253
|
+
) as ISdCliConfig;
|
|
247
254
|
|
|
248
255
|
logger.debug("프로젝트 package.json 가져오기...");
|
|
249
256
|
const projNpmConf = (await FsUtil.readJsonAsync(path.resolve(process.cwd(), "package.json"))) as INpmConfig;
|
|
@@ -295,7 +302,10 @@ export class SdCliProject {
|
|
|
295
302
|
const logger = Logger.get(["simplysm", "sd-cli", "SdCliProject", "publishAsync"]);
|
|
296
303
|
|
|
297
304
|
logger.debug("프로젝트 설정 가져오기...");
|
|
298
|
-
const projConf = (await import(pathToFileURL(path.resolve(process.cwd(), opt.confFileRelPath)).href)).default(
|
|
305
|
+
const projConf = (await import(pathToFileURL(path.resolve(process.cwd(), opt.confFileRelPath)).href)).default(
|
|
306
|
+
false,
|
|
307
|
+
opt.optNames,
|
|
308
|
+
) as ISdCliConfig;
|
|
299
309
|
|
|
300
310
|
logger.debug("프로젝트 package.json 가져오기...");
|
|
301
311
|
const projNpmConf = (await FsUtil.readJsonAsync(path.resolve(process.cwd(), "package.json"))) as INpmConfig;
|
|
@@ -383,22 +393,19 @@ export class SdCliProject {
|
|
|
383
393
|
return process.env[envName] ?? item;
|
|
384
394
|
});
|
|
385
395
|
await SdProcess.spawnAsync(script);
|
|
386
|
-
}
|
|
387
|
-
else {
|
|
396
|
+
} else {
|
|
388
397
|
throw new NeverEntryError();
|
|
389
398
|
}
|
|
390
399
|
}
|
|
391
400
|
}
|
|
392
401
|
|
|
393
|
-
|
|
394
402
|
logger.info(`모든 배포가 완료되었습니다. (v${projNpmConf.version})`);
|
|
395
403
|
}
|
|
396
404
|
|
|
397
405
|
private static async _publishPkgAsync(pkgPath: string, pkgPubConf: TSdCliPackageConfig["publish"]): Promise<void> {
|
|
398
406
|
if (pkgPubConf === "npm") {
|
|
399
|
-
await SdProcess.spawnAsync("yarn npm publish --access public", {cwd: pkgPath});
|
|
400
|
-
}
|
|
401
|
-
else if (pkgPubConf?.type === "local-directory") {
|
|
407
|
+
await SdProcess.spawnAsync("yarn npm publish --access public", { cwd: pkgPath });
|
|
408
|
+
} else if (pkgPubConf?.type === "local-directory") {
|
|
402
409
|
const pkgNpmConf = (await FsUtil.readJsonAsync(path.resolve(pkgPath, "package.json"))) as INpmConfig;
|
|
403
410
|
|
|
404
411
|
const targetRootPath = pkgPubConf.path.replace(/%([^%]*)%/g, (item) => {
|
|
@@ -414,7 +421,7 @@ export class SdCliProject {
|
|
|
414
421
|
|
|
415
422
|
const filePaths = await FsUtil.globAsync(path.resolve(pkgPath, "dist", "**", "*"), {
|
|
416
423
|
dot: true,
|
|
417
|
-
nodir: true
|
|
424
|
+
nodir: true,
|
|
418
425
|
});
|
|
419
426
|
|
|
420
427
|
await filePaths.parallelAsync(async (filePath) => {
|
|
@@ -422,18 +429,16 @@ export class SdCliProject {
|
|
|
422
429
|
const targetPath = PathUtil.posix(targetRootPath, relativeFilePath);
|
|
423
430
|
await FsUtil.copyAsync(filePath, targetPath);
|
|
424
431
|
});
|
|
425
|
-
}
|
|
426
|
-
else if (pkgPubConf?.type === "ftp" || pkgPubConf?.type === "ftps" || pkgPubConf?.type === "sftp") {
|
|
432
|
+
} else if (pkgPubConf?.type === "ftp" || pkgPubConf?.type === "ftps" || pkgPubConf?.type === "sftp") {
|
|
427
433
|
const ftp = await SdStorage.connectAsync(pkgPubConf.type, {
|
|
428
434
|
host: pkgPubConf.host,
|
|
429
435
|
port: pkgPubConf.port,
|
|
430
436
|
user: pkgPubConf.user,
|
|
431
|
-
pass: pkgPubConf.pass
|
|
437
|
+
pass: pkgPubConf.pass,
|
|
432
438
|
});
|
|
433
439
|
await ftp.uploadDirAsync(path.resolve(pkgPath, "dist"), pkgPubConf.path ?? "/");
|
|
434
440
|
await ftp.closeAsync();
|
|
435
|
-
}
|
|
436
|
-
else {
|
|
441
|
+
} else {
|
|
437
442
|
throw new NeverEntryError();
|
|
438
443
|
}
|
|
439
444
|
}
|
|
@@ -475,7 +480,7 @@ export class SdCliProject {
|
|
|
475
480
|
updateDepVersion(projNpmConf.peerDependencies);
|
|
476
481
|
|
|
477
482
|
const projNpmConfFilePath = path.resolve(process.cwd(), "package.json");
|
|
478
|
-
await FsUtil.writeJsonAsync(projNpmConfFilePath, projNpmConf, {space: 2});
|
|
483
|
+
await FsUtil.writeJsonAsync(projNpmConfFilePath, projNpmConf, { space: 2 });
|
|
479
484
|
|
|
480
485
|
// 각 패키지 package.json 버전 설정
|
|
481
486
|
await allPkgPaths.parallelAsync(async (pkgPath) => {
|
|
@@ -488,11 +493,13 @@ export class SdCliProject {
|
|
|
488
493
|
updateDepVersion(pkgNpmConf.devDependencies);
|
|
489
494
|
updateDepVersion(pkgNpmConf.peerDependencies);
|
|
490
495
|
|
|
491
|
-
await FsUtil.writeJsonAsync(pkgNpmConfFilePath, pkgNpmConf, {space: 2});
|
|
496
|
+
await FsUtil.writeJsonAsync(pkgNpmConfFilePath, pkgNpmConf, { space: 2 });
|
|
492
497
|
|
|
493
498
|
if (FsUtil.exists(path.resolve(pkgPath, "plugin.xml"))) {
|
|
494
499
|
const cordovaPluginConfFilePath = path.resolve(pkgPath, "plugin.xml");
|
|
495
|
-
const cordovaPluginConfXml = await xml2js.parseStringPromise(
|
|
500
|
+
const cordovaPluginConfXml = await xml2js.parseStringPromise(
|
|
501
|
+
await FsUtil.readFileAsync(cordovaPluginConfFilePath),
|
|
502
|
+
);
|
|
496
503
|
cordovaPluginConfXml.plugin.$.version = newVersion;
|
|
497
504
|
|
|
498
505
|
await FsUtil.writeFileAsync(cordovaPluginConfFilePath, new xml2js.Builder().buildObject(cordovaPluginConfXml));
|
|
@@ -501,7 +508,10 @@ export class SdCliProject {
|
|
|
501
508
|
}
|
|
502
509
|
|
|
503
510
|
private static _logging(buildResults: ISdCliPackageBuildResult[], logger: Logger): void {
|
|
504
|
-
const messageMap = buildResults.toSetMap(
|
|
511
|
+
const messageMap = buildResults.toSetMap(
|
|
512
|
+
(item) => item.severity,
|
|
513
|
+
(item) => SdCliBuildResultUtil.getMessage(item),
|
|
514
|
+
);
|
|
505
515
|
|
|
506
516
|
if (messageMap.has("message")) {
|
|
507
517
|
logger.log(`알림\n${[...messageMap.get("message")!].join("\n")}`);
|
|
@@ -523,17 +533,13 @@ export class SdCliProject {
|
|
|
523
533
|
private static async _prepareClusterAsync(): Promise<cp.ChildProcess> {
|
|
524
534
|
const logger = Logger.get(["simplysm", "sd-cli", "SdCliProject", "_runBuildClusterAsync"]);
|
|
525
535
|
return await new Promise<cp.ChildProcess>((resolve, reject) => {
|
|
526
|
-
const cluster = cp.fork(
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
// "NG_BUILD_PARALLEL_TS": "0"
|
|
534
|
-
}
|
|
535
|
-
}
|
|
536
|
-
);
|
|
536
|
+
const cluster = cp.fork(fileURLToPath(import.meta.resolve("../build-cluster")), [], {
|
|
537
|
+
stdio: ["pipe", "pipe", "pipe", "ipc"],
|
|
538
|
+
env: {
|
|
539
|
+
...process.env,
|
|
540
|
+
// "NG_BUILD_PARALLEL_TS": "0"
|
|
541
|
+
},
|
|
542
|
+
});
|
|
537
543
|
|
|
538
544
|
cluster.stdout!.pipe(process.stdout);
|
|
539
545
|
cluster.stderr!.pipe(process.stderr);
|
|
@@ -561,16 +567,37 @@ export class SdCliProject {
|
|
|
561
567
|
});
|
|
562
568
|
}
|
|
563
569
|
|
|
564
|
-
private static async _runCommandAsync(
|
|
565
|
-
|
|
566
|
-
|
|
570
|
+
private static async _runCommandAsync(
|
|
571
|
+
cluster: cp.ChildProcess,
|
|
572
|
+
cmd: "watch",
|
|
573
|
+
projConf: ISdCliConfig,
|
|
574
|
+
pkgPath: string,
|
|
575
|
+
execArgs: string[],
|
|
576
|
+
): Promise<void>;
|
|
577
|
+
private static async _runCommandAsync(
|
|
578
|
+
cluster: cp.ChildProcess,
|
|
579
|
+
cmd: "build",
|
|
580
|
+
projConf: ISdCliConfig,
|
|
581
|
+
pkgPath: string,
|
|
582
|
+
): Promise<ISdCliPackageBuildResult[]>;
|
|
583
|
+
private static async _runCommandAsync(
|
|
584
|
+
cluster: cp.ChildProcess,
|
|
585
|
+
cmd: "watch" | "build",
|
|
586
|
+
projConf: ISdCliConfig,
|
|
587
|
+
pkgPath: string,
|
|
588
|
+
execArgs?: string[],
|
|
589
|
+
): Promise<ISdCliPackageBuildResult[] | void> {
|
|
567
590
|
return await new Promise<ISdCliPackageBuildResult[] | void>((resolve) => {
|
|
568
591
|
const cb = (message: ISdCliBuildClusterResMessage): void => {
|
|
569
592
|
if (cmd === "watch" && message.type === "ready" && message.req.cmd === cmd && message.req.pkgPath === pkgPath) {
|
|
570
593
|
cluster.off("message", cb);
|
|
571
594
|
resolve();
|
|
572
|
-
}
|
|
573
|
-
|
|
595
|
+
} else if (
|
|
596
|
+
cmd === "build" &&
|
|
597
|
+
message.type === "complete" &&
|
|
598
|
+
message.req.cmd === cmd &&
|
|
599
|
+
message.req.pkgPath === pkgPath
|
|
600
|
+
) {
|
|
574
601
|
cluster.off("message", cb);
|
|
575
602
|
resolve(message.result?.buildResults);
|
|
576
603
|
}
|
|
@@ -581,7 +608,7 @@ export class SdCliProject {
|
|
|
581
608
|
cmd,
|
|
582
609
|
projConf,
|
|
583
610
|
pkgPath,
|
|
584
|
-
execArgs
|
|
611
|
+
execArgs,
|
|
585
612
|
});
|
|
586
613
|
});
|
|
587
614
|
}
|
|
@@ -590,11 +617,16 @@ export class SdCliProject {
|
|
|
590
617
|
cluster.kill("SIGKILL");
|
|
591
618
|
}
|
|
592
619
|
|
|
593
|
-
private static async _restartServerAsync(
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
620
|
+
private static async _restartServerAsync(
|
|
621
|
+
pkgOrOpt:
|
|
622
|
+
| { path: string; conf: ISdCliServerPackageConfig }
|
|
623
|
+
| {
|
|
624
|
+
port: number;
|
|
625
|
+
},
|
|
626
|
+
prevServerProcess?: cp.ChildProcess,
|
|
627
|
+
): Promise<{
|
|
628
|
+
worker: cp.ChildProcess;
|
|
629
|
+
port: number;
|
|
598
630
|
}> {
|
|
599
631
|
const logger = Logger.get(["simplysm", "sd-cli", "SdCliProject", "_restartServerAsync"]);
|
|
600
632
|
|
|
@@ -602,11 +634,14 @@ export class SdCliProject {
|
|
|
602
634
|
prevServerProcess.kill("SIGKILL");
|
|
603
635
|
}
|
|
604
636
|
|
|
605
|
-
const npmConf =
|
|
637
|
+
const npmConf =
|
|
638
|
+
"path" in pkgOrOpt
|
|
639
|
+
? ((await FsUtil.readJsonAsync(path.resolve(pkgOrOpt.path, "package.json"))) as INpmConfig)
|
|
640
|
+
: undefined;
|
|
606
641
|
|
|
607
642
|
return await new Promise<{
|
|
608
|
-
worker: cp.ChildProcess
|
|
609
|
-
port: number
|
|
643
|
+
worker: cp.ChildProcess;
|
|
644
|
+
port: number;
|
|
610
645
|
}>((resolve, reject) => {
|
|
611
646
|
const worker = cp.fork(
|
|
612
647
|
fileURLToPath(import.meta.resolve("../server-worker")),
|
|
@@ -618,9 +653,9 @@ export class SdCliProject {
|
|
|
618
653
|
NODE_ENV: "development",
|
|
619
654
|
TZ: "Asia/Seoul",
|
|
620
655
|
SD_VERSION: npmConf?.version ?? "serverless",
|
|
621
|
-
..."path" in pkgOrOpt ? pkgOrOpt.conf.env : {}
|
|
622
|
-
}
|
|
623
|
-
}
|
|
656
|
+
...("path" in pkgOrOpt ? pkgOrOpt.conf.env : {}),
|
|
657
|
+
},
|
|
658
|
+
},
|
|
624
659
|
);
|
|
625
660
|
|
|
626
661
|
worker.stdout!.pipe(process.stdout);
|
|
@@ -645,10 +680,10 @@ export class SdCliProject {
|
|
|
645
680
|
logger.debug("서버가 시작되었습니다.");
|
|
646
681
|
resolve({
|
|
647
682
|
worker,
|
|
648
|
-
port: message.port
|
|
683
|
+
port: message.port,
|
|
649
684
|
});
|
|
650
685
|
}
|
|
651
686
|
});
|
|
652
687
|
});
|
|
653
688
|
}
|
|
654
|
-
}
|
|
689
|
+
}
|