@nx/rspack 21.4.0 → 21.5.0-beta.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/generators.json CHANGED
@@ -29,7 +29,7 @@
29
29
  "x-deprecated": "This generator will be removed in Nx 22. Please use the equivalent generator for your application type instead."
30
30
  },
31
31
  "convert-webpack": {
32
- "alias": "convert-to-rspack",
32
+ "aliases": ["convert-to-rspack"],
33
33
  "factory": "./src/generators/convert-webpack/convert-webpack",
34
34
  "schema": "./src/generators/convert-webpack/schema.json",
35
35
  "description": "Convert a webpack application to use rspack."
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@nx/rspack",
3
3
  "description": "The Nx Plugin for Rspack contains executors and generators that support building applications using Rspack.",
4
- "version": "21.4.0",
4
+ "version": "21.5.0-beta.1",
5
5
  "type": "commonjs",
6
6
  "repository": {
7
7
  "type": "git",
@@ -24,10 +24,10 @@
24
24
  "generators": "./generators.json",
25
25
  "executors": "./executors.json",
26
26
  "dependencies": {
27
- "@nx/js": "21.4.0",
28
- "@nx/devkit": "21.4.0",
29
- "@nx/web": "21.4.0",
30
- "@nx/module-federation": "21.4.0",
27
+ "@nx/js": "21.5.0-beta.1",
28
+ "@nx/devkit": "21.5.0-beta.1",
29
+ "@nx/web": "21.5.0-beta.1",
30
+ "@nx/module-federation": "21.5.0-beta.1",
31
31
  "@phenomnomnominal/tsquery": "~5.0.1",
32
32
  "@rspack/core": "^1.3.8",
33
33
  "@rspack/dev-server": "^1.1.1",
@@ -53,11 +53,12 @@
53
53
  "postcss-loader": "^8.1.1",
54
54
  "postcss": "^8.4.38",
55
55
  "tslib": "^2.3.0",
56
- "webpack": "^5.80.0",
56
+ "webpack": "^5.101.3",
57
57
  "webpack-node-externals": "^3.0.0"
58
58
  },
59
59
  "devDependencies": {
60
- "nx": "21.4.0"
60
+ "nx": "21.5.0-beta.1",
61
+ "@nx/nest": "21.5.0-beta.1"
61
62
  },
62
63
  "peerDependencies": {
63
64
  "@module-federation/enhanced": "^0.18.0",
@@ -1 +1 @@
1
- {"version":3,"file":"convert-webpack.d.ts","sourceRoot":"","sources":["../../../../../../packages/rspack/src/generators/convert-webpack/convert-webpack.ts"],"names":[],"mappings":"AAAA,OAAO,EAKL,KAAK,IAAI,EAGV,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAQlC,yBAA+B,IAAI,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,mDA8GzD"}
1
+ {"version":3,"file":"convert-webpack.d.ts","sourceRoot":"","sources":["../../../../../../packages/rspack/src/generators/convert-webpack/convert-webpack.ts"],"names":[],"mappings":"AAAA,OAAO,EAML,KAAK,IAAI,EAGV,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AASlC,yBAA+B,IAAI,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,mDAwJzD"}
@@ -5,13 +5,15 @@ const devkit_1 = require("@nx/devkit");
5
5
  const versions_1 = require("../../utils/versions");
6
6
  const transform_esm_1 = require("./lib/transform-esm");
7
7
  const transform_cjs_1 = require("./lib/transform-cjs");
8
+ const transform_plugin_config_1 = require("./lib/transform-plugin-config");
8
9
  async function default_1(tree, options) {
9
10
  const projects = (0, devkit_1.getProjects)(tree);
10
11
  if (!projects.has(options.project)) {
11
12
  throw new Error(`Could not find project '${options.project}'. Ensure you have specified the project you'd like to convert correctly.`);
12
13
  }
13
14
  const project = projects.get(options.project);
14
- const webpackConfigsToConvert = [];
15
+ const webpackConfigsWithHelpersToConvert = [];
16
+ const webpackConfigsWithPluginsToConvert = [];
15
17
  for (const [targetName, target] of Object.entries(project.targets)) {
16
18
  if (target.executor === '@nx/webpack:webpack') {
17
19
  target.executor = '@nx/rspack:rspack';
@@ -23,7 +25,10 @@ async function default_1(tree, options) {
23
25
  return;
24
26
  }
25
27
  const rspackConfigPath = options.webpackConfig.replace(/webpack(?!.*webpack)/, 'rspack');
26
- webpackConfigsToConvert.push([options.webpackConfig, rspackConfigPath]);
28
+ webpackConfigsWithHelpersToConvert.push([
29
+ options.webpackConfig,
30
+ rspackConfigPath,
31
+ ]);
27
32
  options.rspackConfig = rspackConfigPath;
28
33
  delete options.webpackConfig;
29
34
  };
@@ -36,6 +41,22 @@ async function default_1(tree, options) {
36
41
  }
37
42
  }
38
43
  }
44
+ else if ((target.executor === 'nx:run-commands' && target.options.command) ||
45
+ target.command === 'webpack-cli build') {
46
+ if (target.options?.command) {
47
+ target.options.command = 'rspack build';
48
+ }
49
+ else if (target.command) {
50
+ target.command = 'rspack build';
51
+ }
52
+ const webpackConfigPath = findWebpackConfigPath(tree, project.root);
53
+ if (webpackConfigPath) {
54
+ webpackConfigsWithPluginsToConvert.push([
55
+ webpackConfigPath,
56
+ webpackConfigPath.replace(/webpack(?!.*webpack)/, 'rspack'),
57
+ ]);
58
+ }
59
+ }
39
60
  else if (target.executor === '@nx/webpack:dev-server') {
40
61
  target.executor = '@nx/rspack:dev-server';
41
62
  }
@@ -52,9 +73,18 @@ async function default_1(tree, options) {
52
73
  target.executor = '@nx/rspack:module-federation-static-server';
53
74
  }
54
75
  }
55
- for (const [webpackConfigPath, rspackConfigPath] of webpackConfigsToConvert) {
76
+ if (webpackConfigsWithHelpersToConvert.length === 0 &&
77
+ webpackConfigsWithPluginsToConvert.length === 0) {
78
+ console.error(`Project '${options.project}' does not have any webpack targets to convert.`);
79
+ return;
80
+ }
81
+ for (const [webpackConfigPath, rspackConfigPath,] of webpackConfigsWithHelpersToConvert) {
56
82
  tree.rename(webpackConfigPath, rspackConfigPath);
57
- transformConfigFile(tree, rspackConfigPath);
83
+ transformConfigFileWithHelpers(tree, rspackConfigPath);
84
+ }
85
+ for (const [webpackConfigPath, rspackConfigPath,] of webpackConfigsWithPluginsToConvert) {
86
+ tree.rename(webpackConfigPath, rspackConfigPath);
87
+ transformConfigFileWithPlugins(tree, rspackConfigPath);
58
88
  }
59
89
  (0, devkit_1.updateProjectConfiguration)(tree, options.project, project);
60
90
  const nxJson = (0, devkit_1.readNxJson)(tree);
@@ -89,7 +119,10 @@ async function default_1(tree, options) {
89
119
  }
90
120
  return installTask;
91
121
  }
92
- function transformConfigFile(tree, configPath) {
122
+ function transformConfigFileWithPlugins(tree, configPath) {
123
+ (0, transform_plugin_config_1.transformPluginConfig)(tree, configPath);
124
+ }
125
+ function transformConfigFileWithHelpers(tree, configPath) {
93
126
  (0, transform_esm_1.transformEsmConfigFile)(tree, configPath);
94
127
  (0, transform_cjs_1.transformCjsConfigFile)(tree, configPath);
95
128
  cleanupEmptyImports(tree, configPath);
@@ -109,3 +142,19 @@ function cleanupEmptyImports(tree, configPath) {
109
142
  newContents = newContents.replace(emptyConstRequires, '');
110
143
  tree.write(configPath, newContents);
111
144
  }
145
+ function findWebpackConfigPath(tree, projectRoot) {
146
+ const possibleConfigPaths = [
147
+ 'webpack.config.js',
148
+ 'webpack.config.mjs',
149
+ 'webpack.config.cjs',
150
+ 'webpack.config.ts',
151
+ 'webpack.config.mts',
152
+ 'webpack.config.cts',
153
+ ];
154
+ for (const configPath of possibleConfigPaths) {
155
+ const possiblePath = (0, devkit_1.joinPathFragments)(projectRoot, configPath);
156
+ if (tree.exists(possiblePath)) {
157
+ return possiblePath;
158
+ }
159
+ }
160
+ }
@@ -0,0 +1,3 @@
1
+ import { type Tree } from '@nx/devkit';
2
+ export declare function transformPluginConfig(tree: Tree, webpackConfigPath: string): void;
3
+ //# sourceMappingURL=transform-plugin-config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"transform-plugin-config.d.ts","sourceRoot":"","sources":["../../../../../../../packages/rspack/src/generators/convert-webpack/lib/transform-plugin-config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,IAAI,EAAE,MAAM,YAAY,CAAC;AAIvC,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,IAAI,EAAE,iBAAiB,EAAE,MAAM,QAU1E"}
@@ -0,0 +1,86 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.transformPluginConfig = transformPluginConfig;
4
+ const tsquery_1 = require("@phenomnomnominal/tsquery");
5
+ function transformPluginConfig(tree, webpackConfigPath) {
6
+ const webpackConfigContents = tree.read(webpackConfigPath, 'utf-8');
7
+ const ast = tsquery_1.tsquery.ast(webpackConfigContents);
8
+ let newConfigContents = webpackConfigContents;
9
+ if (webpackConfigContents.includes("require('@nx/webpack/app-plugin')")) {
10
+ newConfigContents = transformCjsConfig(tree, webpackConfigContents, ast);
11
+ }
12
+ else {
13
+ newConfigContents = transformEsmConfig(tree, webpackConfigContents, ast);
14
+ }
15
+ tree.write(webpackConfigPath, newConfigContents);
16
+ }
17
+ function transformCjsConfig(tree, webpackConfigContents, ast) {
18
+ // Convert require('@nx/webpack/app-plugin') to require('@nx/rspack/app-plugin')
19
+ const WEBPACK_APP_PLUGIN_REQUIRE_SELECTOR = 'CallExpression:has(Identifier[name=require]) > StringLiteral[value=@nx/webpack/app-plugin]';
20
+ let nodes = (0, tsquery_1.tsquery)(ast, WEBPACK_APP_PLUGIN_REQUIRE_SELECTOR, {
21
+ visitAllChildren: true,
22
+ });
23
+ if (nodes.length === 0) {
24
+ return webpackConfigContents;
25
+ }
26
+ const requireNode = nodes[0];
27
+ webpackConfigContents = `${webpackConfigContents.slice(0, requireNode.getStart())}'@nx/rspack/app-plugin'${webpackConfigContents.slice(requireNode.getEnd())}`;
28
+ // Convert const { NxAppWebpackPlugin } to const { NxAppRspackPlugin }
29
+ ast = tsquery_1.tsquery.ast(webpackConfigContents);
30
+ const WEBPACK_APP_BINDING_ELEMENT_SELECTOR = 'BindingElement:has(Identifier[name=NxAppWebpackPlugin])';
31
+ nodes = (0, tsquery_1.tsquery)(ast, WEBPACK_APP_BINDING_ELEMENT_SELECTOR, {
32
+ visitAllChildren: true,
33
+ });
34
+ if (nodes.length === 0) {
35
+ return webpackConfigContents;
36
+ }
37
+ const bindingElement = nodes[0];
38
+ webpackConfigContents = `${webpackConfigContents.slice(0, bindingElement.getStart())}NxAppRspackPlugin${webpackConfigContents.slice(bindingElement.getEnd())}`;
39
+ // Convert new NxAppWebpackPlugin() to new NxAppRspackPlugin()
40
+ ast = tsquery_1.tsquery.ast(webpackConfigContents);
41
+ const WEBPACK_APP_INSTANTIATION_SELECTOR = 'NewExpression > Identifier[name=NxAppWebpackPlugin]';
42
+ nodes = (0, tsquery_1.tsquery)(ast, WEBPACK_APP_INSTANTIATION_SELECTOR, {
43
+ visitAllChildren: true,
44
+ });
45
+ if (nodes.length === 0) {
46
+ return webpackConfigContents;
47
+ }
48
+ const instantiation = nodes[0];
49
+ webpackConfigContents = `${webpackConfigContents.slice(0, instantiation.getStart())}NxAppRspackPlugin${webpackConfigContents.slice(instantiation.getEnd())}`;
50
+ return webpackConfigContents;
51
+ }
52
+ function transformEsmConfig(tree, webpackConfigContents, ast) {
53
+ // Convert from '@nx/webpack/app-plugin' to from '@nx/rspack/app-plugin'
54
+ const WEBPACK_APP_PLUGIN_IMPORT_SELECTOR = 'ImportClause ~ StringLiteral[value=@nx/webpack/app-plugin]';
55
+ let nodes = (0, tsquery_1.tsquery)(ast, WEBPACK_APP_PLUGIN_IMPORT_SELECTOR, {
56
+ visitAllChildren: true,
57
+ });
58
+ if (nodes.length === 0) {
59
+ return webpackConfigContents;
60
+ }
61
+ const importNode = nodes[0];
62
+ webpackConfigContents = `${webpackConfigContents.slice(0, importNode.getStart())}'@nx/rspack/app-plugin'${webpackConfigContents.slice(importNode.getEnd())}`;
63
+ // Convert import { NxAppWebpackPlugin } to import { NxAppRspackPlugin }
64
+ ast = tsquery_1.tsquery.ast(webpackConfigContents);
65
+ const WEBPACK_APP_IMPORT_SPECIFIER_SELECTOR = 'ImportSpecifier > Identifier[name=NxAppWebpackPlugin]';
66
+ nodes = (0, tsquery_1.tsquery)(ast, WEBPACK_APP_IMPORT_SPECIFIER_SELECTOR, {
67
+ visitAllChildren: true,
68
+ });
69
+ if (nodes.length === 0) {
70
+ return webpackConfigContents;
71
+ }
72
+ const importSpecifier = nodes[0];
73
+ webpackConfigContents = `${webpackConfigContents.slice(0, importSpecifier.getStart())}NxAppRspackPlugin${webpackConfigContents.slice(importSpecifier.getEnd())}`;
74
+ // Convert new NxAppWebpackPlugin() to new NxAppRspackPlugin()
75
+ ast = tsquery_1.tsquery.ast(webpackConfigContents);
76
+ const WEBPACK_APP_INSTANTIATION_SELECTOR = 'NewExpression > Identifier[name=NxAppWebpackPlugin]';
77
+ nodes = (0, tsquery_1.tsquery)(ast, WEBPACK_APP_INSTANTIATION_SELECTOR, {
78
+ visitAllChildren: true,
79
+ });
80
+ if (nodes.length === 0) {
81
+ return webpackConfigContents;
82
+ }
83
+ const instantiation = nodes[0];
84
+ webpackConfigContents = `${webpackConfigContents.slice(0, instantiation.getStart())}NxAppRspackPlugin${webpackConfigContents.slice(instantiation.getEnd())}`;
85
+ return webpackConfigContents;
86
+ }
@@ -1 +1 @@
1
- {"version":3,"file":"postcss-cli-resources.d.ts","sourceRoot":"","sources":["../../../../../../../packages/rspack/src/plugins/utils/plugins/postcss-cli-resources.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAalD,MAAM,WAAW,0BAA0B;IACzC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,aAAa,CAAC,OAAO,CAAC,CAAC;IAC/B,UAAU,EAAE,MAAM,CAAC;CACpB;AAgBD,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,0BAA0B;;;EA4JtE"}
1
+ {"version":3,"file":"postcss-cli-resources.d.ts","sourceRoot":"","sources":["../../../../../../../packages/rspack/src/plugins/utils/plugins/postcss-cli-resources.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAalD,MAAM,WAAW,0BAA0B;IACzC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,aAAa,CAAC,OAAO,CAAC,CAAC;IAC/B,UAAU,EAAE,MAAM,CAAC;CACpB;AAgBD,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,0BAA0B;;;EA8JtE"}
@@ -4,7 +4,6 @@ exports.PostcssCliResources = PostcssCliResources;
4
4
  const tslib_1 = require("tslib");
5
5
  const loader_utils_1 = require("loader-utils");
6
6
  const path = tslib_1.__importStar(require("path"));
7
- const url = tslib_1.__importStar(require("node:url"));
8
7
  function wrapUrl(url) {
9
8
  let wrappedUrl;
10
9
  const hasSingleQuotes = url.indexOf("'") >= 0;
@@ -68,7 +67,9 @@ function PostcssCliResources(options) {
68
67
  resourceCache.set(cacheKey, outputUrl);
69
68
  return outputUrl;
70
69
  }
71
- const { pathname, hash, search } = url.parse(inputUrl.replace(/\\/g, '/'));
70
+ const normalizedUrl = inputUrl.replace(/\\/g, '/');
71
+ const parsedUrl = new URL(normalizedUrl, 'file:///');
72
+ const { pathname, hash, search } = parsedUrl;
72
73
  const resolver = (file, base) => new Promise((resolve, reject) => {
73
74
  loader.resolve(base, decodeURI(file), (err, result) => {
74
75
  if (err) {
@@ -93,11 +94,11 @@ function PostcssCliResources(options) {
93
94
  loader.emitFile(outputPath, content, undefined);
94
95
  let outputUrl = outputPath.replace(/\\/g, '/');
95
96
  if (hash || search) {
96
- outputUrl = url.format({ pathname: outputUrl, hash, search });
97
+ outputUrl = outputUrl + (search || '') + (hash || '');
97
98
  }
98
99
  const loaderOptions = loader.loaders[loader.loaderIndex].options;
99
100
  if (deployUrl && loaderOptions.ident !== 'extracted') {
100
- outputUrl = url.resolve(deployUrl, outputUrl);
101
+ outputUrl = new URL(outputUrl, deployUrl).href;
101
102
  }
102
103
  resourceCache.set(cacheKey, outputUrl);
103
104
  resolve(outputUrl);