@simplysm/sd-cli 12.5.19 → 12.5.21

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.
Files changed (58) hide show
  1. package/dist/build-tools/SdNgBundler.d.ts +1 -0
  2. package/dist/build-tools/SdNgBundler.js +70 -57
  3. package/dist/build-tools/SdNgBundler.js.map +1 -1
  4. package/dist/build-tools/SdReactBundler.d.ts +25 -0
  5. package/dist/build-tools/SdReactBundler.js +295 -0
  6. package/dist/build-tools/SdReactBundler.js.map +1 -0
  7. package/dist/build-tools/SdReactBundlerContext.d.ts +14 -0
  8. package/dist/build-tools/SdReactBundlerContext.js +59 -0
  9. package/dist/build-tools/SdReactBundlerContext.js.map +1 -0
  10. package/dist/build-tools/SdServerBundler.d.ts +1 -0
  11. package/dist/build-tools/SdServerBundler.js +8 -7
  12. package/dist/build-tools/SdServerBundler.js.map +1 -1
  13. package/dist/build-tools/SdTsCompiler.d.ts +1 -0
  14. package/dist/build-tools/SdTsCompiler.js +355 -327
  15. package/dist/build-tools/SdTsCompiler.js.map +1 -1
  16. package/dist/build-tools/SdTsLibBundler.d.ts +1 -1
  17. package/dist/build-tools/SdTsLibBundler.js +2 -1
  18. package/dist/build-tools/SdTsLibBundler.js.map +1 -1
  19. package/dist/builders/SdCliClientBuilder.js +42 -20
  20. package/dist/builders/SdCliClientBuilder.js.map +1 -1
  21. package/dist/builders/SdCliServerBuilder.js +2 -1
  22. package/dist/builders/SdCliServerBuilder.js.map +1 -1
  23. package/dist/builders/SdCliTsLibBuilder.js +4 -2
  24. package/dist/builders/SdCliTsLibBuilder.js.map +1 -1
  25. package/dist/bundle-plugins/sdNgPlugin.d.ts +1 -0
  26. package/dist/bundle-plugins/sdNgPlugin.js +38 -23
  27. package/dist/bundle-plugins/sdNgPlugin.js.map +1 -1
  28. package/dist/bundle-plugins/sdReactPlugin.d.ts +16 -0
  29. package/dist/bundle-plugins/sdReactPlugin.js +117 -0
  30. package/dist/bundle-plugins/sdReactPlugin.js.map +1 -0
  31. package/dist/bundle-plugins/sdServerPlugin.d.ts +1 -0
  32. package/dist/bundle-plugins/sdServerPlugin.js +1 -0
  33. package/dist/bundle-plugins/sdServerPlugin.js.map +1 -1
  34. package/dist/entry/SdCliProject.js +7 -4
  35. package/dist/entry/SdCliProject.js.map +1 -1
  36. package/dist/index.d.ts +4 -0
  37. package/dist/index.js +4 -0
  38. package/dist/index.js.map +1 -1
  39. package/dist/utils/SdCliPerformanceTime.d.ts +9 -0
  40. package/dist/utils/SdCliPerformanceTime.js +40 -0
  41. package/dist/utils/SdCliPerformanceTime.js.map +1 -0
  42. package/package.json +13 -10
  43. package/src/build-tools/SdNgBundler.ts +82 -68
  44. package/src/build-tools/SdReactBundler.ts +372 -0
  45. package/src/build-tools/SdReactBundlerContext.ts +71 -0
  46. package/src/build-tools/SdServerBundler.ts +22 -20
  47. package/src/build-tools/SdTsCompiler.ts +341 -357
  48. package/src/build-tools/SdTsLibBundler.ts +2 -1
  49. package/src/builders/SdCliClientBuilder.ts +53 -29
  50. package/src/builders/SdCliServerBuilder.ts +5 -4
  51. package/src/builders/SdCliTsLibBuilder.ts +7 -4
  52. package/src/bundle-plugins/sdNgPlugin.ts +44 -23
  53. package/src/bundle-plugins/sdReactPlugin.ts +164 -0
  54. package/src/bundle-plugins/sdServerPlugin.ts +2 -0
  55. package/src/entry/SdCliProject.ts +6 -4
  56. package/src/index.ts +4 -0
  57. package/src/utils/SdCliPerformanceTime.ts +42 -0
  58. package/tsconfig.json +1 -1
@@ -10,7 +10,7 @@ export class SdTsLibBundler {
10
10
 
11
11
  readonly #pkgPath: string;
12
12
 
13
- public constructor(pkgPath: string, dev: boolean) {
13
+ public constructor(pkgPath: string, dev: boolean, watchScopePaths: string[]) {
14
14
  this.#pkgPath = pkgPath;
15
15
  this.#compiler = new SdTsCompiler({
16
16
  pkgPath,
@@ -18,6 +18,7 @@ export class SdTsLibBundler {
18
18
  isDevMode: dev,
19
19
  globalStyleFilePath: path.resolve(pkgPath, "src/styles.scss"),
20
20
  isForBundle: false,
21
+ watchScopePaths: watchScopePaths,
21
22
  });
22
23
  }
23
24
 
@@ -14,18 +14,15 @@ import { SdCliCordova } from "../build-tools/SdCliCordova";
14
14
  import { SdCliNgRoutesFileGenerator } from "../build-tools/SdCliNgRoutesFileGenerator";
15
15
  import { SdLinter } from "../build-tools/SdLinter";
16
16
  import { SdCliElectron } from "../entry/SdCliElectron";
17
-
18
- // import ts from "typescript";
17
+ import { SdReactBundler } from "../build-tools/SdReactBundler";
19
18
 
20
19
  export class SdCliClientBuilder extends EventEmitter {
21
20
  private readonly _logger = Logger.get(["simplysm", "sd-cli", "SdCliClientBuilder"]);
22
21
  private readonly _pkgConf: ISdCliClientPackageConfig;
23
22
  private readonly _npmConf: INpmConfig;
24
- private _builders?: SdNgBundler[];
23
+ private _builders?: (SdNgBundler | SdReactBundler)[];
25
24
  private _cordova?: SdCliCordova;
26
25
 
27
- // #program?: ts.Program;
28
-
29
26
  public constructor(
30
27
  private readonly _projConf: ISdCliConfig,
31
28
  private readonly _pkgPath: string,
@@ -116,6 +113,10 @@ export class SdCliClientBuilder extends EventEmitter {
116
113
  affectedFileSet: Set<string>;
117
114
  buildResults: ISdCliPackageBuildResult[];
118
115
  }> {
116
+ const localUpdatePaths = Object.keys(this._projConf.localUpdates ?? {}).mapMany((key) =>
117
+ FsUtil.glob(path.resolve(this._pkgPath, "../../node_modules", key)),
118
+ );
119
+
119
120
  const builderTypes = Object.keys(this._pkgConf.builder ?? { web: {} }) as ("web" | "electron" | "cordova")[];
120
121
  if (this._pkgConf.builder?.cordova && !this._cordova) {
121
122
  this._debug("CORDOVA 준비...");
@@ -129,27 +130,53 @@ export class SdCliClientBuilder extends EventEmitter {
129
130
  if (!this._builders) {
130
131
  this._debug(`BUILD 준비...`);
131
132
 
132
- this._builders = builderTypes.map(
133
- (builderType) =>
134
- new SdNgBundler({
135
- dev: opt.dev,
136
- builderType: builderType,
137
- pkgPath: this._pkgPath,
138
- outputPath:
139
- builderType === "web"
140
- ? path.resolve(this._pkgPath, "dist")
141
- : builderType === "electron" && !opt.dev
142
- ? path.resolve(this._pkgPath, ".electron/src")
143
- : builderType === "cordova" && !opt.dev
144
- ? path.resolve(this._pkgPath, ".cordova/www")
145
- : path.resolve(this._pkgPath, "dist", builderType),
146
- env: {
147
- ...this._pkgConf.env,
148
- ...this._pkgConf.builder?.[builderType]?.env,
149
- },
150
- cordovaConfig: builderType === "cordova" ? this._pkgConf.builder!.cordova : undefined,
151
- }),
152
- );
133
+ if (this._npmConf.dependencies && Object.keys(this._npmConf.dependencies).includes("react")) {
134
+ this._builders = builderTypes.map(
135
+ (builderType) =>
136
+ new SdReactBundler({
137
+ dev: opt.dev,
138
+ builderType: builderType,
139
+ pkgPath: this._pkgPath,
140
+ outputPath:
141
+ builderType === "web"
142
+ ? path.resolve(this._pkgPath, "dist")
143
+ : builderType === "electron" && !opt.dev
144
+ ? path.resolve(this._pkgPath, ".electron/src")
145
+ : builderType === "cordova" && !opt.dev
146
+ ? path.resolve(this._pkgPath, ".cordova/www")
147
+ : path.resolve(this._pkgPath, "dist", builderType),
148
+ env: {
149
+ ...this._pkgConf.env,
150
+ ...this._pkgConf.builder?.[builderType]?.env,
151
+ },
152
+ cordovaConfig: builderType === "cordova" ? this._pkgConf.builder!.cordova : undefined,
153
+ watchScopePaths: [path.resolve(this._pkgPath, "../"), ...localUpdatePaths],
154
+ }),
155
+ );
156
+ } else {
157
+ this._builders = builderTypes.map(
158
+ (builderType) =>
159
+ new SdNgBundler({
160
+ dev: opt.dev,
161
+ builderType: builderType,
162
+ pkgPath: this._pkgPath,
163
+ outputPath:
164
+ builderType === "web"
165
+ ? path.resolve(this._pkgPath, "dist")
166
+ : builderType === "electron" && !opt.dev
167
+ ? path.resolve(this._pkgPath, ".electron/src")
168
+ : builderType === "cordova" && !opt.dev
169
+ ? path.resolve(this._pkgPath, ".cordova/www")
170
+ : path.resolve(this._pkgPath, "dist", builderType),
171
+ env: {
172
+ ...this._pkgConf.env,
173
+ ...this._pkgConf.builder?.[builderType]?.env,
174
+ },
175
+ cordovaConfig: builderType === "cordova" ? this._pkgConf.builder!.cordova : undefined,
176
+ watchScopePaths: [path.resolve(this._pkgPath, "../"), ...localUpdatePaths],
177
+ }),
178
+ );
179
+ }
153
180
  }
154
181
 
155
182
  this._debug(`BUILD & CHECK...`);
@@ -184,9 +211,6 @@ export class SdCliClientBuilder extends EventEmitter {
184
211
  }
185
212
 
186
213
  this._debug(`빌드 완료`);
187
- const localUpdatePaths = Object.keys(this._projConf.localUpdates ?? {}).mapMany((key) =>
188
- FsUtil.glob(path.resolve(this._pkgPath, "../../node_modules", key)),
189
- );
190
214
  const currWatchFileSet = new Set(
191
215
  Array.from(watchFileSet).filter(
192
216
  (item) =>
@@ -219,6 +219,10 @@ Options = UnsafeLegacyRenegotiation`.trim(),
219
219
  affectedFileSet: Set<string>;
220
220
  buildResults: ISdCliPackageBuildResult[];
221
221
  }> {
222
+ const localUpdatePaths = Object.keys(this._projConf.localUpdates ?? {}).mapMany((key) =>
223
+ FsUtil.glob(path.resolve(this._pkgPath, "../../node_modules", key)),
224
+ );
225
+
222
226
  this._debug(`BUILD 준비...`);
223
227
  const tsConfig = FsUtil.readJson(path.resolve(this._pkgPath, "tsconfig.json")) as ITsConfig;
224
228
  this.#extModules = this.#extModules ?? (await this._getExternalModulesAsync());
@@ -231,16 +235,13 @@ Options = UnsafeLegacyRenegotiation`.trim(),
231
235
  ? tsConfig.files.map((item) => path.resolve(this._pkgPath, item))
232
236
  : [path.resolve(this._pkgPath, "src/main.ts")],
233
237
  external: this.#extModules.map((item) => item.name),
238
+ watchScopePaths: [path.resolve(this._pkgPath, "../"), ...localUpdatePaths],
234
239
  });
235
240
 
236
241
  this._debug(`BUILD & CHECK...`);
237
242
  const buildResult = await this.#builder.bundleAsync();
238
243
 
239
244
  //-- filePaths
240
-
241
- const localUpdatePaths = Object.keys(this._projConf.localUpdates ?? {}).mapMany((key) =>
242
- FsUtil.glob(path.resolve(this._pkgPath, "../../node_modules", key)),
243
- );
244
245
  const watchFileSet = new Set(
245
246
  Array.from(buildResult.watchFileSet).filter(
246
247
  (item) =>
@@ -88,8 +88,14 @@ export class SdCliTsLibBuilder extends EventEmitter {
88
88
  affectedFileSet: Set<string>;
89
89
  buildResults: ISdCliPackageBuildResult[];
90
90
  }> {
91
+ const localUpdatePaths = Object.keys(this.#projConf.localUpdates ?? {}).mapMany((key) =>
92
+ FsUtil.glob(path.resolve(this.#pkgPath, "../../node_modules", key)),
93
+ );
94
+
91
95
  this._debug(`BUILD...`);
92
- this.#bundler = this.#bundler ?? new SdTsLibBundler(this.#pkgPath, dev);
96
+ this.#bundler =
97
+ this.#bundler ??
98
+ new SdTsLibBundler(this.#pkgPath, dev, [path.resolve(this.#pkgPath, "../"), ...localUpdatePaths]);
93
99
  const buildResult = await this.#bundler.buildAsync();
94
100
 
95
101
  this._debug("LINT...");
@@ -99,9 +105,6 @@ export class SdCliTsLibBuilder extends EventEmitter {
99
105
  const lintResults = await SdLinter.lintAsync(this.#pkgPath, buildResult.affectedFileSet, buildResult.program);
100
106
 
101
107
  this._debug(`빌드 완료`);
102
- const localUpdatePaths = Object.keys(this.#projConf.localUpdates ?? {}).mapMany((key) =>
103
- FsUtil.glob(path.resolve(this.#pkgPath, "../../node_modules", key)),
104
- );
105
108
  const watchFileSet = new Set(
106
109
  Array.from(buildResult.watchFileSet).filter(
107
110
  (item) =>
@@ -5,13 +5,23 @@ import os from "os";
5
5
  import { ISdTsCompilerResult, SdTsCompiler } from "../build-tools/SdTsCompiler";
6
6
  import { JavaScriptTransformer } from "@angular/build/src/tools/esbuild/javascript-transformer";
7
7
  import { convertTypeScriptDiagnostic } from "@angular/build/src/tools/esbuild/angular/diagnostics";
8
+ import { SdCliPerformanceTimer } from "../utils/SdCliPerformanceTime";
9
+ import { Logger } from "@simplysm/sd-core-node";
8
10
 
9
11
  export function sdNgPlugin(conf: {
10
12
  pkgPath: string;
11
13
  dev: boolean;
12
14
  modifiedFileSet: Set<string>;
13
15
  result: INgPluginResultCache;
16
+ watchScopePaths: string[];
14
17
  }): esbuild.Plugin {
18
+ let perf: SdCliPerformanceTimer;
19
+ const logger = Logger.get(["simplysm", "sd-cli", "sdNgPlugin"]);
20
+
21
+ function debug(...msg: any[]): void {
22
+ logger.debug(`[${path.basename(conf.pkgPath)}]`, ...msg);
23
+ }
24
+
15
25
  return {
16
26
  name: "sd-ng-compiler",
17
27
  setup: (build: esbuild.PluginBuild) => {
@@ -20,6 +30,7 @@ export function sdNgPlugin(conf: {
20
30
  additionalOptions: { declaration: false },
21
31
  isDevMode: conf.dev,
22
32
  isForBundle: true,
33
+ watchScopePaths: conf.watchScopePaths,
23
34
  });
24
35
 
25
36
  let buildResult: ISdTsCompilerResult;
@@ -39,32 +50,39 @@ export function sdNgPlugin(conf: {
39
50
  //---------------------------
40
51
 
41
52
  build.onStart(async () => {
42
- compiler.invalidate(conf.modifiedFileSet);
43
- for (const modifiedFile of conf.modifiedFileSet) {
44
- outputContentsCacheMap.delete(modifiedFile);
45
- }
53
+ perf = new SdCliPerformanceTimer("esbuild");
46
54
 
47
- buildResult = await compiler.buildAsync();
55
+ const res = await perf.run("typescript build", async () => {
56
+ compiler.invalidate(conf.modifiedFileSet);
57
+ for (const modifiedFile of conf.modifiedFileSet) {
58
+ outputContentsCacheMap.delete(modifiedFile);
59
+ }
48
60
 
49
- conf.result.watchFileSet = buildResult.watchFileSet;
50
- conf.result.affectedFileSet = buildResult.affectedFileSet;
51
- conf.result.program = buildResult.program;
61
+ buildResult = await compiler.buildAsync();
62
+
63
+ conf.result.watchFileSet = buildResult.watchFileSet;
64
+ conf.result.affectedFileSet = buildResult.affectedFileSet;
65
+ conf.result.program = buildResult.program;
66
+
67
+ //-- return err/warn
68
+ return {
69
+ errors: [
70
+ ...buildResult.typescriptDiagnostics
71
+ .filter((item) => item.category === ts.DiagnosticCategory.Error)
72
+ .map((item) => convertTypeScriptDiagnostic(ts, item)),
73
+ ...Array.from(buildResult.stylesheetBundlingResultMap.values()).flatMap((item) => item.errors),
74
+ ].filterExists(),
75
+ warnings: [
76
+ ...buildResult.typescriptDiagnostics
77
+ .filter((item) => item.category !== ts.DiagnosticCategory.Error)
78
+ .map((item) => convertTypeScriptDiagnostic(ts, item)),
79
+ // ...Array.from(buildResult.stylesheetResultMap.values()).flatMap(item => item.warnings)
80
+ ],
81
+ };
82
+ });
52
83
 
53
- //-- return err/warn
54
- return {
55
- errors: [
56
- ...buildResult.typescriptDiagnostics
57
- .filter((item) => item.category === ts.DiagnosticCategory.Error)
58
- .map((item) => convertTypeScriptDiagnostic(ts, item)),
59
- ...Array.from(buildResult.stylesheetBundlingResultMap.values()).flatMap((item) => item.errors),
60
- ].filterExists(),
61
- warnings: [
62
- ...buildResult.typescriptDiagnostics
63
- .filter((item) => item.category !== ts.DiagnosticCategory.Error)
64
- .map((item) => convertTypeScriptDiagnostic(ts, item)),
65
- // ...Array.from(buildResult.stylesheetResultMap.values()).flatMap(item => item.warnings)
66
- ],
67
- };
84
+ perf.start("transform & bundling");
85
+ return res;
68
86
  });
69
87
 
70
88
  build.onLoad({ filter: /\.ts$/ }, async (args) => {
@@ -132,6 +150,9 @@ export function sdNgPlugin(conf: {
132
150
  );
133
151
 
134
152
  build.onEnd((result) => {
153
+ perf.end("transform & bundling");
154
+ debug(perf.toString());
155
+
135
156
  for (const { outputFiles, metafile } of buildResult.stylesheetBundlingResultMap.values()) {
136
157
  result.outputFiles = result.outputFiles ?? [];
137
158
  result.outputFiles.push(...outputFiles);
@@ -0,0 +1,164 @@
1
+ import esbuild from "esbuild";
2
+ import ts from "typescript";
3
+ import path from "path";
4
+ import { ISdTsCompilerResult, SdTsCompiler } from "../build-tools/SdTsCompiler";
5
+ import { convertTypeScriptDiagnostic } from "@angular/build/src/tools/esbuild/angular/diagnostics";
6
+ import postcss from "postcss";
7
+ import { FsUtil } from "@simplysm/sd-core-node";
8
+ import postcssUrl from "postcss-url";
9
+ import postcssHas from "css-has-pseudo";
10
+ import autoprefixer from "autoprefixer";
11
+
12
+ export function sdReactPlugin(conf: {
13
+ pkgPath: string;
14
+ dev: boolean;
15
+ modifiedFileSet: Set<string>;
16
+ result: IReactPluginResultCache;
17
+ watchScopePaths: string[];
18
+ }): esbuild.Plugin {
19
+ return {
20
+ name: "sd-ng-compiler",
21
+ setup: (build: esbuild.PluginBuild) => {
22
+ const compiler = new SdTsCompiler({
23
+ pkgPath: conf.pkgPath,
24
+ additionalOptions: { declaration: false },
25
+ isDevMode: conf.dev,
26
+ isForBundle: true,
27
+ watchScopePaths: conf.watchScopePaths
28
+ });
29
+
30
+ let buildResult: ISdTsCompilerResult;
31
+ const outputContentsCacheMap = new Map<string, string | Uint8Array | undefined>();
32
+
33
+ //---------------------------
34
+
35
+ build.onStart(async () => {
36
+ compiler.invalidate(conf.modifiedFileSet);
37
+ for (const modifiedFile of conf.modifiedFileSet) {
38
+ outputContentsCacheMap.delete(modifiedFile);
39
+ }
40
+
41
+ buildResult = await compiler.buildAsync();
42
+
43
+ conf.result.watchFileSet = buildResult.watchFileSet;
44
+ conf.result.affectedFileSet = buildResult.affectedFileSet;
45
+ conf.result.program = buildResult.program;
46
+
47
+ //-- return err/warn
48
+ return {
49
+ errors: [
50
+ ...buildResult.typescriptDiagnostics
51
+ .filter((item) => item.category === ts.DiagnosticCategory.Error)
52
+ .map((item) => convertTypeScriptDiagnostic(ts, item)),
53
+ ...Array.from(buildResult.stylesheetBundlingResultMap.values()).flatMap((item) => item.errors),
54
+ ].filterExists(),
55
+ warnings: [
56
+ ...buildResult.typescriptDiagnostics
57
+ .filter((item) => item.category !== ts.DiagnosticCategory.Error)
58
+ .map((item) => convertTypeScriptDiagnostic(ts, item)),
59
+ // ...Array.from(buildResult.stylesheetResultMap.values()).flatMap(item => item.warnings)
60
+ ],
61
+ };
62
+ });
63
+
64
+ build.onLoad({ filter: /\.tsx?$/ }, (args) => {
65
+ const output = outputContentsCacheMap.get(path.normalize(args.path));
66
+ if (output != null) {
67
+ return { contents: output, loader: "js" };
68
+ }
69
+
70
+ const emittedJsFile = buildResult.emittedFilesCacheMap.get(path.normalize(args.path))?.last();
71
+ if (!emittedJsFile) {
72
+ throw new Error(`ts 빌더 결과 emit 파일이 존재하지 않습니다. ${args.path}`);
73
+ }
74
+
75
+ const contents = emittedJsFile.text;
76
+
77
+ outputContentsCacheMap.set(path.normalize(args.path), contents);
78
+
79
+ return { contents, loader: "js" };
80
+ });
81
+
82
+ build.onLoad({ filter: /\.[cm]?jsx?$/ }, (args) => {
83
+ conf.result.watchFileSet!.add(path.normalize(args.path));
84
+ return null;
85
+ });
86
+
87
+ build.onLoad({ filter: /\.css$/ }, async (args) => {
88
+ conf.result.watchFileSet!.add(path.normalize(args.path));
89
+ const output = outputContentsCacheMap.get(path.normalize(args.path));
90
+ if (output != null) {
91
+ return {
92
+ contents: output,
93
+ loader: "file",
94
+ };
95
+ }
96
+
97
+ const css = await FsUtil.readFileAsync(path.normalize(args.path));
98
+ const result = await postcss()
99
+ .use(
100
+ autoprefixer({
101
+ overrideBrowserslist: ["Chrome > 78"]
102
+ })
103
+ )
104
+ .use(
105
+ postcssUrl({
106
+ url: "copy",
107
+ }),
108
+ )
109
+ .use(
110
+ postcssHas()
111
+ )
112
+ .process(css, {
113
+ from: path.normalize(args.path),
114
+ to: path.resolve(conf.pkgPath, "dist", "media", path.basename(args.path)),
115
+ });
116
+
117
+ outputContentsCacheMap.set(path.normalize(args.path), result.css);
118
+
119
+ return { contents: result.css, loader: "file" };
120
+ });
121
+
122
+ build.onLoad(
123
+ {
124
+ filter: new RegExp(
125
+ "(" +
126
+ Object.keys(build.initialOptions.loader!)
127
+ .map((item) => "\\" + item)
128
+ .join("|") +
129
+ ")$",
130
+ ),
131
+ },
132
+ (args) => {
133
+ conf.result.watchFileSet!.add(path.normalize(args.path));
134
+ return null;
135
+ },
136
+ );
137
+
138
+ build.onEnd((result) => {
139
+ for (const { outputFiles, metafile } of buildResult.stylesheetBundlingResultMap.values()) {
140
+ result.outputFiles = result.outputFiles ?? [];
141
+ result.outputFiles.push(...outputFiles);
142
+
143
+ if (result.metafile && metafile) {
144
+ result.metafile.inputs = { ...result.metafile.inputs, ...metafile.inputs };
145
+ result.metafile.outputs = { ...result.metafile.outputs, ...metafile.outputs };
146
+ }
147
+ }
148
+
149
+ conf.result.outputFiles = result.outputFiles;
150
+ conf.result.metafile = result.metafile;
151
+
152
+ conf.modifiedFileSet.clear();
153
+ });
154
+ },
155
+ };
156
+ }
157
+
158
+ export interface IReactPluginResultCache {
159
+ watchFileSet?: Set<string>;
160
+ affectedFileSet?: Set<string>;
161
+ program?: ts.Program;
162
+ outputFiles?: esbuild.OutputFile[];
163
+ metafile?: esbuild.Metafile;
164
+ }
@@ -9,6 +9,7 @@ export function sdServerPlugin(conf: {
9
9
  dev: boolean;
10
10
  modifiedFileSet: Set<string>;
11
11
  result: IServerPluginResultCache;
12
+ watchScopePaths: string[];
12
13
  }): esbuild.Plugin {
13
14
  return {
14
15
  name: "sd-server-compiler",
@@ -18,6 +19,7 @@ export function sdServerPlugin(conf: {
18
19
  additionalOptions: { declaration: false },
19
20
  isDevMode: conf.dev,
20
21
  isForBundle: true,
22
+ watchScopePaths: conf.watchScopePaths
21
23
  });
22
24
 
23
25
  let buildResult: ISdTsCompilerResult;
@@ -102,10 +102,10 @@ export class SdCliProject {
102
102
  }
103
103
 
104
104
  for (const buildResult of message.result!.buildResults) {
105
- if (buildResult.filePath == null || PathUtil.isChildPath(buildResult.filePath, message.req.pkgPath)) {
106
- const cacheItem = resultCache.getOrCreate(buildResult.filePath ?? "none", []);
107
- cacheItem.push(buildResult);
108
- }
105
+ // if (buildResult.filePath == null || PathUtil.isChildPath(buildResult.filePath, message.req.pkgPath)) {
106
+ const cacheItem = resultCache.getOrCreate(buildResult.filePath ?? "none", []);
107
+ cacheItem.push(buildResult);
108
+ // }
109
109
  }
110
110
 
111
111
  const pkgConf = message.req.projConf.packages[path.basename(message.req.pkgPath)]!;
@@ -147,6 +147,7 @@ export class SdCliProject {
147
147
  }
148
148
 
149
149
  serverInfo.pathProxy[pkgName] = path.resolve(message.req.pkgPath, "dist");
150
+ serverInfo.pathProxy["node_modules"] = path.resolve(process.cwd(), "node_modules");
150
151
  // serverInfo.changeFilePaths.push(...message.result!.affectedFilePaths);
151
152
 
152
153
  serverInfo.hasClientChanges = true;
@@ -205,6 +206,7 @@ export class SdCliProject {
205
206
  for (const serverInfo of serverInfoMap.values()) {
206
207
  if (Object.keys(serverInfo.pathProxy).length > 0) {
207
208
  for (const proxyPath of Object.keys(serverInfo.pathProxy)) {
209
+ if (proxyPath === "node_modules") continue;
208
210
  clientPaths.push(`http://localhost:${serverInfo.port}/${proxyPath}/`);
209
211
  }
210
212
  } else {
package/src/index.ts CHANGED
@@ -4,6 +4,8 @@ export * from "./build-tools/SdCliNgRoutesFileGenerator";
4
4
  export * from "./build-tools/SdLinter";
5
5
  export * from "./build-tools/SdNgBundler";
6
6
  export * from "./build-tools/SdNgBundlerContext";
7
+ export * from "./build-tools/SdReactBundler";
8
+ export * from "./build-tools/SdReactBundlerContext";
7
9
  export * from "./build-tools/SdServerBundler";
8
10
  export * from "./build-tools/SdTsCompiler";
9
11
  export * from "./build-tools/SdTsLibBundler";
@@ -12,9 +14,11 @@ export * from "./builders/SdCliJsLibLinter";
12
14
  export * from "./builders/SdCliServerBuilder";
13
15
  export * from "./builders/SdCliTsLibBuilder";
14
16
  export * from "./bundle-plugins/sdNgPlugin";
17
+ export * from "./bundle-plugins/sdReactPlugin";
15
18
  export * from "./bundle-plugins/sdServerPlugin";
16
19
  export * from "./commons";
17
20
  export * from "./entry/SdCliElectron";
18
21
  export * from "./entry/SdCliLocalUpdate";
19
22
  export * from "./entry/SdCliProject";
20
23
  export * from "./utils/SdCliBuildResultUtil";
24
+ export * from "./utils/SdCliPerformanceTime";
@@ -0,0 +1,42 @@
1
+ export class SdCliPerformanceTimer {
2
+ #startingMap = new Map<string, number>();
3
+ #resultMap = new Map<string, number>();
4
+
5
+ constructor(private _name: string) {}
6
+
7
+ start(name: string) {
8
+ this.#startingMap.set(name, new Date().getTime());
9
+ }
10
+
11
+ end(name: string) {
12
+ const val = this.#startingMap.get(name);
13
+ if (val == null) throw new Error();
14
+ this.#resultMap.set(name, new Date().getTime() - val);
15
+ this.#startingMap.delete(name);
16
+ }
17
+
18
+ run<R>(name: string, fn: () => R): R {
19
+ const startTime = new Date().getTime();
20
+ let res = fn();
21
+ if (res instanceof Promise) {
22
+ return res.then((realRes) => {
23
+ const duration = new Date().getTime() - startTime;
24
+ this.#resultMap.update(name, (v) => (v ?? 0) + duration);
25
+ return realRes;
26
+ }) as R;
27
+ }
28
+
29
+ const duration = new Date().getTime() - startTime;
30
+ this.#resultMap.update(name, (v) => (v ?? 0) + duration);
31
+ return res;
32
+ }
33
+
34
+ toString() {
35
+ return `${this._name} performance report
36
+ ------------------------------------
37
+ ${Array.from(this.#resultMap.entries())
38
+ .map((en) => `${en[0]}: ${en[1].toLocaleString()}ms`)
39
+ .join("\n")}
40
+ ------------------------------------`;
41
+ }
42
+ }
package/tsconfig.json CHANGED
@@ -1,5 +1,5 @@
1
1
  {
2
- "extends": "../tsconfig.json",
2
+ "extends": "../../tsconfig.base.json",
3
3
  "compilerOptions": {
4
4
  "lib": ["ES2021"],
5
5
  "outDir": "./dist",