@nx/react 0.0.0-pr-29720-06f67e5 → 0.0.0-pr-3-4fa8cf8
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/package.json +6 -6
- package/router-plugin.d.ts +1 -0
- package/router-plugin.js +5 -0
- package/src/generators/application/application.js +48 -9
- package/src/generators/application/files/react-router-ssr/common/app/app-nav.tsx__tmpl__ +15 -0
- package/src/generators/application/files/react-router-ssr/common/app/entry.client.tsx__tmpl__ +18 -0
- package/src/generators/application/files/react-router-ssr/common/app/entry.server.tsx__tmpl__ +74 -0
- package/src/generators/application/files/react-router-ssr/common/app/root.tsx__tmpl__ +51 -0
- package/src/generators/application/files/react-router-ssr/common/app/routes/about.tsx__tmpl__ +7 -0
- package/src/generators/application/files/react-router-ssr/common/app/routes.tsx__tmpl__ +6 -0
- package/src/generators/application/files/react-router-ssr/common/public/favicon.ico +0 -0
- package/src/generators/application/files/react-router-ssr/common/react-router.config.ts__tmpl__ +5 -0
- package/src/generators/application/files/react-router-ssr/common/tests/routes/_index.spec.tsx__tmpl__ +16 -0
- package/src/generators/application/files/react-router-ssr/common/tsconfig.app.json__tmpl__ +23 -0
- package/src/generators/application/files/react-router-ssr/common/tsconfig.json__tmpl__ +27 -0
- package/src/generators/application/files/react-router-ssr/non-root/.gitignore__tmpl__ +5 -0
- package/src/generators/application/files/react-router-ssr/non-root/package.json__tmpl__ +24 -0
- package/src/generators/application/files/react-router-ssr/nx-welcome/claimed/app/nx-welcome.tsx__tmpl__ +866 -0
- package/src/generators/application/files/react-router-ssr/nx-welcome/not-configured/app/nx-welcome.tsx__tmpl__ +866 -0
- package/src/generators/application/files/react-router-ssr/nx-welcome/unclaimed/app/nx-welcome.tsx__tmpl__ +864 -0
- package/src/generators/application/files/react-router-ssr/ts-solution/package.json__tmpl__ +24 -0
- package/src/generators/application/files/react-router-ssr/ts-solution/tsconfig.app.json__tmpl__ +39 -0
- package/src/generators/application/lib/add-e2e.js +29 -24
- package/src/generators/application/lib/add-linting.d.ts +1 -0
- package/src/generators/application/lib/add-linting.js +38 -0
- package/src/generators/application/lib/add-project.js +31 -15
- package/src/generators/application/lib/add-routing.js +1 -1
- package/src/generators/application/lib/bundlers/add-vite.js +15 -6
- package/src/generators/application/lib/create-application-files.js +41 -4
- package/src/generators/application/lib/install-common-dependencies.js +13 -2
- package/src/generators/application/lib/normalize-options.d.ts +0 -2
- package/src/generators/application/lib/normalize-options.js +11 -20
- package/src/generators/application/schema.d.ts +5 -1
- package/src/generators/application/schema.json +10 -1
- package/src/generators/host/host.js +6 -3
- package/src/generators/init/init.js +23 -0
- package/src/generators/init/schema.d.ts +2 -0
- package/src/generators/library/lib/add-rollup-build-target.d.ts +3 -1
- package/src/generators/library/lib/add-rollup-build-target.js +6 -7
- package/src/generators/library/lib/create-files.js +2 -1
- package/src/generators/library/lib/normalize-options.js +8 -5
- package/src/generators/library/library.js +21 -15
- package/src/generators/library/schema.d.ts +2 -0
- package/src/generators/library/schema.json +4 -0
- package/src/generators/remote/remote.js +12 -9
- package/src/plugins/router-plugin.d.ts +10 -0
- package/src/plugins/router-plugin.js +219 -0
- package/src/utils/ast-utils.d.ts +1 -1
- package/src/utils/ast-utils.js +2 -2
- package/src/utils/versions.d.ts +3 -1
- package/src/utils/versions.js +6 -3
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "<%= projectName %>",
|
|
3
|
+
"private": true,
|
|
4
|
+
"type": "module",
|
|
5
|
+
"scripts": {},
|
|
6
|
+
"dependencies": {
|
|
7
|
+
"@react-router/node": "<%= reactRouterVersion %>",
|
|
8
|
+
"@react-router/serve": "<%= reactRouterVersion %>",
|
|
9
|
+
"isbot": "<%= reactRouterIsBotVersion %>",
|
|
10
|
+
"react": "<%= reactVersion %>",
|
|
11
|
+
"react-dom": "<%= reactVersion %>",
|
|
12
|
+
"react-router": "<%= reactRouterVersion %>"
|
|
13
|
+
},
|
|
14
|
+
"devDependencies": {
|
|
15
|
+
"@react-router/dev": "<%= reactRouterVersion %>",
|
|
16
|
+
"@types/node": "<%= typesNodeVersion %>",
|
|
17
|
+
"@types/react": "<%= reactVersion %>",
|
|
18
|
+
"@types/react-dom": "<%= reactVersion %>"
|
|
19
|
+
},
|
|
20
|
+
"engines": {
|
|
21
|
+
"node": ">=20"
|
|
22
|
+
},
|
|
23
|
+
"sideEffects": false,
|
|
24
|
+
}
|
package/src/generators/application/files/react-router-ssr/ts-solution/tsconfig.app.json__tmpl__
ADDED
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "<%= offsetFromRoot %>tsconfig.base.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"outDir": "dist",
|
|
5
|
+
"lib": ["DOM", "DOM.Iterable", "ES2019"],
|
|
6
|
+
"types": ["@react-router/node", "vite/client"],
|
|
7
|
+
"isolatedModules": true,
|
|
8
|
+
"esModuleInterop": true,
|
|
9
|
+
"jsx": "react-jsx",
|
|
10
|
+
"module": "ESNext",
|
|
11
|
+
"moduleResolution": "Bundler",
|
|
12
|
+
"resolveJsonModule": true,
|
|
13
|
+
"target": "ES2022",
|
|
14
|
+
"strict": true,
|
|
15
|
+
"allowJs": true,
|
|
16
|
+
"skipLibCheck": true,
|
|
17
|
+
"forceConsistentCasingInFileNames": true
|
|
18
|
+
},
|
|
19
|
+
"include": [
|
|
20
|
+
"app/**/*.ts",
|
|
21
|
+
"app/**/*.tsx",
|
|
22
|
+
"app/**/*.js",
|
|
23
|
+
"app/**/*.jsx",
|
|
24
|
+
"**/.server/**/*.ts",
|
|
25
|
+
"**/.server/**/*.tsx",
|
|
26
|
+
"**/.client/**/*.ts",
|
|
27
|
+
"**/.client/**/*.tsx"
|
|
28
|
+
],
|
|
29
|
+
"exclude": [
|
|
30
|
+
"tests/**/*.spec.ts",
|
|
31
|
+
"tests/**/*.test.ts",
|
|
32
|
+
"tests/**/*.spec.tsx",
|
|
33
|
+
"tests/**/*.test.tsx",
|
|
34
|
+
"tests/**/*.spec.js",
|
|
35
|
+
"tests/**/*.test.js",
|
|
36
|
+
"tests/**/*.spec.jsx",
|
|
37
|
+
"tests/**/*.test.jsx"
|
|
38
|
+
]
|
|
39
|
+
}
|
|
@@ -28,8 +28,10 @@ async function addE2e(tree, options) {
|
|
|
28
28
|
e2eWebServerInfo = await getWebpackE2EWebServerInfo(tree, options.projectName, (0, devkit_1.joinPathFragments)(options.appProjectRoot, `webpack.config.${options.js ? 'js' : 'ts'}`), options.addPlugin, options.devServerPort ?? 4200);
|
|
29
29
|
}
|
|
30
30
|
else if (options.bundler === 'vite') {
|
|
31
|
-
const { getViteE2EWebServerInfo } = (0, devkit_1.ensurePackage)('@nx/vite', versions_1.nxVersion);
|
|
32
|
-
e2eWebServerInfo =
|
|
31
|
+
const { getViteE2EWebServerInfo, getReactRouterE2EWebServerInfo } = (0, devkit_1.ensurePackage)('@nx/vite', versions_1.nxVersion);
|
|
32
|
+
e2eWebServerInfo = options.useReactRouter
|
|
33
|
+
? await getReactRouterE2EWebServerInfo(tree, options.projectName, (0, devkit_1.joinPathFragments)(options.appProjectRoot, `vite.config.${options.js ? 'js' : 'ts'}`), options.addPlugin, options.devServerPort ?? 4200)
|
|
34
|
+
: await getViteE2EWebServerInfo(tree, options.projectName, (0, devkit_1.joinPathFragments)(options.appProjectRoot, `vite.config.${options.js ? 'js' : 'ts'}`), options.addPlugin, options.devServerPort ?? 4200);
|
|
33
35
|
}
|
|
34
36
|
else if (options.bundler === 'rsbuild') {
|
|
35
37
|
(0, devkit_1.ensurePackage)('@nx/rsbuild', versions_1.nxVersion);
|
|
@@ -46,17 +48,15 @@ async function addE2e(tree, options) {
|
|
|
46
48
|
switch (options.e2eTestRunner) {
|
|
47
49
|
case 'cypress': {
|
|
48
50
|
const { configurationGenerator } = (0, devkit_1.ensurePackage)('@nx/cypress', versions_1.nxVersion);
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
},
|
|
59
|
-
});
|
|
51
|
+
const packageJson = {
|
|
52
|
+
name: options.e2eProjectName,
|
|
53
|
+
version: '0.0.1',
|
|
54
|
+
private: true,
|
|
55
|
+
};
|
|
56
|
+
if (!options.useProjectJson) {
|
|
57
|
+
packageJson.nx = {
|
|
58
|
+
implicitDependencies: [options.projectName],
|
|
59
|
+
};
|
|
60
60
|
}
|
|
61
61
|
else {
|
|
62
62
|
(0, devkit_1.addProjectConfiguration)(tree, options.e2eProjectName, {
|
|
@@ -68,6 +68,9 @@ async function addE2e(tree, options) {
|
|
|
68
68
|
tags: [],
|
|
69
69
|
});
|
|
70
70
|
}
|
|
71
|
+
if (!options.useProjectJson || options.isUsingTsSolutionConfig) {
|
|
72
|
+
(0, devkit_1.writeJson)(tree, (0, devkit_1.joinPathFragments)(options.e2eProjectRoot, 'package.json'), packageJson);
|
|
73
|
+
}
|
|
71
74
|
const e2eTask = await configurationGenerator(tree, {
|
|
72
75
|
...options,
|
|
73
76
|
project: options.e2eProjectName,
|
|
@@ -116,17 +119,15 @@ async function addE2e(tree, options) {
|
|
|
116
119
|
}
|
|
117
120
|
case 'playwright': {
|
|
118
121
|
const { configurationGenerator } = (0, devkit_1.ensurePackage)('@nx/playwright', versions_1.nxVersion);
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
},
|
|
129
|
-
});
|
|
122
|
+
const packageJson = {
|
|
123
|
+
name: options.e2eProjectName,
|
|
124
|
+
version: '0.0.1',
|
|
125
|
+
private: true,
|
|
126
|
+
};
|
|
127
|
+
if (!options.useProjectJson) {
|
|
128
|
+
packageJson.nx = {
|
|
129
|
+
implicitDependencies: [options.projectName],
|
|
130
|
+
};
|
|
130
131
|
}
|
|
131
132
|
else {
|
|
132
133
|
(0, devkit_1.addProjectConfiguration)(tree, options.e2eProjectName, {
|
|
@@ -135,8 +136,12 @@ async function addE2e(tree, options) {
|
|
|
135
136
|
sourceRoot: (0, devkit_1.joinPathFragments)(options.e2eProjectRoot, 'src'),
|
|
136
137
|
targets: {},
|
|
137
138
|
implicitDependencies: [options.projectName],
|
|
139
|
+
tags: [],
|
|
138
140
|
});
|
|
139
141
|
}
|
|
142
|
+
if (!options.useProjectJson || options.isUsingTsSolutionConfig) {
|
|
143
|
+
(0, devkit_1.writeJson)(tree, (0, devkit_1.joinPathFragments)(options.e2eProjectRoot, 'package.json'), packageJson);
|
|
144
|
+
}
|
|
140
145
|
const e2eTask = await configurationGenerator(tree, {
|
|
141
146
|
project: options.e2eProjectName,
|
|
142
147
|
skipFormat: true,
|
|
@@ -1,3 +1,4 @@
|
|
|
1
1
|
import { type Tree, type GeneratorCallback } from '@nx/devkit';
|
|
2
2
|
import { NormalizedSchema } from '../schema';
|
|
3
3
|
export declare function addLinting(host: Tree, options: NormalizedSchema): Promise<GeneratorCallback>;
|
|
4
|
+
export declare function isEslintInstalled(tree: Tree): boolean;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.addLinting = addLinting;
|
|
4
|
+
exports.isEslintInstalled = isEslintInstalled;
|
|
4
5
|
const devkit_1 = require("@nx/devkit");
|
|
5
6
|
const eslint_1 = require("@nx/eslint");
|
|
6
7
|
const eslint_file_1 = require("@nx/eslint/src/generators/utils/eslint-file");
|
|
@@ -8,6 +9,7 @@ const flat_config_1 = require("@nx/eslint/src/utils/flat-config");
|
|
|
8
9
|
const devkit_2 = require("@nx/devkit");
|
|
9
10
|
const add_swc_dependencies_1 = require("@nx/js/src/utils/swc/add-swc-dependencies");
|
|
10
11
|
const lint_1 = require("../../../utils/lint");
|
|
12
|
+
const versions_1 = require("../../../utils/versions");
|
|
11
13
|
async function addLinting(host, options) {
|
|
12
14
|
const tasks = [];
|
|
13
15
|
if (options.linter === eslint_1.Linter.EsLint) {
|
|
@@ -43,6 +45,42 @@ async function addLinting(host, options) {
|
|
|
43
45
|
const addSwcTask = (0, add_swc_dependencies_1.addSwcDependencies)(host);
|
|
44
46
|
tasks.push(installTask, addSwcTask);
|
|
45
47
|
}
|
|
48
|
+
if (options.useReactRouter) {
|
|
49
|
+
await ignoreReactRouterFilesInEslintConfig(host, options.appProjectRoot);
|
|
50
|
+
}
|
|
46
51
|
}
|
|
47
52
|
return (0, devkit_2.runTasksInSerial)(...tasks);
|
|
48
53
|
}
|
|
54
|
+
async function ignoreReactRouterFilesInEslintConfig(tree, projectRoot) {
|
|
55
|
+
if (!isEslintInstalled(tree)) {
|
|
56
|
+
return;
|
|
57
|
+
}
|
|
58
|
+
(0, devkit_1.ensurePackage)('@nx/eslint', versions_1.nxVersion);
|
|
59
|
+
const { addIgnoresToLintConfig, isEslintConfigSupported } = await Promise.resolve().then(() => require('@nx/eslint/src/generators/utils/eslint-file'));
|
|
60
|
+
if (!isEslintConfigSupported(tree)) {
|
|
61
|
+
return;
|
|
62
|
+
}
|
|
63
|
+
const { useFlatConfig } = await Promise.resolve().then(() => require('@nx/eslint/src/utils/flat-config'));
|
|
64
|
+
const isUsingFlatConfig = useFlatConfig(tree);
|
|
65
|
+
if (!projectRoot && !isUsingFlatConfig) {
|
|
66
|
+
// root eslintrc files ignore all files and the root eslintrc files add
|
|
67
|
+
// back all the project files, so we only add the ignores to the project
|
|
68
|
+
// eslintrc files
|
|
69
|
+
return;
|
|
70
|
+
}
|
|
71
|
+
// for flat config, we update the root config file
|
|
72
|
+
const directory = isUsingFlatConfig ? '' : projectRoot ?? '';
|
|
73
|
+
addIgnoresToLintConfig(tree, directory, ['**/build', '**/.react-router']);
|
|
74
|
+
}
|
|
75
|
+
function isEslintInstalled(tree) {
|
|
76
|
+
try {
|
|
77
|
+
require('eslint');
|
|
78
|
+
return true;
|
|
79
|
+
}
|
|
80
|
+
catch { }
|
|
81
|
+
// it might not be installed yet, but it might be in the tree pending install
|
|
82
|
+
const { devDependencies, dependencies } = tree.exists('package.json')
|
|
83
|
+
? (0, devkit_1.readJson)(tree, 'package.json')
|
|
84
|
+
: {};
|
|
85
|
+
return !!devDependencies?.['eslint'] || !!dependencies?.['eslint'];
|
|
86
|
+
}
|
|
@@ -28,26 +28,42 @@ function addProject(host, options) {
|
|
|
28
28
|
serve: createRspackServeTarget(options),
|
|
29
29
|
};
|
|
30
30
|
}
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
31
|
+
const packageJson = {
|
|
32
|
+
name: options.importPath,
|
|
33
|
+
version: '0.0.1',
|
|
34
|
+
private: true,
|
|
35
|
+
};
|
|
36
|
+
if (!options.useProjectJson) {
|
|
37
|
+
if (options.projectName !== options.importPath) {
|
|
38
|
+
packageJson.nx = { name: options.projectName };
|
|
39
|
+
}
|
|
40
|
+
if (Object.keys(project.targets).length) {
|
|
41
|
+
packageJson.nx ??= {};
|
|
42
|
+
packageJson.nx.targets = project.targets;
|
|
43
|
+
}
|
|
44
|
+
if (options.parsedTags?.length) {
|
|
45
|
+
packageJson.nx ??= {};
|
|
46
|
+
packageJson.nx.tags = options.parsedTags;
|
|
47
|
+
}
|
|
37
48
|
}
|
|
38
|
-
|
|
49
|
+
else {
|
|
39
50
|
(0, devkit_1.addProjectConfiguration)(host, options.projectName, {
|
|
40
51
|
...project,
|
|
41
52
|
});
|
|
42
53
|
}
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
54
|
+
if (!options.useProjectJson || options.isUsingTsSolutionConfig) {
|
|
55
|
+
// React Router already adds a package.json to the project root
|
|
56
|
+
if (options.useReactRouter) {
|
|
57
|
+
(0, devkit_1.updateJson)(host, (0, devkit_1.joinPathFragments)(options.appProjectRoot, 'package.json'), (json) => {
|
|
58
|
+
return {
|
|
59
|
+
name: packageJson.name,
|
|
60
|
+
...json,
|
|
61
|
+
};
|
|
62
|
+
});
|
|
63
|
+
}
|
|
64
|
+
else {
|
|
65
|
+
(0, devkit_1.writeJson)(host, (0, devkit_1.joinPathFragments)(options.appProjectRoot, 'package.json'), packageJson);
|
|
66
|
+
}
|
|
51
67
|
}
|
|
52
68
|
}
|
|
53
69
|
function createRspackBuildTarget(options) {
|
|
@@ -20,7 +20,7 @@ function addRouting(host, options) {
|
|
|
20
20
|
}, `src/app/${options.fileName}.tsx`));
|
|
21
21
|
const appFileContent = host.read(appPath, 'utf-8');
|
|
22
22
|
const appSource = tsModule.createSourceFile(appPath, appFileContent, tsModule.ScriptTarget.Latest, true);
|
|
23
|
-
const changes = (0, devkit_1.applyChangesToString)(appFileContent, (0, ast_utils_1.addInitialRoutes)(appPath, appSource));
|
|
23
|
+
const changes = (0, devkit_1.applyChangesToString)(appFileContent, (0, ast_utils_1.addInitialRoutes)(appPath, appSource, options.inSourceTests));
|
|
24
24
|
host.write(appPath, changes);
|
|
25
25
|
if (!options.skipPackageJson) {
|
|
26
26
|
return (0, devkit_1.addDependenciesToPackageJson)(host, { 'react-router-dom': versions_1.reactRouterDomVersion }, {});
|
|
@@ -11,6 +11,18 @@ async function setupViteConfiguration(tree, options, tasks) {
|
|
|
11
11
|
if (tree.exists((0, devkit_1.joinPathFragments)(options.appProjectRoot, 'src/environments'))) {
|
|
12
12
|
tree.delete((0, devkit_1.joinPathFragments)(options.appProjectRoot, 'src/environments'));
|
|
13
13
|
}
|
|
14
|
+
const reactRouterFrameworkConfig = {
|
|
15
|
+
imports: [`import { reactRouter } from '@react-router/dev/vite'`],
|
|
16
|
+
plugins: ['!process.env.VITEST && reactRouter()'],
|
|
17
|
+
};
|
|
18
|
+
const baseReactConfig = {
|
|
19
|
+
imports: [
|
|
20
|
+
options.compiler === 'swc'
|
|
21
|
+
? `import react from '@vitejs/plugin-react-swc'`
|
|
22
|
+
: `import react from '@vitejs/plugin-react'`,
|
|
23
|
+
],
|
|
24
|
+
plugins: ['react()'],
|
|
25
|
+
};
|
|
14
26
|
const viteTask = await viteConfigurationGenerator(tree, {
|
|
15
27
|
uiFramework: 'react',
|
|
16
28
|
project: options.projectName,
|
|
@@ -29,12 +41,9 @@ async function setupViteConfiguration(tree, options, tasks) {
|
|
|
29
41
|
includeVitest: options.unitTestRunner === 'vitest',
|
|
30
42
|
inSourceTests: options.inSourceTests,
|
|
31
43
|
rollupOptionsExternal: ["'react'", "'react-dom'", "'react/jsx-runtime'"],
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
: `import react from '@vitejs/plugin-react'`,
|
|
36
|
-
],
|
|
37
|
-
plugins: ['react()'],
|
|
44
|
+
...(options.useReactRouter
|
|
45
|
+
? reactRouterFrameworkConfig
|
|
46
|
+
: baseReactConfig),
|
|
38
47
|
}, false);
|
|
39
48
|
}
|
|
40
49
|
async function setupVitestConfiguration(tree, options, tasks) {
|
|
@@ -12,6 +12,7 @@ const get_app_tests_1 = require("./get-app-tests");
|
|
|
12
12
|
const onboarding_1 = require("nx/src/nx-cloud/utilities/onboarding");
|
|
13
13
|
const has_rspack_plugin_1 = require("../../../utils/has-rspack-plugin");
|
|
14
14
|
const ts_solution_setup_1 = require("@nx/js/src/utils/typescript/ts-solution-setup");
|
|
15
|
+
const versions_1 = require("../../../utils/versions");
|
|
15
16
|
async function createApplicationFiles(host, options) {
|
|
16
17
|
let styleSolutionSpecificAppFiles;
|
|
17
18
|
if (options.styledModule && options.style !== 'styled-jsx') {
|
|
@@ -39,8 +40,15 @@ async function createApplicationFiles(host, options) {
|
|
|
39
40
|
const relativePathToRootTsConfig = (0, js_1.getRelativePathToRootTsConfig)(host, options.appProjectRoot);
|
|
40
41
|
const appTests = (0, get_app_tests_1.getAppTests)(options);
|
|
41
42
|
const templateVariables = {
|
|
42
|
-
...
|
|
43
|
+
...options.names,
|
|
43
44
|
...options,
|
|
45
|
+
typesNodeVersion: versions_1.typesNodeVersion,
|
|
46
|
+
typesReactDomVersion: versions_1.typesReactDomVersion,
|
|
47
|
+
reactRouterVersion: versions_1.reactRouterVersion,
|
|
48
|
+
typesReactVersion: versions_1.typesReactVersion,
|
|
49
|
+
reactDomVersion: versions_1.reactDomVersion,
|
|
50
|
+
reactVersion: versions_1.reactVersion,
|
|
51
|
+
reactRouterIsBotVersion: versions_1.reactRouterIsBotVersion,
|
|
44
52
|
js: !!options.js, // Ensure this is defined in template
|
|
45
53
|
tmpl: '',
|
|
46
54
|
offsetFromRoot: (0, devkit_1.offsetFromRoot)(options.appProjectRoot),
|
|
@@ -50,9 +58,12 @@ async function createApplicationFiles(host, options) {
|
|
|
50
58
|
hasStyleFile,
|
|
51
59
|
isUsingTsSolutionSetup: (0, ts_solution_setup_1.isUsingTsSolutionSetup)(host),
|
|
52
60
|
};
|
|
53
|
-
if (options.bundler === 'vite') {
|
|
61
|
+
if (options.bundler === 'vite' && !options.useReactRouter) {
|
|
54
62
|
(0, devkit_1.generateFiles)(host, (0, path_1.join)(__dirname, '../files/base-vite'), options.appProjectRoot, templateVariables);
|
|
55
63
|
}
|
|
64
|
+
else if (options.bundler === 'vite' && options.useReactRouter) {
|
|
65
|
+
generateReactRouterFiles(host, options, templateVariables);
|
|
66
|
+
}
|
|
56
67
|
else if (options.bundler === 'webpack') {
|
|
57
68
|
(0, devkit_1.generateFiles)(host, (0, path_1.join)(__dirname, '../files/base-webpack'), options.appProjectRoot, {
|
|
58
69
|
...templateVariables,
|
|
@@ -137,9 +148,12 @@ async function createApplicationFiles(host, options) {
|
|
|
137
148
|
const tutorialUrl = options.rootProject
|
|
138
149
|
? 'https://nx.dev/getting-started/tutorials/react-standalone-tutorial'
|
|
139
150
|
: 'https://nx.dev/react-tutorial/1-code-generation?utm_source=nx-project';
|
|
140
|
-
|
|
151
|
+
const path = options.useReactRouter
|
|
152
|
+
? '../files/react-router-ssr/nx-welcome'
|
|
153
|
+
: '../files/nx-welcome';
|
|
154
|
+
(0, devkit_1.generateFiles)(host, (0, path_1.join)(__dirname, path, onBoardingStatus), options.appProjectRoot, { ...templateVariables, connectCloudUrl, tutorialUrl });
|
|
141
155
|
}
|
|
142
|
-
(0, devkit_1.generateFiles)(host, (0, path_1.join)(__dirname, styleSolutionSpecificAppFiles), options.appProjectRoot, templateVariables);
|
|
156
|
+
(0, devkit_1.generateFiles)(host, (0, path_1.join)(__dirname, styleSolutionSpecificAppFiles, options.useReactRouter ? 'src' : ''), options.appProjectRoot, templateVariables);
|
|
143
157
|
if (options.js) {
|
|
144
158
|
(0, devkit_1.toJS)(host, {
|
|
145
159
|
useJsx: options.bundler === 'vite' || options.bundler === 'rspack',
|
|
@@ -194,3 +208,26 @@ function createNxRspackPluginOptions(options, rootOffset) {
|
|
|
194
208
|
],
|
|
195
209
|
};
|
|
196
210
|
}
|
|
211
|
+
function generateReactRouterFiles(tree, options, templateVariables) {
|
|
212
|
+
(0, devkit_1.generateFiles)(tree, (0, path_1.join)(__dirname, '../files/react-router-ssr/common'), options.appProjectRoot, templateVariables);
|
|
213
|
+
if (options.rootProject) {
|
|
214
|
+
const gitignore = tree.read('.gitignore', 'utf-8');
|
|
215
|
+
tree.write('.gitignore', `${gitignore}\n.cache\nbuild\npublic/build\n.env\n\.react-router\n`);
|
|
216
|
+
}
|
|
217
|
+
else {
|
|
218
|
+
(0, devkit_1.generateFiles)(tree, (0, devkit_1.joinPathFragments)(__dirname, '../files/react-router-ssr/non-root'), options.appProjectRoot, templateVariables);
|
|
219
|
+
}
|
|
220
|
+
if (options.isUsingTsSolutionConfig) {
|
|
221
|
+
(0, devkit_1.generateFiles)(tree, (0, devkit_1.joinPathFragments)(__dirname, '../files/react-router-ssr/ts-solution'), options.appProjectRoot, templateVariables);
|
|
222
|
+
(0, devkit_1.updateJson)(tree, (0, devkit_1.joinPathFragments)(options.appProjectRoot, 'package.json'), (json) => {
|
|
223
|
+
if (options.projectName !== options.importPath) {
|
|
224
|
+
json.nx = { name: options.projectName };
|
|
225
|
+
}
|
|
226
|
+
if (options.parsedTags?.length) {
|
|
227
|
+
json.nx ??= {};
|
|
228
|
+
json.nx.tags = options.parsedTags;
|
|
229
|
+
}
|
|
230
|
+
return json;
|
|
231
|
+
});
|
|
232
|
+
}
|
|
233
|
+
}
|
|
@@ -11,13 +11,24 @@ async function installCommonDependencies(host, options) {
|
|
|
11
11
|
const reactDeps = await (0, version_utils_1.getReactDependenciesVersionsToInstall)(host);
|
|
12
12
|
const dependencies = {};
|
|
13
13
|
const devDependencies = {
|
|
14
|
-
'@types/node': versions_1.typesNodeVersion,
|
|
15
14
|
'@types/react': reactDeps['@types/react'],
|
|
16
15
|
'@types/react-dom': reactDeps['@types/react-dom'],
|
|
16
|
+
'@types/node': versions_1.typesNodeVersion,
|
|
17
|
+
...(options.useReactRouter
|
|
18
|
+
? {
|
|
19
|
+
'@react-router/dev': versions_1.reactRouterVersion,
|
|
20
|
+
}
|
|
21
|
+
: {}),
|
|
17
22
|
};
|
|
18
23
|
if (options.bundler !== 'vite') {
|
|
19
24
|
dependencies['tslib'] = versions_1.tsLibVersion;
|
|
20
25
|
}
|
|
26
|
+
if (options.useReactRouter) {
|
|
27
|
+
dependencies['react-router'] = versions_1.reactRouterVersion;
|
|
28
|
+
dependencies['@react-router/node'] = versions_1.reactRouterVersion;
|
|
29
|
+
dependencies['@react-router/serve'] = versions_1.reactRouterVersion;
|
|
30
|
+
dependencies['isbot'] = versions_1.reactRouterIsBotVersion;
|
|
31
|
+
}
|
|
21
32
|
// Vite requires style preprocessors to be installed manually.
|
|
22
33
|
// `@nx/webpack` installs them automatically for now.
|
|
23
34
|
if (options.bundler === 'vite' || options.unitTestRunner === 'vitest') {
|
|
@@ -45,5 +56,5 @@ async function installCommonDependencies(host, options) {
|
|
|
45
56
|
devDependencies['@testing-library/react'] = versions_1.testingLibraryReactVersion;
|
|
46
57
|
devDependencies['@testing-library/dom'] = versions_1.testingLibraryDomVersion;
|
|
47
58
|
}
|
|
48
|
-
return (0, devkit_1.addDependenciesToPackageJson)(host,
|
|
59
|
+
return (0, devkit_1.addDependenciesToPackageJson)(host, dependencies, devDependencies);
|
|
49
60
|
}
|
|
@@ -1,5 +1,3 @@
|
|
|
1
1
|
import { Tree } from '@nx/devkit';
|
|
2
2
|
import { NormalizedSchema, Schema } from '../schema';
|
|
3
|
-
export declare function normalizeDirectory(options: Schema): string;
|
|
4
|
-
export declare function normalizeProjectName(options: Schema): string;
|
|
5
3
|
export declare function normalizeOptions<T extends Schema = Schema>(host: Tree, options: Schema): Promise<NormalizedSchema<T>>;
|
|
@@ -1,27 +1,14 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.normalizeDirectory = normalizeDirectory;
|
|
4
|
-
exports.normalizeProjectName = normalizeProjectName;
|
|
5
3
|
exports.normalizeOptions = normalizeOptions;
|
|
6
4
|
const devkit_1 = require("@nx/devkit");
|
|
7
5
|
const project_name_and_root_utils_1 = require("@nx/devkit/src/generators/project-name-and-root-utils");
|
|
8
6
|
const assertion_1 = require("../../../utils/assertion");
|
|
9
7
|
const find_free_port_1 = require("./find-free-port");
|
|
10
8
|
const ts_solution_setup_1 = require("@nx/js/src/utils/typescript/ts-solution-setup");
|
|
11
|
-
const get_import_path_1 = require("@nx/js/src/utils/get-import-path");
|
|
12
|
-
function normalizeDirectory(options) {
|
|
13
|
-
options.directory = options.directory?.replace(/\\{1,2}/g, '/');
|
|
14
|
-
const { projectDirectory } = (0, devkit_1.extractLayoutDirectory)(options.directory);
|
|
15
|
-
return projectDirectory
|
|
16
|
-
? `${(0, devkit_1.names)(projectDirectory).fileName}/${(0, devkit_1.names)(options.name).fileName}`
|
|
17
|
-
: (0, devkit_1.names)(options.name).fileName;
|
|
18
|
-
}
|
|
19
|
-
function normalizeProjectName(options) {
|
|
20
|
-
return normalizeDirectory(options).replace(new RegExp('/', 'g'), '-');
|
|
21
|
-
}
|
|
22
9
|
async function normalizeOptions(host, options) {
|
|
23
|
-
await (0, project_name_and_root_utils_1.
|
|
24
|
-
const { projectName:
|
|
10
|
+
await (0, project_name_and_root_utils_1.ensureRootProjectName)(options, 'application');
|
|
11
|
+
const { projectName, names: projectNames, projectRoot: appProjectRoot, importPath, } = await (0, project_name_and_root_utils_1.determineProjectNameAndRootOptions)(host, {
|
|
25
12
|
name: options.name,
|
|
26
13
|
projectType: 'application',
|
|
27
14
|
directory: options.directory,
|
|
@@ -32,6 +19,8 @@ async function normalizeOptions(host, options) {
|
|
|
32
19
|
nxJson.useInferencePlugins !== false;
|
|
33
20
|
options.addPlugin ??= addPlugin;
|
|
34
21
|
options.rootProject = appProjectRoot === '.';
|
|
22
|
+
const isUsingTsSolutionConfig = (0, ts_solution_setup_1.isUsingTsSolutionSetup)(host);
|
|
23
|
+
const appProjectName = !isUsingTsSolutionConfig || options.name ? projectName : importPath;
|
|
35
24
|
const e2eProjectName = options.rootProject ? 'e2e' : `${appProjectName}-e2e`;
|
|
36
25
|
const e2eProjectRoot = options.rootProject ? 'e2e' : `${appProjectRoot}-e2e`;
|
|
37
26
|
const parsedTags = options.tags
|
|
@@ -42,23 +31,25 @@ async function normalizeOptions(host, options) {
|
|
|
42
31
|
? null
|
|
43
32
|
: options.style;
|
|
44
33
|
(0, assertion_1.assertValidStyle)(options.style);
|
|
45
|
-
|
|
34
|
+
options.bundler = options.useReactRouter ? 'vite' : options.bundler;
|
|
35
|
+
options.useReactRouter = options.routing ? options.useReactRouter : false;
|
|
46
36
|
const normalized = {
|
|
47
37
|
...options,
|
|
48
|
-
|
|
49
|
-
projectName: isUsingTsSolutionConfig
|
|
50
|
-
? (0, get_import_path_1.getImportPath)(host, appProjectName)
|
|
51
|
-
: appProjectName,
|
|
38
|
+
projectName: appProjectName,
|
|
52
39
|
appProjectRoot,
|
|
40
|
+
importPath,
|
|
53
41
|
e2eProjectName,
|
|
54
42
|
e2eProjectRoot,
|
|
55
43
|
parsedTags,
|
|
56
44
|
fileName,
|
|
57
45
|
styledModule,
|
|
58
46
|
hasStyles: options.style !== 'none',
|
|
47
|
+
names: (0, devkit_1.names)(projectNames.projectSimpleName),
|
|
59
48
|
isUsingTsSolutionConfig,
|
|
49
|
+
useProjectJson: options.useProjectJson ?? !isUsingTsSolutionConfig,
|
|
60
50
|
};
|
|
61
51
|
normalized.routing = normalized.routing ?? false;
|
|
52
|
+
normalized.useReactRouter = normalized.useReactRouter ?? false;
|
|
62
53
|
normalized.strict = normalized.strict ?? true;
|
|
63
54
|
normalized.classComponent = normalized.classComponent ?? false;
|
|
64
55
|
normalized.compiler = normalized.compiler ?? 'babel';
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { names } from '@nx/devkit';
|
|
1
2
|
import type { Linter, LinterType } from '@nx/eslint';
|
|
2
3
|
import type { SupportedStyles } from '../../../typings/style';
|
|
3
4
|
|
|
@@ -13,6 +14,7 @@ export interface Schema {
|
|
|
13
14
|
linter: Linter | LinterType;
|
|
14
15
|
classComponent?: boolean;
|
|
15
16
|
routing?: boolean;
|
|
17
|
+
useReactRouter?: boolean;
|
|
16
18
|
skipNxJson?: boolean;
|
|
17
19
|
js?: boolean;
|
|
18
20
|
globalCss?: boolean;
|
|
@@ -30,7 +32,7 @@ export interface Schema {
|
|
|
30
32
|
nxCloudToken?: string;
|
|
31
33
|
useTsSolution?: boolean;
|
|
32
34
|
formatter?: 'prettier' | 'none';
|
|
33
|
-
|
|
35
|
+
useProjectJson?: boolean;
|
|
34
36
|
}
|
|
35
37
|
|
|
36
38
|
export interface NormalizedSchema<T extends Schema = Schema> extends T {
|
|
@@ -38,11 +40,13 @@ export interface NormalizedSchema<T extends Schema = Schema> extends T {
|
|
|
38
40
|
appProjectRoot: string;
|
|
39
41
|
e2eProjectName: string;
|
|
40
42
|
e2eProjectRoot: string;
|
|
43
|
+
importPath: string;
|
|
41
44
|
parsedTags: string[];
|
|
42
45
|
fileName: string;
|
|
43
46
|
styledModule: null | SupportedStyles;
|
|
44
47
|
hasStyles: boolean;
|
|
45
48
|
unitTestRunner: 'jest' | 'vitest' | 'none';
|
|
46
49
|
addPlugin?: boolean;
|
|
50
|
+
names: ReturnType<typeof names>;
|
|
47
51
|
isUsingTsSolutionConfig?: boolean;
|
|
48
52
|
}
|
|
@@ -83,7 +83,12 @@
|
|
|
83
83
|
"routing": {
|
|
84
84
|
"type": "boolean",
|
|
85
85
|
"description": "Generate application with routes.",
|
|
86
|
-
"x-prompt": "Would you like to add
|
|
86
|
+
"x-prompt": "Would you like to add routing to this application?",
|
|
87
|
+
"default": false
|
|
88
|
+
},
|
|
89
|
+
"useReactRouter": {
|
|
90
|
+
"description": "Use React Router for routing.",
|
|
91
|
+
"type": "boolean",
|
|
87
92
|
"default": false
|
|
88
93
|
},
|
|
89
94
|
"skipFormat": {
|
|
@@ -187,6 +192,10 @@
|
|
|
187
192
|
"description": "Generate a React app with a minimal setup, no separate test files.",
|
|
188
193
|
"type": "boolean",
|
|
189
194
|
"default": false
|
|
195
|
+
},
|
|
196
|
+
"useProjectJson": {
|
|
197
|
+
"type": "boolean",
|
|
198
|
+
"description": "Use a `project.json` configuration file instead of inlining the Nx configuration in the `package.json` file."
|
|
190
199
|
}
|
|
191
200
|
},
|
|
192
201
|
"required": ["directory"],
|
|
@@ -19,7 +19,10 @@ const update_module_federation_tsconfig_1 = require("./lib/update-module-federat
|
|
|
19
19
|
async function hostGenerator(host, schema) {
|
|
20
20
|
const tasks = [];
|
|
21
21
|
const options = {
|
|
22
|
-
...(await (0, normalize_options_1.normalizeOptions)(host,
|
|
22
|
+
...(await (0, normalize_options_1.normalizeOptions)(host, {
|
|
23
|
+
...schema,
|
|
24
|
+
useProjectJson: true,
|
|
25
|
+
})),
|
|
23
26
|
js: schema.js ?? false,
|
|
24
27
|
typescriptConfiguration: schema.js
|
|
25
28
|
? false
|
|
@@ -39,7 +42,7 @@ async function hostGenerator(host, schema) {
|
|
|
39
42
|
}
|
|
40
43
|
});
|
|
41
44
|
}
|
|
42
|
-
await (0, project_name_and_root_utils_1.
|
|
45
|
+
await (0, project_name_and_root_utils_1.ensureRootProjectName)(options, 'application');
|
|
43
46
|
const initTask = await (0, application_1.default)(host, {
|
|
44
47
|
...options,
|
|
45
48
|
directory: options.appProjectRoot,
|
|
@@ -47,7 +50,7 @@ async function hostGenerator(host, schema) {
|
|
|
47
50
|
// The target use-case is loading remotes as child routes, thus always enable routing.
|
|
48
51
|
routing: true,
|
|
49
52
|
skipFormat: true,
|
|
50
|
-
|
|
53
|
+
useProjectJson: true,
|
|
51
54
|
});
|
|
52
55
|
tasks.push(initTask);
|
|
53
56
|
const remotesWithPorts = [];
|
|
@@ -4,6 +4,8 @@ exports.reactInitGenerator = reactInitGenerator;
|
|
|
4
4
|
const devkit_1 = require("@nx/devkit");
|
|
5
5
|
const versions_1 = require("../../utils/versions");
|
|
6
6
|
const version_utils_1 = require("../../utils/version-utils");
|
|
7
|
+
const add_plugin_1 = require("@nx/devkit/src/utils/add-plugin");
|
|
8
|
+
const router_plugin_1 = require("../../plugins/router-plugin");
|
|
7
9
|
async function reactInitGenerator(tree, schema) {
|
|
8
10
|
const tasks = [];
|
|
9
11
|
if (!schema.skipPackageJson) {
|
|
@@ -16,6 +18,27 @@ async function reactInitGenerator(tree, schema) {
|
|
|
16
18
|
'@nx/react': versions_1.nxVersion,
|
|
17
19
|
}, undefined, schema.keepExistingVersions));
|
|
18
20
|
}
|
|
21
|
+
const nxJson = (0, devkit_1.readNxJson)(tree);
|
|
22
|
+
schema.addPlugin ??=
|
|
23
|
+
process.env.NX_ADD_PLUGINS !== 'false' &&
|
|
24
|
+
nxJson.useInferencePlugins !== false;
|
|
25
|
+
if (schema.addPlugin) {
|
|
26
|
+
await (0, add_plugin_1.addPlugin)(tree, await (0, devkit_1.createProjectGraphAsync)(), '@nx/react/router-plugin', router_plugin_1.createNodesV2, {
|
|
27
|
+
buildTargetName: ['build', 'react-router:build', 'react-router-build'],
|
|
28
|
+
devTargetName: ['dev', 'react-router:dev', 'react-router-dev'],
|
|
29
|
+
startTargetName: ['start', 'react-router-serve', 'react-router-start'],
|
|
30
|
+
watchDepsTargetName: [
|
|
31
|
+
'watch-deps',
|
|
32
|
+
'react-router:watch-deps',
|
|
33
|
+
'react-router-watch-deps',
|
|
34
|
+
],
|
|
35
|
+
buildDepsTargetName: [
|
|
36
|
+
'build-deps',
|
|
37
|
+
'react-router:build-deps',
|
|
38
|
+
'react-router-build-deps',
|
|
39
|
+
],
|
|
40
|
+
}, schema.updatePackageScripts);
|
|
41
|
+
}
|
|
19
42
|
if (!schema.skipFormat) {
|
|
20
43
|
await (0, devkit_1.formatFiles)(tree);
|
|
21
44
|
}
|