@nx/rspack 20.1.0 → 20.2.0-beta.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (38) hide show
  1. package/package.json +8 -6
  2. package/src/executors/dev-server/dev-server.impl.js +12 -2
  3. package/src/executors/dev-server/lib/get-dev-server-config.js +1 -1
  4. package/src/executors/rspack/lib/normalize-options.d.ts +3 -0
  5. package/src/executors/rspack/lib/normalize-options.js +40 -0
  6. package/src/executors/rspack/rspack.impl.js +7 -3
  7. package/src/plugins/utils/apply-base-config.d.ts +5 -0
  8. package/src/plugins/utils/apply-base-config.js +348 -0
  9. package/src/plugins/utils/apply-react-config.d.ts +5 -0
  10. package/src/plugins/utils/apply-react-config.js +45 -0
  11. package/src/plugins/utils/apply-web-config.js +44 -45
  12. package/src/plugins/utils/get-terser-ecma-version.d.ts +1 -0
  13. package/src/plugins/utils/get-terser-ecma-version.js +35 -0
  14. package/src/plugins/utils/hash-format.js +7 -1
  15. package/src/plugins/utils/loaders/stylesheet-loaders.js +1 -1
  16. package/src/plugins/utils/models.d.ts +9 -8
  17. package/src/plugins/utils/plugins/generate-package-json-plugin.d.ts +15 -0
  18. package/src/plugins/utils/plugins/generate-package-json-plugin.js +45 -0
  19. package/src/plugins/utils/plugins/normalize-options.d.ts +4 -0
  20. package/src/plugins/utils/plugins/normalize-options.js +170 -0
  21. package/src/plugins/utils/plugins/nx-tsconfig-paths-rspack-plugin.d.ts +10 -0
  22. package/src/plugins/utils/plugins/nx-tsconfig-paths-rspack-plugin.js +62 -0
  23. package/src/plugins/utils/plugins/rspack-nx-build-coordination-plugin.d.ts +11 -0
  24. package/src/plugins/utils/plugins/rspack-nx-build-coordination-plugin.js +94 -0
  25. package/src/plugins/utils/plugins/stats-json-plugin.d.ts +4 -0
  26. package/src/plugins/utils/plugins/stats-json-plugin.js +13 -0
  27. package/src/utils/config.js +3 -2
  28. package/src/utils/create-compiler.js +25 -4
  29. package/src/utils/get-copy-patterns.js +1 -1
  30. package/src/utils/module-federation/share.js +2 -2
  31. package/src/utils/module-federation/with-module-federation/utils.js +1 -1
  32. package/src/utils/normalize-assets.js +1 -1
  33. package/src/utils/with-nx.d.ts +8 -3
  34. package/src/utils/with-nx.js +26 -184
  35. package/src/utils/with-react.d.ts +6 -1
  36. package/src/utils/with-react.js +3 -57
  37. package/src/utils/with-web.d.ts +0 -1
  38. package/src/utils/with-web.js +2 -2
@@ -4,7 +4,6 @@ exports.applyWebConfig = applyWebConfig;
4
4
  const core_1 = require("@rspack/core");
5
5
  const instantiate_script_plugins_1 = require("./instantiate-script-plugins");
6
6
  const path_1 = require("path");
7
- const webpack_subresource_integrity_1 = require("webpack-subresource-integrity");
8
7
  const hash_format_1 = require("./hash-format");
9
8
  const normalize_entry_1 = require("./normalize-entry");
10
9
  const stylesheet_loaders_1 = require("./loaders/stylesheet-loaders");
@@ -35,15 +34,15 @@ function applyWebConfig(options, config = {}, { useNormalizedEntry, } = {}) {
35
34
  if (options.index && options.generateIndexHtml) {
36
35
  plugins.push(new core_1.HtmlRspackPlugin({
37
36
  template: options.index,
38
- sri: options.subresourceIntegrity ? 'sha256' : undefined,
37
+ sri: 'sha256',
39
38
  ...(options.baseHref ? { base: { href: options.baseHref } } : {}),
39
+ ...(config.output?.scriptType === 'module'
40
+ ? { scriptLoading: 'module' }
41
+ : {}),
40
42
  }));
41
43
  }
42
- if (options.subresourceIntegrity) {
43
- plugins.push(new webpack_subresource_integrity_1.SubresourceIntegrityPlugin());
44
- }
45
44
  const minimizer = [];
46
- if (stylesOptimization) {
45
+ if (isProd && stylesOptimization) {
47
46
  minimizer.push(new core_1.LightningCssMinimizerRspackPlugin({
48
47
  test: /\.(?:css|scss|sass|less|styl)$/,
49
48
  }));
@@ -272,12 +271,10 @@ function applyWebConfig(options, config = {}, { useNormalizedEntry, } = {}) {
272
271
  }
273
272
  config.output = {
274
273
  ...(config.output ?? {}),
275
- assetModuleFilename: '[name].[contenthash:20][ext]',
276
- crossOriginLoading: options.subresourceIntegrity
277
- ? 'anonymous'
278
- : false,
274
+ assetModuleFilename: '[name].[contenthash:16][ext]',
275
+ crossOriginLoading: 'anonymous',
279
276
  };
280
- // In case users customize their webpack config with unsupported entry.
277
+ // In case users customize their rspack config with unsupported entry.
281
278
  if (typeof config.entry === 'function')
282
279
  throw new Error('Entry function is not supported. Use an object.');
283
280
  if (typeof config.entry === 'string')
@@ -292,40 +289,42 @@ function applyWebConfig(options, config = {}, { useNormalizedEntry, } = {}) {
292
289
  config.entry[entryName] = entryData.import;
293
290
  }
294
291
  });
295
- config.optimization = {
296
- ...(config.optimization ?? {}),
297
- minimizer: [...(config.optimization?.minimizer ?? []), ...minimizer],
298
- emitOnErrors: false,
299
- moduleIds: 'deterministic',
300
- runtimeChunk: options.runtimeChunk ? { name: 'runtime' } : false,
301
- splitChunks: {
302
- defaultSizeTypes: config.optimization?.splitChunks !== false
303
- ? config.optimization?.splitChunks?.defaultSizeTypes
304
- : ['...'],
305
- maxAsyncRequests: Infinity,
306
- cacheGroups: {
307
- default: !!options.commonChunk && {
308
- chunks: 'async',
309
- minChunks: 2,
310
- priority: 10,
311
- },
312
- common: !!options.commonChunk && {
313
- name: 'common',
314
- chunks: 'async',
315
- minChunks: 2,
316
- enforce: true,
317
- priority: 5,
318
- },
319
- vendors: false,
320
- vendor: !!options.vendorChunk && {
321
- name: 'vendor',
322
- chunks: (chunk) => chunk.name === 'main',
323
- enforce: true,
324
- test: /[\\/]node_modules[\\/]/,
292
+ config.optimization = !isProd
293
+ ? undefined
294
+ : {
295
+ ...(config.optimization ?? {}),
296
+ minimizer: [...(config.optimization?.minimizer ?? []), ...minimizer],
297
+ emitOnErrors: false,
298
+ moduleIds: 'deterministic',
299
+ runtimeChunk: options.runtimeChunk ? { name: 'runtime' } : false,
300
+ splitChunks: {
301
+ defaultSizeTypes: config.optimization?.splitChunks !== false
302
+ ? config.optimization?.splitChunks?.defaultSizeTypes
303
+ : ['...'],
304
+ maxAsyncRequests: Infinity,
305
+ cacheGroups: {
306
+ default: !!options.commonChunk && {
307
+ chunks: 'async',
308
+ minChunks: 2,
309
+ priority: 10,
310
+ },
311
+ common: !!options.commonChunk && {
312
+ name: 'common',
313
+ chunks: 'async',
314
+ minChunks: 2,
315
+ enforce: true,
316
+ priority: 5,
317
+ },
318
+ vendors: false,
319
+ vendor: !!options.vendorChunk && {
320
+ name: 'vendor',
321
+ chunks: (chunk) => chunk.name === 'main',
322
+ enforce: true,
323
+ test: /[\\/]node_modules[\\/]/,
324
+ },
325
325
  },
326
326
  },
327
- },
328
- };
327
+ };
329
328
  config.resolve.mainFields = ['browser', 'module', 'main'];
330
329
  config.module = {
331
330
  ...(config.module ?? {}),
@@ -364,7 +363,7 @@ function applyWebConfig(options, config = {}, { useNormalizedEntry, } = {}) {
364
363
  }
365
364
  function getClientEnvironment(mode) {
366
365
  // Grab NODE_ENV and NX_PUBLIC_* environment variables and prepare them to be
367
- // injected into the application via DefinePlugin in webpack configuration.
366
+ // injected into the application via DefinePlugin in rspack configuration.
368
367
  const nxPublicKeyRegex = /^NX_PUBLIC_/i;
369
368
  const raw = Object.keys(process.env)
370
369
  .filter((key) => nxPublicKeyRegex.test(key))
@@ -372,7 +371,7 @@ function getClientEnvironment(mode) {
372
371
  env[key] = process.env[key];
373
372
  return env;
374
373
  }, {});
375
- // Stringify all values so we can feed into webpack DefinePlugin
374
+ // Stringify all values so we can feed into rspack DefinePlugin
376
375
  const stringified = {
377
376
  'process.env': Object.keys(raw).reduce((env, key) => {
378
377
  env[key] = JSON.stringify(raw[key]);
@@ -0,0 +1 @@
1
+ export declare function getTerserEcmaVersion(projectRoot: string): 2020 | 5;
@@ -0,0 +1,35 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getTerserEcmaVersion = getTerserEcmaVersion;
4
+ const tslib_1 = require("tslib");
5
+ const path = tslib_1.__importStar(require("path"));
6
+ const fs = tslib_1.__importStar(require("fs"));
7
+ const browserslist = require("browserslist");
8
+ const VALID_BROWSERSLIST_FILES = ['.browserslistrc', 'browserslist'];
9
+ const ES5_BROWSERS = [
10
+ 'ie 10',
11
+ 'ie 11',
12
+ 'safari 11',
13
+ 'safari 11.1',
14
+ 'safari 12',
15
+ 'safari 12.1',
16
+ 'safari 13',
17
+ 'ios_saf 13.0',
18
+ 'ios_saf 13.3',
19
+ ];
20
+ function getTerserEcmaVersion(projectRoot) {
21
+ let pathToBrowserslistFile = '';
22
+ for (const browserslistFile of VALID_BROWSERSLIST_FILES) {
23
+ const fullPathToFile = path.join(projectRoot, browserslistFile);
24
+ if (fs.existsSync(fullPathToFile)) {
25
+ pathToBrowserslistFile = fullPathToFile;
26
+ break;
27
+ }
28
+ }
29
+ if (!pathToBrowserslistFile) {
30
+ return 2020;
31
+ }
32
+ const env = browserslist.loadConfig({ path: pathToBrowserslistFile });
33
+ const browsers = browserslist(env);
34
+ return browsers.some((b) => ES5_BROWSERS.includes(b)) ? 5 : 2020;
35
+ }
@@ -1,7 +1,13 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.getOutputHashFormat = getOutputHashFormat;
4
- function getOutputHashFormat(option, length = 20) {
4
+ const devkit_1 = require("@nx/devkit");
5
+ const MAX_HASH_LENGTH = 16;
6
+ function getOutputHashFormat(option, length = MAX_HASH_LENGTH) {
7
+ if (length > MAX_HASH_LENGTH) {
8
+ devkit_1.logger.warn(`Hash format length cannot be longer than ${MAX_HASH_LENGTH}. Using default of ${MAX_HASH_LENGTH}.`);
9
+ length = MAX_HASH_LENGTH;
10
+ }
5
11
  const hashFormats = {
6
12
  none: { chunk: '', extract: '', file: '', script: '' },
7
13
  media: { chunk: '', extract: '', file: `.[hash:${length}]`, script: '' },
@@ -82,7 +82,7 @@ function getCommonLoadersForGlobalStyle(options, includePaths) {
82
82
  }
83
83
  function postcssOptionsCreator(options, { includePaths, forCssModules = false, }) {
84
84
  const hashFormat = (0, hash_format_1.getOutputHashFormat)(options.outputHashing);
85
- // PostCSS options depend on the webpack loader, but we need to set the `config` path as a string due to this check:
85
+ // PostCSS options depend on the rspack loader, but we need to set the `config` path as a string due to this check:
86
86
  // https://github.com/webpack-contrib/postcss-loader/blob/0d342b1/src/utils.js#L36
87
87
  const postcssOptions = (loader) => ({
88
88
  map: options.sourceMap &&
@@ -1,6 +1,11 @@
1
1
  import type { Mode } from '@rspack/core';
2
2
  import type { ProjectGraph } from '@nx/devkit';
3
3
  import type { AssetGlob } from '@nx/js/src/utils/assets/assets';
4
+ export interface SvgrOptions {
5
+ svgo?: boolean;
6
+ titleProp?: boolean;
7
+ ref?: boolean;
8
+ }
4
9
  export interface AssetGlobPattern {
5
10
  glob: string;
6
11
  input: string;
@@ -120,11 +125,11 @@ export interface NxAppRspackPluginOptions {
120
125
  */
121
126
  outputHashing?: any;
122
127
  /**
123
- * Override `output.path` in webpack configuration. This setting is not recommended and exists for backwards compatibility.
128
+ * Override `output.path` in rspack configuration. This setting is not recommended and exists for backwards compatibility.
124
129
  */
125
130
  outputPath?: string;
126
131
  /**
127
- * Override `watchOptions.poll` in webpack configuration. This setting is not recommended and exists for backwards compatibility.
132
+ * Override `watchOptions.poll` in rspack configuration. This setting is not recommended and exists for backwards compatibility.
128
133
  */
129
134
  poll?: number;
130
135
  /**
@@ -140,7 +145,7 @@ export interface NxAppRspackPluginOptions {
140
145
  */
141
146
  progress?: boolean;
142
147
  /**
143
- * Add an additional chunk for the Webpack runtime. Defaults to `true` when `target === 'web'`.
148
+ * Add an additional chunk for the rspack runtime. Defaults to `true` when `target === 'web'`.
144
149
  */
145
150
  runtimeChunk?: boolean;
146
151
  /**
@@ -184,11 +189,7 @@ export interface NxAppRspackPluginOptions {
184
189
  */
185
190
  styles?: Array<ExtraEntryPointClass | string>;
186
191
  /**
187
- * Enables the use of subresource integrity validation.
188
- */
189
- subresourceIntegrity?: boolean;
190
- /**
191
- * Override the `target` option in webpack configuration. This setting is not recommended and exists for backwards compatibility.
192
+ * Override the `target` option in rspack configuration. This setting is not recommended and exists for backwards compatibility.
192
193
  */
193
194
  target?: string | string[];
194
195
  /**
@@ -0,0 +1,15 @@
1
+ import { type Compiler, type RspackPluginInstance } from '@rspack/core';
2
+ import { type ProjectGraph } from '@nx/devkit';
3
+ export declare class GeneratePackageJsonPlugin implements RspackPluginInstance {
4
+ private readonly options;
5
+ constructor(options: {
6
+ skipPackageManager?: boolean;
7
+ tsConfig: string;
8
+ outputFileName: string;
9
+ root: string;
10
+ projectName: string;
11
+ targetName: string;
12
+ projectGraph: ProjectGraph;
13
+ });
14
+ apply(compiler: Compiler): void;
15
+ }
@@ -0,0 +1,45 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.GeneratePackageJsonPlugin = void 0;
4
+ const core_1 = require("@rspack/core");
5
+ const js_1 = require("@nx/js");
6
+ const devkit_1 = require("@nx/devkit");
7
+ const pluginName = 'GeneratePackageJsonPlugin';
8
+ class GeneratePackageJsonPlugin {
9
+ constructor(options) {
10
+ this.options = options;
11
+ }
12
+ apply(compiler) {
13
+ compiler.hooks.thisCompilation.tap(pluginName, (compilation) => {
14
+ compilation.hooks.processAssets.tap({
15
+ name: pluginName,
16
+ stage: compiler.rspack.Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL,
17
+ }, () => {
18
+ const helperDependencies = (0, js_1.getHelperDependenciesFromProjectGraph)(this.options.root, this.options.projectName, this.options.projectGraph);
19
+ const importHelpers = !!(0, js_1.readTsConfig)(this.options.tsConfig).options
20
+ .importHelpers;
21
+ const shouldAddHelperDependency = importHelpers &&
22
+ helperDependencies.every((dep) => dep.target !== js_1.HelperDependency.tsc);
23
+ if (shouldAddHelperDependency) {
24
+ helperDependencies.push({
25
+ type: 'static',
26
+ source: this.options.projectName,
27
+ target: js_1.HelperDependency.tsc,
28
+ });
29
+ }
30
+ const packageJson = (0, js_1.createPackageJson)(this.options.projectName, this.options.projectGraph, {
31
+ target: this.options.targetName,
32
+ root: this.options.root,
33
+ isProduction: true,
34
+ helperDependencies: helperDependencies.map((dep) => dep.target),
35
+ skipPackageManager: this.options.skipPackageManager,
36
+ });
37
+ packageJson.main = packageJson.main ?? this.options.outputFileName;
38
+ compilation.emitAsset('package.json', new core_1.sources.RawSource((0, devkit_1.serializeJson)(packageJson)));
39
+ const packageManager = (0, devkit_1.detectPackageManager)(this.options.root);
40
+ compilation.emitAsset((0, js_1.getLockFileName)(packageManager), new core_1.sources.RawSource((0, js_1.createLockFile)(packageJson, this.options.projectGraph, packageManager)));
41
+ });
42
+ });
43
+ }
44
+ }
45
+ exports.GeneratePackageJsonPlugin = GeneratePackageJsonPlugin;
@@ -0,0 +1,4 @@
1
+ import { AssetGlobPattern, FileReplacement, NxAppRspackPluginOptions, NormalizedNxAppRspackPluginOptions } from '../models';
2
+ export declare function normalizeOptions(options: NxAppRspackPluginOptions): NormalizedNxAppRspackPluginOptions;
3
+ export declare function normalizeAssets(assets: any[], root: string, sourceRoot: string, projectRoot: string, resolveRelativePathsToProjectRoot?: boolean): AssetGlobPattern[];
4
+ export declare function normalizeFileReplacements(root: string, fileReplacements: FileReplacement[]): FileReplacement[];
@@ -0,0 +1,170 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.normalizeOptions = normalizeOptions;
4
+ exports.normalizeAssets = normalizeAssets;
5
+ exports.normalizeFileReplacements = normalizeFileReplacements;
6
+ const path_1 = require("path");
7
+ const fs_1 = require("fs");
8
+ const devkit_1 = require("@nx/devkit");
9
+ function normalizeOptions(options) {
10
+ const combinedPluginAndMaybeExecutorOptions = {};
11
+ const isProd = process.env.NODE_ENV === 'production';
12
+ // Since this is invoked by the executor, the graph has already been created and cached.
13
+ const projectGraph = (0, devkit_1.readCachedProjectGraph)();
14
+ const taskDetailsFromBuildTarget = process.env.NX_BUILD_TARGET
15
+ ? (0, devkit_1.parseTargetString)(process.env.NX_BUILD_TARGET, projectGraph)
16
+ : undefined;
17
+ const projectName = taskDetailsFromBuildTarget
18
+ ? taskDetailsFromBuildTarget.project
19
+ : process.env.NX_TASK_TARGET_PROJECT;
20
+ const targetName = taskDetailsFromBuildTarget
21
+ ? taskDetailsFromBuildTarget.target
22
+ : process.env.NX_TASK_TARGET_TARGET;
23
+ const configurationName = taskDetailsFromBuildTarget
24
+ ? taskDetailsFromBuildTarget.configuration
25
+ : process.env.NX_TASK_TARGET_CONFIGURATION;
26
+ const projectNode = projectGraph.nodes[projectName];
27
+ const targetConfig = projectNode.data.targets[targetName];
28
+ normalizeRelativePaths(projectNode.data.root, options);
29
+ // Merge options from `@nx/rspack:rspack` into plugin options.
30
+ // Options from `@nx/rspack:rspack` take precedence.
31
+ const originalTargetOptions = targetConfig.options;
32
+ if (configurationName) {
33
+ Object.assign(originalTargetOptions, targetConfig.configurations?.[configurationName]);
34
+ }
35
+ // This could be called from dev-server which means we need to read `buildTarget` to get actual build options.
36
+ // Otherwise, the options are passed from the `@nx/rspack:rspack` executor.
37
+ if (originalTargetOptions.buildTarget) {
38
+ const buildTargetOptions = targetConfig.options;
39
+ if (configurationName) {
40
+ Object.assign(buildTargetOptions, targetConfig.configurations?.[configurationName]);
41
+ }
42
+ Object.assign(combinedPluginAndMaybeExecutorOptions, options,
43
+ // executor options take precedence (especially for overriding with CLI args)
44
+ buildTargetOptions);
45
+ }
46
+ else {
47
+ Object.assign(combinedPluginAndMaybeExecutorOptions, options,
48
+ // executor options take precedence (especially for overriding with CLI args)
49
+ originalTargetOptions);
50
+ }
51
+ const sourceRoot = projectNode.data.sourceRoot ?? projectNode.data.root;
52
+ if (!combinedPluginAndMaybeExecutorOptions.main) {
53
+ throw new Error(`Missing "main" option for the entry file. Set this option in your Nx rspack plugin.`);
54
+ }
55
+ return {
56
+ ...combinedPluginAndMaybeExecutorOptions,
57
+ assets: combinedPluginAndMaybeExecutorOptions.assets
58
+ ? normalizeAssets(combinedPluginAndMaybeExecutorOptions.assets, devkit_1.workspaceRoot, sourceRoot, projectNode.data.root)
59
+ : [],
60
+ baseHref: combinedPluginAndMaybeExecutorOptions.baseHref ?? '/',
61
+ buildLibsFromSource: combinedPluginAndMaybeExecutorOptions.buildLibsFromSource ?? true,
62
+ commonChunk: combinedPluginAndMaybeExecutorOptions.commonChunk ?? true,
63
+ configurationName,
64
+ deleteOutputPath: combinedPluginAndMaybeExecutorOptions.deleteOutputPath ?? true,
65
+ extractCss: combinedPluginAndMaybeExecutorOptions.extractCss ?? true,
66
+ fileReplacements: normalizeFileReplacements(devkit_1.workspaceRoot, combinedPluginAndMaybeExecutorOptions.fileReplacements),
67
+ generateIndexHtml: combinedPluginAndMaybeExecutorOptions.generateIndexHtml ?? true,
68
+ main: combinedPluginAndMaybeExecutorOptions.main,
69
+ namedChunks: combinedPluginAndMaybeExecutorOptions.namedChunks ?? !isProd,
70
+ optimization: combinedPluginAndMaybeExecutorOptions.optimization ?? isProd,
71
+ outputFileName: combinedPluginAndMaybeExecutorOptions.outputFileName ?? 'main.js',
72
+ outputHashing: combinedPluginAndMaybeExecutorOptions.outputHashing ??
73
+ (isProd ? 'all' : 'none'),
74
+ outputPath: combinedPluginAndMaybeExecutorOptions.outputPath,
75
+ projectGraph,
76
+ projectName,
77
+ projectRoot: projectNode.data.root,
78
+ root: devkit_1.workspaceRoot,
79
+ runtimeChunk: combinedPluginAndMaybeExecutorOptions.runtimeChunk ?? true,
80
+ scripts: combinedPluginAndMaybeExecutorOptions.scripts ?? [],
81
+ sourceMap: combinedPluginAndMaybeExecutorOptions.sourceMap ?? !isProd,
82
+ sourceRoot,
83
+ styles: combinedPluginAndMaybeExecutorOptions.styles ?? [],
84
+ target: combinedPluginAndMaybeExecutorOptions.target,
85
+ targetName,
86
+ vendorChunk: combinedPluginAndMaybeExecutorOptions.vendorChunk ?? !isProd,
87
+ };
88
+ }
89
+ function normalizeAssets(assets, root, sourceRoot, projectRoot, resolveRelativePathsToProjectRoot = true) {
90
+ return assets.map((asset) => {
91
+ if (typeof asset === 'string') {
92
+ const assetPath = (0, devkit_1.normalizePath)(asset);
93
+ const resolvedAssetPath = (0, path_1.resolve)(root, assetPath);
94
+ const resolvedSourceRoot = (0, path_1.resolve)(root, sourceRoot);
95
+ if (!resolvedAssetPath.startsWith(resolvedSourceRoot)) {
96
+ throw new Error(`The ${resolvedAssetPath} asset path must start with the project source root: ${sourceRoot}`);
97
+ }
98
+ const isDirectory = (0, fs_1.statSync)(resolvedAssetPath).isDirectory();
99
+ const input = isDirectory
100
+ ? resolvedAssetPath
101
+ : (0, path_1.dirname)(resolvedAssetPath);
102
+ const output = (0, path_1.relative)(resolvedSourceRoot, (0, path_1.resolve)(root, input));
103
+ const glob = isDirectory ? '**/*' : (0, path_1.basename)(resolvedAssetPath);
104
+ return {
105
+ input,
106
+ output,
107
+ glob,
108
+ };
109
+ }
110
+ else {
111
+ if (asset.output.startsWith('..')) {
112
+ throw new Error('An asset cannot be written to a location outside of the output path.');
113
+ }
114
+ const assetPath = (0, devkit_1.normalizePath)(asset.input);
115
+ let resolvedAssetPath = (0, path_1.resolve)(root, assetPath);
116
+ if (resolveRelativePathsToProjectRoot && asset.input.startsWith('.')) {
117
+ const resolvedProjectRoot = (0, path_1.resolve)(root, projectRoot);
118
+ resolvedAssetPath = (0, path_1.resolve)(resolvedProjectRoot, assetPath);
119
+ }
120
+ return {
121
+ ...asset,
122
+ input: resolvedAssetPath,
123
+ // Now we remove starting slash to make rspack place it from the output root.
124
+ output: asset.output.replace(/^\//, ''),
125
+ };
126
+ }
127
+ });
128
+ }
129
+ function normalizeFileReplacements(root, fileReplacements) {
130
+ return fileReplacements
131
+ ? fileReplacements.map((fileReplacement) => ({
132
+ replace: (0, path_1.resolve)(root, fileReplacement.replace),
133
+ with: (0, path_1.resolve)(root, fileReplacement.with),
134
+ }))
135
+ : [];
136
+ }
137
+ function normalizeRelativePaths(projectRoot, options) {
138
+ for (const [fieldName, fieldValue] of Object.entries(options)) {
139
+ if (isRelativePath(fieldValue)) {
140
+ options[fieldName] = (0, path_1.join)(projectRoot, fieldValue);
141
+ }
142
+ else if (fieldName === 'additionalEntryPoints') {
143
+ for (let i = 0; i < fieldValue.length; i++) {
144
+ const v = fieldValue[i];
145
+ if (isRelativePath(v)) {
146
+ fieldValue[i] = {
147
+ entryName: (0, path_1.parse)(v).name,
148
+ entryPath: (0, path_1.join)(projectRoot, v),
149
+ };
150
+ }
151
+ else if (isRelativePath(v.entryPath)) {
152
+ v.entryPath = (0, path_1.join)(projectRoot, v.entryPath);
153
+ }
154
+ }
155
+ }
156
+ else if (Array.isArray(fieldValue)) {
157
+ for (let i = 0; i < fieldValue.length; i++) {
158
+ if (isRelativePath(fieldValue[i])) {
159
+ fieldValue[i] = (0, path_1.join)(projectRoot, fieldValue[i]);
160
+ }
161
+ }
162
+ }
163
+ }
164
+ }
165
+ function isRelativePath(val) {
166
+ return (typeof val === 'string' &&
167
+ (val.startsWith('./') ||
168
+ // Windows
169
+ val.startsWith('.\\')));
170
+ }
@@ -0,0 +1,10 @@
1
+ import { Compiler, type Configuration, type RspackOptionsNormalized } from '@rspack/core';
2
+ import { NormalizedNxAppRspackPluginOptions } from '../models';
3
+ export declare class NxTsconfigPathsRspackPlugin {
4
+ private options;
5
+ private tmpTsConfigPath;
6
+ constructor(options: NormalizedNxAppRspackPluginOptions);
7
+ apply(compiler: Compiler): void;
8
+ cleanupTmpTsConfigFile(): void;
9
+ handleBuildLibsFromSource(config: Partial<RspackOptionsNormalized | Configuration>, options: any): void;
10
+ }
@@ -0,0 +1,62 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.NxTsconfigPathsRspackPlugin = void 0;
4
+ const tslib_1 = require("tslib");
5
+ const path = tslib_1.__importStar(require("path"));
6
+ const devkit_1 = require("@nx/devkit");
7
+ const buildable_libs_utils_1 = require("@nx/js/src/utils/buildable-libs-utils");
8
+ const rspack_nx_build_coordination_plugin_1 = require("./rspack-nx-build-coordination-plugin");
9
+ const fs_1 = require("fs");
10
+ class NxTsconfigPathsRspackPlugin {
11
+ constructor(options) {
12
+ this.options = options;
13
+ if (!this.options.tsConfig)
14
+ throw new Error(`Missing "tsConfig" option. Set this option in your Nx rspack plugin.`);
15
+ }
16
+ apply(compiler) {
17
+ // TODO(Colum): Investigate the best way to handle this, currently it is not working and affecting HMR
18
+ // // If we are not building libs from source, we need to remap paths so tsconfig may be updated.
19
+ // this.handleBuildLibsFromSource(compiler.options, this.options);
20
+ const pathToTsconfig = !path.isAbsolute(this.options.tsConfig)
21
+ ? path.join(devkit_1.workspaceRoot, this.options.tsConfig)
22
+ : this.options.tsConfig;
23
+ const extensions = new Set([
24
+ ...['.ts', '.tsx', '.mjs', '.js', '.jsx'],
25
+ ...(compiler.options?.resolve?.extensions ?? []),
26
+ ]);
27
+ compiler.options.resolve = {
28
+ ...compiler.options.resolve,
29
+ extensions: [...extensions],
30
+ tsConfig: { configFile: pathToTsconfig },
31
+ };
32
+ }
33
+ cleanupTmpTsConfigFile() {
34
+ if (this.tmpTsConfigPath) {
35
+ try {
36
+ if (this.tmpTsConfigPath) {
37
+ (0, fs_1.unlinkSync)(this.tmpTsConfigPath);
38
+ }
39
+ }
40
+ catch (e) { }
41
+ }
42
+ }
43
+ handleBuildLibsFromSource(config, options) {
44
+ if (!options.buildLibsFromSource && options.targetName) {
45
+ const remappedTarget = options.targetName === 'serve' ? 'build' : options.targetName;
46
+ const { target, dependencies } = (0, buildable_libs_utils_1.calculateProjectBuildableDependencies)(undefined, options.projectGraph, options.root, options.projectName, remappedTarget, options.configurationName);
47
+ options.tsConfig = (0, buildable_libs_utils_1.createTmpTsConfig)(options.tsConfig, options.root, target.data.root, dependencies);
48
+ this.tmpTsConfigPath = options.tsConfig;
49
+ if (options.targetName === 'serve') {
50
+ const buildableDependencies = dependencies
51
+ .filter((dependency) => dependency.node.type === 'lib')
52
+ .map((dependency) => dependency.node.name)
53
+ .join(',');
54
+ const buildCommand = `nx run-many --target=build --projects=${buildableDependencies}`;
55
+ if (buildableDependencies && buildableDependencies.length > 0) {
56
+ config.plugins.push(new rspack_nx_build_coordination_plugin_1.RspackNxBuildCoordinationPlugin(buildCommand));
57
+ }
58
+ }
59
+ }
60
+ }
61
+ }
62
+ exports.NxTsconfigPathsRspackPlugin = NxTsconfigPathsRspackPlugin;
@@ -0,0 +1,11 @@
1
+ import type { Compiler } from '@rspack/core';
2
+ export declare class RspackNxBuildCoordinationPlugin {
3
+ private readonly buildCmd;
4
+ private currentlyRunning;
5
+ private buildCmdProcess;
6
+ constructor(buildCmd: string, skipInitialBuild?: boolean);
7
+ apply(compiler: Compiler): void;
8
+ startWatchingBuildableLibs(): Promise<void>;
9
+ buildChangedProjects(): Promise<void>;
10
+ private createFileWatcher;
11
+ }