@simplysm/sd-cli 6.0.28 → 6.0.38
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-node/bin/sd-cli.js +19 -4
- package/dist-node/bin/sd-cli.js.map +1 -1
- package/dist-node/build-tools/SdCliNgModuleFilesGenerator.js +106 -57
- package/dist-node/build-tools/SdCliNgModuleFilesGenerator.js.map +1 -1
- package/dist-node/build-tools/metadata/SdAotMetadataReader.js +13 -11
- package/dist-node/build-tools/metadata/SdAotMetadataReader.js.map +1 -1
- package/dist-node/build-tools/metadata/SdIvyMetadataReader.js +23 -6
- package/dist-node/build-tools/metadata/SdIvyMetadataReader.js.map +1 -1
- package/dist-node/build-tools/metadata/SdMetadataError.js +13 -0
- package/dist-node/build-tools/metadata/SdMetadataError.js.map +1 -0
- package/dist-node/build-tools/metadata/SdMyMetadataReader.js +22 -5
- package/dist-node/build-tools/metadata/SdMyMetadataReader.js.map +1 -1
- package/dist-node/builders/SdCliNgClientBuilder.js +74 -74
- package/dist-node/builders/SdCliNgClientBuilder.js.map +1 -1
- package/dist-node/builders/SdCliNgLibraryBuilder.js +49 -45
- package/dist-node/builders/SdCliNgLibraryBuilder.js.map +1 -1
- package/dist-node/builders/SdCliServerBuilder.js +33 -23
- package/dist-node/builders/SdCliServerBuilder.js.map +1 -1
- package/dist-node/builders/SdCliTypescriptBuilder.js +75 -65
- package/dist-node/builders/SdCliTypescriptBuilder.js.map +1 -1
- package/dist-node/entry-points/SdCliProject.js +17 -17
- package/dist-node/entry-points/SdCliProject.js.map +1 -1
- package/dist-node/packages/SdCliClientPackage.js +6 -4
- package/dist-node/packages/SdCliClientPackage.js.map +1 -1
- package/dist-node/packages/SdCliLibraryPackage.js +5 -3
- package/dist-node/packages/SdCliLibraryPackage.js.map +1 -1
- package/dist-node/packages/SdCliServerPackage.js +4 -3
- package/dist-node/packages/SdCliServerPackage.js.map +1 -1
- package/dist-node/utils/SdWebpackUtil.js +33 -13
- package/dist-node/utils/SdWebpackUtil.js.map +1 -1
- package/dist-node/workers/client-ng-gen-worker.js +54 -0
- package/dist-node/workers/client-ng-gen-worker.js.map +1 -0
- package/dist-node/workers/lib-build-worker.js +7 -6
- package/dist-node/workers/lib-build-worker.js.map +1 -1
- package/dist-types/build-tools/metadata/SdIvyMetadataReader.d.ts +1 -0
- package/dist-types/build-tools/metadata/SdMetadataError.d.ts +6 -0
- package/dist-types/build-tools/metadata/SdMyMetadataReader.d.ts +1 -0
- package/dist-types/builders/SdCliNgClientBuilder.d.ts +6 -2
- package/dist-types/builders/SdCliNgLibraryBuilder.d.ts +3 -2
- package/dist-types/builders/SdCliServerBuilder.d.ts +2 -1
- package/dist-types/builders/SdCliTypescriptBuilder.d.ts +5 -5
- package/dist-types/commons.d.ts +4 -1
- package/dist-types/entry-points/SdCliProject.d.ts +5 -1
- package/dist-types/packages/SdCliClientPackage.d.ts +2 -1
- package/dist-types/packages/SdCliLibraryPackage.d.ts +2 -1
- package/dist-types/packages/SdCliServerPackage.d.ts +2 -1
- package/dist-types/utils/SdWebpackUtil.d.ts +1 -1
- package/dist-types/workers/client-ng-gen-worker.d.ts +1 -0
- package/package.json +7 -7
- package/schema/schema.json +72 -1
- package/sd-tsconfig.node.json +2 -1
- package/src/bin/sd-cli.ts +19 -4
- package/src/build-tools/SdCliNgModuleFilesGenerator.ts +122 -70
- package/src/build-tools/metadata/SdAotMetadataReader.ts +4 -1
- package/src/build-tools/metadata/SdIvyMetadataReader.ts +27 -4
- package/src/build-tools/metadata/SdMetadataError.ts +7 -0
- package/src/build-tools/metadata/SdMyMetadataReader.ts +25 -3
- package/src/builders/SdCliNgClientBuilder.ts +123 -66
- package/src/builders/SdCliNgLibraryBuilder.ts +79 -42
- package/src/builders/SdCliServerBuilder.ts +48 -19
- package/src/builders/SdCliTypescriptBuilder.ts +102 -78
- package/src/commons.ts +2 -1
- package/src/entry-points/SdCliProject.ts +22 -14
- package/src/packages/SdCliClientPackage.ts +5 -3
- package/src/packages/SdCliLibraryPackage.ts +4 -2
- package/src/packages/SdCliServerPackage.ts +4 -3
- package/src/utils/SdWebpackUtil.ts +42 -22
- package/src/workers/client-ng-gen-worker.ts +60 -0
- package/src/workers/lib-build-worker.ts +7 -6
- package/tsconfig.json +2 -1
|
@@ -3,18 +3,16 @@ import { INpmConfig, ISdClientPackageConfig, ISdPackageBuildResult, ITsconfig }
|
|
|
3
3
|
import * as webpack from "webpack";
|
|
4
4
|
import * as path from "path";
|
|
5
5
|
import * as ts from "typescript";
|
|
6
|
-
import { FsUtil, PathUtil } from "@simplysm/sd-core-node";
|
|
6
|
+
import { FsUtil, Logger, PathUtil, SdProcessWorker } from "@simplysm/sd-core-node";
|
|
7
7
|
import { JavaScriptOptimizerPlugin } from "@angular-devkit/build-angular/src/webpack/plugins/javascript-optimizer-plugin";
|
|
8
8
|
import * as CssMinimizerPlugin from "css-minimizer-webpack-plugin";
|
|
9
9
|
import * as esbuild from "esbuild";
|
|
10
10
|
import {
|
|
11
|
-
AnyComponentStyleBudgetChecker,
|
|
12
11
|
CommonJsUsageWarnPlugin,
|
|
13
12
|
DedupeModuleResolvePlugin,
|
|
14
13
|
SuppressExtractedTextChunksWebpackPlugin
|
|
15
14
|
} from "@angular-devkit/build-angular/src/webpack/plugins";
|
|
16
15
|
import { LicenseWebpackPlugin } from "license-webpack-plugin";
|
|
17
|
-
import { Type } from "@angular-devkit/build-angular";
|
|
18
16
|
import { SassWorkerImplementation } from "@angular-devkit/build-angular/src/sass/sass-service";
|
|
19
17
|
import * as MiniCssExtractPlugin from "mini-css-extract-plugin";
|
|
20
18
|
import { AngularWebpackPlugin } from "@ngtools/webpack";
|
|
@@ -28,7 +26,6 @@ import { StringUtil, Wait } from "@simplysm/sd-core-common";
|
|
|
28
26
|
import { augmentAppWithServiceWorker } from "@angular-devkit/build-angular/src/utils/service-worker";
|
|
29
27
|
import * as browserslist from "browserslist";
|
|
30
28
|
import * as WebpackHotMiddleware from "webpack-hot-middleware";
|
|
31
|
-
import { SdCliNgLibraryBuilder } from "./SdCliNgLibraryBuilder";
|
|
32
29
|
import * as os from "os";
|
|
33
30
|
import { LintResult } from "eslint-webpack-plugin/declarations/options";
|
|
34
31
|
|
|
@@ -39,23 +36,23 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
39
36
|
public parsedTsconfig: ts.ParsedCommandLine;
|
|
40
37
|
public readonly npmConfig: INpmConfig;
|
|
41
38
|
|
|
39
|
+
private _ngGenWorker?: SdProcessWorker;
|
|
40
|
+
|
|
41
|
+
protected readonly _logger: Logger;
|
|
42
|
+
|
|
42
43
|
public constructor(public rootPath: string,
|
|
43
44
|
public tsconfigFilePath: string,
|
|
44
45
|
public projectRootPath: string,
|
|
45
|
-
public config: ISdClientPackageConfig
|
|
46
|
+
public config: ISdClientPackageConfig,
|
|
47
|
+
public useCache: boolean) {
|
|
46
48
|
super();
|
|
47
49
|
|
|
48
50
|
const tsconfig: ITsconfig = FsUtil.readJson(this.tsconfigFilePath);
|
|
49
|
-
|
|
50
|
-
this.parsedTsconfig = {
|
|
51
|
-
...parsedTsconfig,
|
|
52
|
-
options: {
|
|
53
|
-
...parsedTsconfig.options,
|
|
54
|
-
...tsconfig.angularCompilerOptions
|
|
55
|
-
}
|
|
56
|
-
};
|
|
51
|
+
this.parsedTsconfig = ts.parseJsonConfigFileContent(tsconfig, ts.sys, this.rootPath, tsconfig.angularCompilerOptions);
|
|
57
52
|
|
|
58
53
|
this.npmConfig = FsUtil.readJson(path.resolve(this.rootPath, "package.json"));
|
|
54
|
+
|
|
55
|
+
this._logger = Logger.get(["simplysm", "sd-cli", this.constructor.name, this.npmConfig.name]);
|
|
59
56
|
}
|
|
60
57
|
|
|
61
58
|
public on(event: "change", listener: () => void): this;
|
|
@@ -72,12 +69,16 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
72
69
|
const buildResult: ISdPackageBuildResult[] = [];
|
|
73
70
|
|
|
74
71
|
// GENERATOR
|
|
75
|
-
|
|
76
|
-
const
|
|
77
|
-
const
|
|
72
|
+
this._logger.debug("NgGen 수행");
|
|
73
|
+
const genResult = await this._runNgGenWorkerAsync(false);
|
|
74
|
+
// const ngGenerator = new SdCliNgLibraryBuilder(this.rootPath, this.tsconfigFilePath, ["emit", "check", "lint"], undefined);
|
|
75
|
+
// const genFilePaths = await ngGenerator.reloadProgramAsync(false);
|
|
76
|
+
// const genResult = await ngGenerator.generateAdditionalFilesAsync(genFilePaths, false);
|
|
78
77
|
buildResult.push(...genResult.result);
|
|
78
|
+
this._logger.debug("NgGen 수행 결과", genResult);
|
|
79
79
|
|
|
80
80
|
// WEBPACK 빌드
|
|
81
|
+
this._logger.debug("Webpack 빌드 수행");
|
|
81
82
|
const webpackConfig = this._getWebpackConfig(false);
|
|
82
83
|
const compiler = webpack(webpackConfig);
|
|
83
84
|
const webpackBuildResults = await new Promise<ISdPackageBuildResult[]>((resolve, reject) => {
|
|
@@ -91,6 +92,7 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
91
92
|
resolve(results);
|
|
92
93
|
});
|
|
93
94
|
});
|
|
95
|
+
this._logger.debug("Webpack 빌드 결과", webpackBuildResults);
|
|
94
96
|
buildResult.push(...webpackBuildResults);
|
|
95
97
|
|
|
96
98
|
// .config.json 파일 쓰기
|
|
@@ -100,14 +102,16 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
100
102
|
|
|
101
103
|
// service-worker 처리
|
|
102
104
|
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
105
|
+
if (FsUtil.exists(path.resolve(this.rootPath, "ngsw-config.json"))) {
|
|
106
|
+
const packageKey = this.npmConfig.name.split("/").last()!;
|
|
107
|
+
await augmentAppWithServiceWorker(
|
|
108
|
+
PathUtil.posix(this.projectRootPath) as any,
|
|
109
|
+
PathUtil.posix(path.relative(this.projectRootPath, this.rootPath)) as any,
|
|
110
|
+
PathUtil.posix(path.relative(this.projectRootPath, this.parsedTsconfig.options.outDir!)) as any,
|
|
111
|
+
`/${packageKey}/`,
|
|
112
|
+
PathUtil.posix(path.relative(this.projectRootPath, path.resolve(this.rootPath, "ngsw-config.json")))
|
|
113
|
+
);
|
|
114
|
+
}
|
|
111
115
|
|
|
112
116
|
this.emit("complete", buildResult.distinct());
|
|
113
117
|
}
|
|
@@ -115,66 +119,73 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
115
119
|
public async watchAsync(serverPath?: string): Promise<NextHandleFunction[]> {
|
|
116
120
|
await FsUtil.removeAsync(this.parsedTsconfig.options.outDir!);
|
|
117
121
|
|
|
118
|
-
let
|
|
122
|
+
let ngGenResults: ISdPackageBuildResult[] = [];
|
|
119
123
|
|
|
120
|
-
const ngGenerator = new SdCliNgLibraryBuilder(this.rootPath, this.tsconfigFilePath, ["emit", "check", "lint"], undefined);
|
|
124
|
+
// const ngGenerator = new SdCliNgLibraryBuilder(this.rootPath, this.tsconfigFilePath, ["emit", "check", "lint", "genIndex"], undefined);
|
|
121
125
|
|
|
122
126
|
// WEBPACK 빌드
|
|
127
|
+
let invalidFiles = new Set<string>();
|
|
123
128
|
const webpackConfig = this._getWebpackConfig(true);
|
|
124
129
|
const compiler = webpack(webpackConfig);
|
|
125
130
|
return await new Promise<NextHandleFunction[]>((resolve, reject) => {
|
|
131
|
+
compiler.hooks.invalid.tap(this.constructor.name, (fileName) => {
|
|
132
|
+
if (fileName != null) {
|
|
133
|
+
invalidFiles.add(fileName);
|
|
134
|
+
}
|
|
135
|
+
});
|
|
136
|
+
|
|
126
137
|
compiler.hooks.watchRun.tapAsync(this.constructor.name, async (compiler1, callback) => {
|
|
127
138
|
this.emit("change");
|
|
128
139
|
|
|
129
|
-
|
|
140
|
+
ngGenResults = [];
|
|
130
141
|
|
|
131
142
|
// -- FIRST
|
|
132
143
|
|
|
133
144
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition,@typescript-eslint/strict-boolean-expressions
|
|
134
|
-
if (
|
|
135
|
-
|
|
136
|
-
const genResult = await
|
|
137
|
-
|
|
138
|
-
|
|
145
|
+
if (invalidFiles.size === 0) {
|
|
146
|
+
this._logger.debug("첫 NgGen 수행");
|
|
147
|
+
const genResult = await this._runNgGenWorkerAsync(true);
|
|
148
|
+
// const genDirtyFilePaths = await ngGenerator.reloadProgramAsync(true);
|
|
149
|
+
// const genResult = await ngGenerator.generateAdditionalFilesAsync(genDirtyFilePaths, true);
|
|
150
|
+
ngGenResults.push(...genResult.result);
|
|
151
|
+
this._logger.debug("첫 NgGen 수행 결과", genResult);
|
|
152
|
+
|
|
153
|
+
this._logger.debug("Webpack 빌드 수행");
|
|
139
154
|
callback();
|
|
140
155
|
}
|
|
141
156
|
|
|
142
157
|
// -- NOT FIRST
|
|
143
|
-
|
|
144
158
|
else {
|
|
145
|
-
const changedFiles = [...compiler.modifiedFiles, ...compiler.removedFiles];
|
|
146
|
-
|
|
147
159
|
// 변경파일 중, 유효한 파일 추출
|
|
148
|
-
const
|
|
160
|
+
const changedFiles = [...invalidFiles];
|
|
161
|
+
invalidFiles = new Set<string>();
|
|
162
|
+
|
|
149
163
|
const changedFilePaths = changedFiles
|
|
150
164
|
.map((item) => PathUtil.posix(item))
|
|
151
165
|
.filter((item) => path.basename(item).includes("."))
|
|
152
|
-
.filter((item) => watchPaths.includes(path.dirname(item)))
|
|
153
166
|
.distinct();
|
|
154
167
|
if (changedFilePaths.length === 0) {
|
|
168
|
+
this._logger.debug("Webpack 빌드 수행");
|
|
155
169
|
callback();
|
|
156
170
|
return;
|
|
157
171
|
}
|
|
158
172
|
|
|
159
|
-
|
|
160
|
-
const genDirtyFilePaths = await ngGenerator.reloadChangedProgramAsync(changedFilePaths, true);
|
|
161
|
-
if (genDirtyFilePaths.length === 0) {
|
|
162
|
-
callback();
|
|
163
|
-
return;
|
|
164
|
-
}
|
|
173
|
+
this._logger.debug("변경파일에 대한, NgGen 수행", changedFilePaths);
|
|
165
174
|
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
buildResult.push(...genResult.result);
|
|
175
|
+
const genResult = await this._runNgGenWorkerAsync(true, changedFilePaths);
|
|
176
|
+
ngGenResults.push(...genResult.result);
|
|
169
177
|
if (genResult.dirtyFilePaths.length === 0) {
|
|
178
|
+
this._logger.debug("변경파일에 대한, NgGen 결과", genResult);
|
|
179
|
+
this._logger.debug("Webpack 빌드 수행");
|
|
170
180
|
callback();
|
|
171
181
|
return;
|
|
172
182
|
}
|
|
173
|
-
|
|
183
|
+
|
|
184
|
+
this._logger.debug("변경파일에 대한, NgGen 결과", genResult);
|
|
174
185
|
|
|
175
186
|
const modifiedFiles = [...compiler.modifiedFiles];
|
|
176
187
|
const removedFiles = [...compiler.removedFiles];
|
|
177
|
-
for (const genFilePath of
|
|
188
|
+
for (const genFilePath of genResult.dirtyFilePaths.distinct()) {
|
|
178
189
|
if (FsUtil.exists(genFilePath)) {
|
|
179
190
|
modifiedFiles.push(genFilePath);
|
|
180
191
|
}
|
|
@@ -185,6 +196,7 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
185
196
|
compiler.modifiedFiles = new Set(modifiedFiles.distinct());
|
|
186
197
|
compiler.removedFiles = new Set(removedFiles.distinct());
|
|
187
198
|
|
|
199
|
+
this._logger.debug("Webpack 빌드 수행");
|
|
188
200
|
callback();
|
|
189
201
|
}
|
|
190
202
|
});
|
|
@@ -196,7 +208,9 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
196
208
|
|
|
197
209
|
compiler.hooks.failed.tap(this.constructor.name, (err) => {
|
|
198
210
|
const results = SdWebpackUtil.getWebpackResults(err);
|
|
199
|
-
|
|
211
|
+
const allResults = [...ngGenResults, ...results].distinct();
|
|
212
|
+
this.emit("complete", allResults);
|
|
213
|
+
this._logger.debug("Webpack 빌드 수행 결과", allResults);
|
|
200
214
|
reject(err);
|
|
201
215
|
});
|
|
202
216
|
|
|
@@ -212,7 +226,9 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
212
226
|
|
|
213
227
|
|
|
214
228
|
await Wait.true(() => devMiddleware !== undefined && hotMiddleware !== undefined);
|
|
215
|
-
|
|
229
|
+
const allResults = [...ngGenResults, ...results].distinct();
|
|
230
|
+
this.emit("complete", allResults);
|
|
231
|
+
this._logger.debug("Webpack 빌드 수행 결과", allResults);
|
|
216
232
|
resolve([devMiddleware!, hotMiddleware!]);
|
|
217
233
|
});
|
|
218
234
|
|
|
@@ -242,19 +258,16 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
242
258
|
profile: false,
|
|
243
259
|
resolve: {
|
|
244
260
|
roots: [this.rootPath],
|
|
245
|
-
extensions: [".ts", ".
|
|
261
|
+
extensions: [".ts", ".js"],
|
|
246
262
|
symlinks: true,
|
|
247
|
-
modules:
|
|
263
|
+
// modules: allNodeModulePaths,
|
|
248
264
|
mainFields: ["es2015", "browser", "module", "main"],
|
|
249
265
|
fallback: this.config.resolveFallback
|
|
250
266
|
},
|
|
251
|
-
resolveLoader: {
|
|
267
|
+
/*resolveLoader: {
|
|
252
268
|
symlinks: true,
|
|
253
|
-
modules:
|
|
254
|
-
|
|
255
|
-
...this._findAllNodeModules(__dirname, this.projectRootPath)
|
|
256
|
-
]
|
|
257
|
-
},
|
|
269
|
+
modules: allNodeModulePaths
|
|
270
|
+
},*/
|
|
258
271
|
context: this.projectRootPath,
|
|
259
272
|
entry: {
|
|
260
273
|
main: [
|
|
@@ -278,6 +291,7 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
278
291
|
// chunkFilename: watch ? "[name].js" : "[name].[chunkhash:20].js",
|
|
279
292
|
filename: "[name].js",
|
|
280
293
|
chunkFilename: "[name].js",
|
|
294
|
+
assetModuleFilename: "resources/[name][ext][query]",
|
|
281
295
|
crossOriginLoading: false,
|
|
282
296
|
trustedTypes: "angular#bundler"
|
|
283
297
|
},
|
|
@@ -377,18 +391,22 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
377
391
|
{
|
|
378
392
|
test: /\.[jt]sx?$/,
|
|
379
393
|
loader: "@ngtools/webpack"
|
|
394
|
+
},
|
|
395
|
+
{
|
|
396
|
+
test: /\.(png|jpe?g|gif|svg|woff|woff2|ttf|eot|ico|otf|xlsx?|pptx?|docx?|zip|pfx|pkl)$/,
|
|
397
|
+
type: "asset/resource"
|
|
380
398
|
}
|
|
381
399
|
]
|
|
382
400
|
},
|
|
383
401
|
experiments: { syncWebAssembly: true, asyncWebAssembly: true },
|
|
384
|
-
cache: watch ? { type: "memory", maxGenerations: 1 } : false,
|
|
402
|
+
cache: (watch && this.useCache) ? { type: "memory", maxGenerations: 1 } : false,
|
|
385
403
|
optimization: {
|
|
386
404
|
minimizer: watch ? [] : [
|
|
387
405
|
new JavaScriptOptimizerPlugin({
|
|
388
406
|
define: { ngDevMode: false, ngI18nClosureMode: false, ngJitMode: false },
|
|
389
407
|
sourcemap: false,
|
|
390
408
|
target: this.parsedTsconfig.options.target,
|
|
391
|
-
keepNames:
|
|
409
|
+
keepNames: true,
|
|
392
410
|
removeLicenses: true,
|
|
393
411
|
advanced: true
|
|
394
412
|
}) as any,
|
|
@@ -403,9 +421,9 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
403
421
|
minify: true,
|
|
404
422
|
sourcefile,
|
|
405
423
|
target: browserslist([
|
|
406
|
-
"last
|
|
424
|
+
"last 1 Chrome versions",
|
|
407
425
|
"last 2 Edge major versions"
|
|
408
|
-
])
|
|
426
|
+
]).map((item) => item.replace(/ /g, ""))
|
|
409
427
|
});
|
|
410
428
|
|
|
411
429
|
return {
|
|
@@ -437,7 +455,7 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
437
455
|
],
|
|
438
456
|
moduleIds: "deterministic",
|
|
439
457
|
chunkIds: watch ? "named" : "deterministic",
|
|
440
|
-
emitOnErrors:
|
|
458
|
+
emitOnErrors: watch,
|
|
441
459
|
runtimeChunk: "single",
|
|
442
460
|
splitChunks: {
|
|
443
461
|
maxAsyncRequests: Infinity,
|
|
@@ -504,13 +522,13 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
504
522
|
append: undefined
|
|
505
523
|
})
|
|
506
524
|
] : [],
|
|
507
|
-
new AnyComponentStyleBudgetChecker(watch ? [] : [
|
|
525
|
+
/*new AnyComponentStyleBudgetChecker(watch ? [] : [
|
|
508
526
|
{
|
|
509
527
|
type: Type.Any,
|
|
510
528
|
maximumWarning: "2kb",
|
|
511
529
|
maximumError: "4kb"
|
|
512
530
|
}
|
|
513
|
-
])
|
|
531
|
+
]),*/
|
|
514
532
|
{
|
|
515
533
|
apply(compiler) {
|
|
516
534
|
compiler.hooks.shutdown.tap("sass-worker", () => {
|
|
@@ -584,13 +602,37 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
584
602
|
}),
|
|
585
603
|
...watch ? [
|
|
586
604
|
new webpack.HotModuleReplacementPlugin()
|
|
587
|
-
] : []
|
|
605
|
+
] : [],
|
|
606
|
+
/*...watch ? [
|
|
607
|
+
new webpack.WatchIgnorePlugin({
|
|
608
|
+
paths: [
|
|
609
|
+
path.resolve(this.rootPath, "src/_modules/"),
|
|
610
|
+
path.resolve(this.rootPath, "src/_routes.ts")
|
|
611
|
+
]
|
|
612
|
+
})
|
|
613
|
+
] : [],*/
|
|
614
|
+
new webpack.ProgressPlugin({
|
|
615
|
+
handler: (per: number, msg: string, ...args: string[]) => {
|
|
616
|
+
const phaseText = msg ? ` - phase: ${msg}` : "";
|
|
617
|
+
const argsText = args.length > 0 ? ` - args: [${args.join(", ")}]` : "";
|
|
618
|
+
this._logger.debug(`Webpack 빌드 수행중...(${Math.round(per * 100)}%)${phaseText}${argsText}`);
|
|
619
|
+
}
|
|
620
|
+
})
|
|
588
621
|
],
|
|
589
622
|
node: false,
|
|
590
623
|
stats: "errors-warnings"
|
|
591
624
|
};
|
|
592
625
|
}
|
|
593
626
|
|
|
627
|
+
/*private _findAllInternalModuleCachePaths(): string[] {
|
|
628
|
+
return this._findAllNodeModules(this.rootPath, this.projectRootPath)
|
|
629
|
+
.mapMany((item) => (
|
|
630
|
+
FsUtil.readdir(item)
|
|
631
|
+
.filter((item1) => !item1.startsWith("@simplysm"))
|
|
632
|
+
.map((item1) => path.resolve(item, item1))
|
|
633
|
+
));
|
|
634
|
+
}
|
|
635
|
+
|
|
594
636
|
private _findAllNodeModules(from: string, root: string): string[] {
|
|
595
637
|
const nodeModules: string[] = [];
|
|
596
638
|
|
|
@@ -609,5 +651,20 @@ export class SdCliNgClientBuilder extends EventEmitter {
|
|
|
609
651
|
}
|
|
610
652
|
|
|
611
653
|
return nodeModules;
|
|
654
|
+
}*/
|
|
655
|
+
|
|
656
|
+
private async _runNgGenWorkerAsync(watch: boolean, changedFilePaths?: string[]): Promise<{ dirtyFilePaths: string[]; result: ISdPackageBuildResult[] }> {
|
|
657
|
+
if (!this._ngGenWorker) {
|
|
658
|
+
this._ngGenWorker = await SdProcessWorker.createAsync(path.resolve(__dirname, `../workers/client-ng-gen-worker`), []);
|
|
659
|
+
}
|
|
660
|
+
|
|
661
|
+
const sender = this._ngGenWorker.createWorkSender();
|
|
662
|
+
return await new Promise<{ dirtyFilePaths: string[]; result: ISdPackageBuildResult[] }>(async (resolve) => {
|
|
663
|
+
await sender
|
|
664
|
+
.on("complete", (result) => {
|
|
665
|
+
resolve(result);
|
|
666
|
+
})
|
|
667
|
+
.sendAsync(this.rootPath, watch, changedFilePaths);
|
|
668
|
+
});
|
|
612
669
|
}
|
|
613
670
|
}
|
|
@@ -1,22 +1,22 @@
|
|
|
1
1
|
import * as ts from "typescript";
|
|
2
|
-
import { ISdAutoIndexConfig, ISdPackageBuildResult
|
|
2
|
+
import { ISdAutoIndexConfig, ISdPackageBuildResult } from "../commons";
|
|
3
3
|
import * as path from "path";
|
|
4
4
|
import { SdTsDiagnosticUtil } from "../utils/SdTsDiagnosticUtil";
|
|
5
5
|
import { NgccProcessingCache } from "ng-packagr/lib/ng-package/ngcc-cache";
|
|
6
6
|
import { NgccProcessor } from "ng-packagr/lib/ngc/ngcc-processor";
|
|
7
7
|
import { EntryPointNode } from "ng-packagr/lib/ng-package/nodes";
|
|
8
8
|
import { ngccTransformCompilerHost } from "ng-packagr/lib/ts/ngcc-transform-compiler-host";
|
|
9
|
-
import { NgtscProgram } from "@angular/compiler-cli";
|
|
9
|
+
import { MetadataCollector, NgtscProgram } from "@angular/compiler-cli";
|
|
10
10
|
import { ITsBuildFileCache, ITsGenResult, SdCliTypescriptBuilder } from "./SdCliTypescriptBuilder";
|
|
11
11
|
import { NgCompiler } from "@angular/compiler-cli/src/ngtsc/core";
|
|
12
12
|
import { NeverEntryError, StringUtil } from "@simplysm/sd-core-common";
|
|
13
|
-
import {
|
|
13
|
+
import { PathUtil } from "@simplysm/sd-core-node";
|
|
14
14
|
import * as os from "os";
|
|
15
15
|
import * as nodeSass from "node-sass";
|
|
16
16
|
import { createHash } from "crypto";
|
|
17
17
|
import { SdCliNgModuleFilesGenerator } from "../build-tools/SdCliNgModuleFilesGenerator";
|
|
18
18
|
import { OptimizeFor } from "@angular/compiler-cli/src/ngtsc/typecheck/api";
|
|
19
|
-
import {
|
|
19
|
+
import { ModuleMetadata } from "@angular/compiler-cli/src/metadata/schema";
|
|
20
20
|
|
|
21
21
|
export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
22
22
|
protected _ngProgram?: NgtscProgram;
|
|
@@ -29,20 +29,10 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
29
29
|
|
|
30
30
|
public constructor(public rootPath: string,
|
|
31
31
|
public tsconfigFilePath: string,
|
|
32
|
-
|
|
32
|
+
skipProcesses: ("emit" | "check" | "lint" | "genIndex" | "genNgModule")[],
|
|
33
33
|
public autoIndexConfig: ISdAutoIndexConfig | undefined) {
|
|
34
|
-
super(rootPath, tsconfigFilePath,
|
|
35
|
-
this.
|
|
36
|
-
|
|
37
|
-
const tsconfig: ITsconfig = FsUtil.readJson(this.tsconfigFilePath);
|
|
38
|
-
this._parsedTsconfig = {
|
|
39
|
-
...this._parsedTsconfig,
|
|
40
|
-
options: {
|
|
41
|
-
baseUrl: path.dirname(this.tsconfigFilePath),
|
|
42
|
-
...this._parsedTsconfig.options,
|
|
43
|
-
...tsconfig.angularCompilerOptions
|
|
44
|
-
}
|
|
45
|
-
};
|
|
34
|
+
super(rootPath, tsconfigFilePath, skipProcesses as ("emit" | "check" | "lint" | "genIndex")[], autoIndexConfig);
|
|
35
|
+
this.skipProcesses = skipProcesses;
|
|
46
36
|
}
|
|
47
37
|
|
|
48
38
|
protected override async _runProgramAsync(dirtyFilePaths: string[]): Promise<ISdPackageBuildResult[]> {
|
|
@@ -53,7 +43,7 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
53
43
|
|
|
54
44
|
const diagnostics: ts.Diagnostic[] = [];
|
|
55
45
|
|
|
56
|
-
if (!this.
|
|
46
|
+
if (!this.skipProcesses.includes("check")) {
|
|
57
47
|
diagnostics.push(
|
|
58
48
|
...this._ngCompiler.getOptionDiagnostics(),
|
|
59
49
|
...this._builder.getOptionsDiagnostics(),
|
|
@@ -62,9 +52,10 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
62
52
|
|
|
63
53
|
await this._ngCompiler.analyzeAsync();
|
|
64
54
|
|
|
65
|
-
for (const
|
|
66
|
-
const
|
|
67
|
-
|
|
55
|
+
for (const sourceFile of this._builder.getSourceFiles()) {
|
|
56
|
+
/*for (const filePath of dirtyFilePaths) {
|
|
57
|
+
const sourceFile = this._builder.getSourceFile(filePath);
|
|
58
|
+
if (!sourceFile) continue;*/
|
|
68
59
|
|
|
69
60
|
if (this._ngCompiler.ignoreForDiagnostics.has(sourceFile)) continue;
|
|
70
61
|
if (sourceFile.isDeclarationFile) continue;
|
|
@@ -77,7 +68,7 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
77
68
|
}
|
|
78
69
|
}
|
|
79
70
|
|
|
80
|
-
if (!this.
|
|
71
|
+
if (!this.skipProcesses.includes("emit")) {
|
|
81
72
|
const transformers = this._ngCompiler.prepareEmit().transformers;
|
|
82
73
|
|
|
83
74
|
for (const filePath of dirtyFilePaths) {
|
|
@@ -87,11 +78,21 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
87
78
|
if (sourceFile.isDeclarationFile) continue;
|
|
88
79
|
|
|
89
80
|
this._builder.emit(sourceFile, undefined, undefined, undefined, transformers);
|
|
81
|
+
|
|
82
|
+
// TODO: sd-metadata를 ModuleMetadata로 만들게 아니고, 아예 IAotModuleDefMetadata형식으로 만들어지게 해야함
|
|
83
|
+
if (this._program!.getCompilerOptions().declaration) {
|
|
84
|
+
if (sourceFile.fileName.endsWith(".ts") && !sourceFile.fileName.endsWith(".d.ts")) {
|
|
85
|
+
const metadata = this._getMetadata(sourceFile);
|
|
86
|
+
if (metadata) {
|
|
87
|
+
this._writeMetadataFile(sourceFile, metadata);
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
}
|
|
90
91
|
}
|
|
91
92
|
|
|
92
|
-
if (this._parsedTsconfig.options.declaration) {
|
|
93
|
+
/*if (this._parsedTsconfig.options.declaration) {
|
|
93
94
|
this._writeMetadataBundles();
|
|
94
|
-
}
|
|
95
|
+
}*/
|
|
95
96
|
}
|
|
96
97
|
|
|
97
98
|
const result = diagnostics.map((item) => SdTsDiagnosticUtil.convertDiagnosticsToResult(item)).filterExists();
|
|
@@ -101,7 +102,23 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
101
102
|
return result;
|
|
102
103
|
}
|
|
103
104
|
|
|
104
|
-
private
|
|
105
|
+
private _writeMetadataFile(sourceFile: ts.SourceFile, metadata: ModuleMetadata): void {
|
|
106
|
+
const metadataText = JSON.stringify({
|
|
107
|
+
...metadata,
|
|
108
|
+
importAs: this.npmConfig.name
|
|
109
|
+
});
|
|
110
|
+
const outFileName = path.resolve(
|
|
111
|
+
this._program!.getCompilerOptions().declarationDir!,
|
|
112
|
+
path.relative(path.resolve(this.rootPath, "src"), sourceFile.fileName)
|
|
113
|
+
).replace(/\.ts$/, ".sd-metadata.json");
|
|
114
|
+
this._cacheCompilerHost!.writeFile(outFileName, metadataText, false, undefined, [sourceFile]);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
private _getMetadata(sourceFile: ts.SourceFile): ModuleMetadata | undefined {
|
|
118
|
+
return new MetadataCollector().getMetadata(sourceFile, true);
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
/*private _writeMetadataBundles(): void {
|
|
105
122
|
for (const rootFilePath of this._parsedTsconfig.fileNames) {
|
|
106
123
|
const metadata = new MetadataBundler(
|
|
107
124
|
rootFilePath.replace(/\.ts$/, ""),
|
|
@@ -120,17 +137,19 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
120
137
|
if (!fileCache?.sourceFile) throw new NeverEntryError();
|
|
121
138
|
this._cacheCompilerHost!.writeFile(outFileName, JSON.stringify(metadata), false, undefined, [fileCache.sourceFile]);
|
|
122
139
|
}
|
|
123
|
-
}
|
|
140
|
+
}*/
|
|
124
141
|
|
|
125
142
|
public override async reloadProgramAsync(watch: boolean): Promise<string[]> {
|
|
126
143
|
this._logger.debug("프로그램 리로드");
|
|
127
144
|
|
|
128
|
-
|
|
129
|
-
|
|
145
|
+
const parsedTsconfig = ts.parseJsonConfigFileContent(this._tsconfig, ts.sys, this.rootPath, this._tsconfig.angularCompilerOptions);
|
|
146
|
+
|
|
147
|
+
this._moduleResolutionCache = ts.createModuleResolutionCache(this.rootPath, (s) => s, parsedTsconfig.options);
|
|
148
|
+
this._cacheCompilerHost = await this._createCacheCompilerHostAsync(parsedTsconfig, this._moduleResolutionCache);
|
|
130
149
|
|
|
131
150
|
this._ngProgram = new NgtscProgram(
|
|
132
|
-
|
|
133
|
-
|
|
151
|
+
parsedTsconfig.fileNames,
|
|
152
|
+
parsedTsconfig.options,
|
|
134
153
|
this._cacheCompilerHost,
|
|
135
154
|
this._ngProgram
|
|
136
155
|
);
|
|
@@ -152,15 +171,27 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
152
171
|
};
|
|
153
172
|
|
|
154
173
|
if (watch) {
|
|
155
|
-
|
|
156
|
-
this.
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
174
|
+
if (this.skipProcesses.includes("emit")) {
|
|
175
|
+
this._builder = ts.createSemanticDiagnosticsBuilderProgram(
|
|
176
|
+
this._program,
|
|
177
|
+
this._cacheCompilerHost,
|
|
178
|
+
this._builder as ts.SemanticDiagnosticsBuilderProgram
|
|
179
|
+
);
|
|
180
|
+
}
|
|
181
|
+
else {
|
|
182
|
+
this._builder = ts.createEmitAndSemanticDiagnosticsBuilderProgram(
|
|
183
|
+
this._program,
|
|
184
|
+
this._cacheCompilerHost,
|
|
185
|
+
this._builder as ts.EmitAndSemanticDiagnosticsBuilderProgram
|
|
186
|
+
);
|
|
187
|
+
}
|
|
188
|
+
const builder = this._builder as ts.SemanticDiagnosticsBuilderProgram;
|
|
161
189
|
|
|
162
|
-
|
|
190
|
+
let seq = 0;
|
|
191
|
+
const affectedFilePathSet = new Set<string>();
|
|
163
192
|
while (true) {
|
|
193
|
+
const affectedFilePaths: string[] = [];
|
|
194
|
+
this._logger.debug(`프로그램 리로드 > 변경파일 목록구성: [SEQ: ${++seq}]`);
|
|
164
195
|
const result = builder.getSemanticDiagnosticsOfNextAffectedFile(undefined, (sourceFile) => {
|
|
165
196
|
if (this._ngCompiler!.ignoreForDiagnostics.has(sourceFile) && sourceFile.fileName.endsWith(".ngtypecheck.ts")) {
|
|
166
197
|
const originalFilename = sourceFile.fileName.slice(0, -15) + ".ts";
|
|
@@ -173,14 +204,20 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
173
204
|
return false;
|
|
174
205
|
});
|
|
175
206
|
|
|
176
|
-
if (
|
|
177
|
-
|
|
178
|
-
if ("fileName" in result.affected) {
|
|
207
|
+
if (result && "fileName" in result.affected) {
|
|
179
208
|
affectedFilePaths.push(result.affected.fileName);
|
|
180
209
|
}
|
|
210
|
+
|
|
211
|
+
affectedFilePaths.distinctThis();
|
|
212
|
+
|
|
213
|
+
this._logger.debug(`프로그램 리로드 > 변경파일 목록구성: [SEQ: ${seq}, SIZE:${affectedFilePathSet.size}]\n` + affectedFilePaths.map((item) => "- " + item).join("\n"));
|
|
214
|
+
|
|
215
|
+
affectedFilePathSet.adds(...affectedFilePaths.distinct());
|
|
216
|
+
|
|
217
|
+
if (!result) break;
|
|
181
218
|
}
|
|
182
219
|
|
|
183
|
-
const result =
|
|
220
|
+
const result = Array.from(affectedFilePathSet.values());
|
|
184
221
|
|
|
185
222
|
this._logger.debug("프로그램 리로드", result);
|
|
186
223
|
|
|
@@ -234,7 +271,7 @@ export class SdCliNgLibraryBuilder extends SdCliTypescriptBuilder {
|
|
|
234
271
|
this._logger.debug("Angular Module, RoutingModule 생성", dirtyFilePaths);
|
|
235
272
|
|
|
236
273
|
const result: ITsGenResult = { dirtyFilePaths: [], result: [] };
|
|
237
|
-
if (this.
|
|
274
|
+
if (this.skipProcesses.includes("genNgModule")) return result;
|
|
238
275
|
|
|
239
276
|
const reloadResult = await this._moduleFilesGenerator.reloadSourceFilesAsync(
|
|
240
277
|
dirtyFilePaths,
|