diff --git a/packages/angular/src/generators/add-linting/add-linting.ts b/packages/angular/src/generators/add-linting/add-linting.ts index c912baa0ac..d9ea98d460 100755 --- a/packages/angular/src/generators/add-linting/add-linting.ts +++ b/packages/angular/src/generators/add-linting/add-linting.ts @@ -40,7 +40,7 @@ export async function addLintingGenerator( setParserOptionsProject: options.setParserOptionsProject, skipFormat: true, rootProject: rootProject, - addPlugin: false, + addPlugin: options.addPlugin ?? false, addExplicitTargets: true, skipPackageJson: options.skipPackageJson, }); diff --git a/packages/angular/src/generators/add-linting/schema.d.ts b/packages/angular/src/generators/add-linting/schema.d.ts index c471cf65b1..1973f8276d 100644 --- a/packages/angular/src/generators/add-linting/schema.d.ts +++ b/packages/angular/src/generators/add-linting/schema.d.ts @@ -6,4 +6,5 @@ export interface AddLintingGeneratorSchema { skipFormat?: boolean; skipPackageJson?: boolean; unitTestRunner?: string; + addPlugin?: boolean; } diff --git a/packages/angular/src/generators/application/application.spec.ts b/packages/angular/src/generators/application/application.spec.ts index 434b1d08cb..0b0c24e371 100644 --- a/packages/angular/src/generators/application/application.spec.ts +++ b/packages/angular/src/generators/application/application.spec.ts @@ -1246,6 +1246,7 @@ describe('app', () => { ] `); }); + it('should generate a correct setup when --bundler=rspack including a correct config file and no build target', async () => { await generateApp(appTree, 'app1', { bundler: 'rspack', @@ -1257,6 +1258,42 @@ describe('app', () => { expect(appTree.read('app1/rspack.config.ts', 'utf-8')).toMatchSnapshot(); }); + it('should generate use crystal jest when --bundler=rspack', async () => { + await generateApp(appTree, 'app1', { + bundler: 'rspack', + unitTestRunner: UnitTestRunner.Jest, + }); + + const project = readProjectConfiguration(appTree, 'app1'); + expect(project.targets.test).not.toBeDefined(); + + const nxJson = readNxJson(appTree); + const jestPlugin = nxJson.plugins.find( + (p) => + (typeof p === 'string' && p === '@nx/jest/plugin') || + (typeof p !== 'string' && p.plugin === '@nx/jest/plugin') + ); + expect(jestPlugin).toBeDefined(); + }); + + it('should generate use crystal vitest when --bundler=rspack', async () => { + await generateApp(appTree, 'app1', { + bundler: 'rspack', + unitTestRunner: UnitTestRunner.Vitest, + }); + + const project = readProjectConfiguration(appTree, 'app1'); + expect(project.targets.test).not.toBeDefined(); + + const nxJson = readNxJson(appTree); + const vitePlugin = nxJson.plugins.find( + (p) => + (typeof p === 'string' && p === '@nx/vite/plugin') || + (typeof p !== 'string' && p.plugin === '@nx/vite/plugin') + ); + expect(vitePlugin).toBeDefined(); + }); + it('should generate target options "browser" and "buildTarget"', async () => { await generateApp(appTree, 'my-app', { standalone: true }); diff --git a/packages/angular/src/generators/application/application.ts b/packages/angular/src/generators/application/application.ts index 978c95ddba..3838d3907c 100644 --- a/packages/angular/src/generators/application/application.ts +++ b/packages/angular/src/generators/application/application.ts @@ -31,7 +31,6 @@ import { updateEditorTsConfig, } from './lib'; import type { Schema } from './schema'; -import { tsNodeVersion } from '../../utils/versions'; export async function applicationGenerator( tree: Tree, @@ -43,7 +42,7 @@ export async function applicationGenerator( schema.bundler = 'webpack'; } - const options = await normalizeOptions(tree, schema); + const options = await normalizeOptions(tree, schema, isRspack); const rootOffset = offsetFromRoot(options.appProjectRoot); await jsInitGenerator(tree, { @@ -55,6 +54,7 @@ export async function applicationGenerator( await angularInitGenerator(tree, { ...options, skipFormat: true, + addPlugin: options.addPlugin, }); if (!options.skipPackageJson) { diff --git a/packages/angular/src/generators/application/lib/add-e2e.ts b/packages/angular/src/generators/application/lib/add-e2e.ts index 2227cbadf2..591b1b1e1f 100644 --- a/packages/angular/src/generators/application/lib/add-e2e.ts +++ b/packages/angular/src/generators/application/lib/add-e2e.ts @@ -15,8 +15,8 @@ export async function addE2e(tree: Tree, options: NormalizedSchema) { // since e2e are separate projects, default to adding plugins const nxJson = readNxJson(tree); const addPlugin = - process.env.NX_ADD_PLUGINS !== 'false' && - nxJson.useInferencePlugins !== false; + nxJson['useInferencePlugins'] !== false && + process.env.NX_ADD_PLUGINS !== 'false'; const e2eWebServerInfo = getAngularE2EWebServerInfo( tree, diff --git a/packages/angular/src/generators/application/lib/add-linting.ts b/packages/angular/src/generators/application/lib/add-linting.ts index 8f6983f0aa..70da0750fd 100644 --- a/packages/angular/src/generators/application/lib/add-linting.ts +++ b/packages/angular/src/generators/application/lib/add-linting.ts @@ -16,5 +16,6 @@ export async function addLinting(host: Tree, options: NormalizedSchema) { skipPackageJson: options.skipPackageJson, unitTestRunner: options.unitTestRunner, skipFormat: true, + addPlugin: options.addPlugin, }); } diff --git a/packages/angular/src/generators/application/lib/add-unit-test-runner.ts b/packages/angular/src/generators/application/lib/add-unit-test-runner.ts index 822d84511a..9d3ab5aad7 100644 --- a/packages/angular/src/generators/application/lib/add-unit-test-runner.ts +++ b/packages/angular/src/generators/application/lib/add-unit-test-runner.ts @@ -12,6 +12,7 @@ export async function addUnitTestRunner(host: Tree, options: NormalizedSchema) { projectRoot: options.appProjectRoot, skipPackageJson: options.skipPackageJson, strict: options.strict, + addPlugin: options.addPlugin, }); break; case UnitTestRunner.Vitest: @@ -20,6 +21,7 @@ export async function addUnitTestRunner(host: Tree, options: NormalizedSchema) { projectRoot: options.appProjectRoot, skipPackageJson: options.skipPackageJson, strict: options.strict, + addPlugin: options.addPlugin, }); break; } diff --git a/packages/angular/src/generators/application/lib/normalize-options.ts b/packages/angular/src/generators/application/lib/normalize-options.ts index 60372435f2..e632fd20a6 100644 --- a/packages/angular/src/generators/application/lib/normalize-options.ts +++ b/packages/angular/src/generators/application/lib/normalize-options.ts @@ -1,4 +1,4 @@ -import { joinPathFragments, type Tree } from '@nx/devkit'; +import { joinPathFragments, readNxJson, type Tree } from '@nx/devkit'; import { determineProjectNameAndRootOptions, ensureRootProjectName, @@ -8,9 +8,16 @@ import { E2eTestRunner, UnitTestRunner } from '../../../utils/test-runners'; import type { Schema } from '../schema'; import type { NormalizedSchema } from './normalized-schema'; +function arePluginsExplicitlyDisabled(host: Tree) { + const { useInferencePlugins } = readNxJson(host); + const addPluginEnvVar = process.env.NX_ADD_PLUGINS; + return useInferencePlugins === false || addPluginEnvVar === 'false'; +} + export async function normalizeOptions( host: Tree, - options: Partial + options: Partial, + isRspack?: boolean ): Promise { await ensureRootProjectName(options as Schema, 'application'); const { projectName: appProjectName, projectRoot: appProjectRoot } = @@ -31,8 +38,12 @@ export async function normalizeOptions( const bundler = options.bundler ?? 'esbuild'; + const addPlugin = + options.addPlugin ?? (!arePluginsExplicitlyDisabled(host) && isRspack); + // Set defaults and then overwrite with user options return { + addPlugin, style: 'css', routing: true, inlineStyle: false, diff --git a/packages/angular/src/generators/application/schema.d.ts b/packages/angular/src/generators/application/schema.d.ts index 3f701b9d5e..7016bce438 100644 --- a/packages/angular/src/generators/application/schema.d.ts +++ b/packages/angular/src/generators/application/schema.d.ts @@ -31,4 +31,5 @@ export interface Schema { ssr?: boolean; serverRouting?: boolean; nxCloudToken?: string; + addPlugin?: boolean; } diff --git a/packages/angular/src/generators/convert-to-rspack/convert-to-rspack.ts b/packages/angular/src/generators/convert-to-rspack/convert-to-rspack.ts index f61ccd83c3..0e3c5d9eb7 100644 --- a/packages/angular/src/generators/convert-to-rspack/convert-to-rspack.ts +++ b/packages/angular/src/generators/convert-to-rspack/convert-to-rspack.ts @@ -410,8 +410,8 @@ export async function convertToRspack( ); } } + serveTargetNames.push(targetName); } - serveTargetNames.push(targetName); } const customWebpackConfigInfo = customWebpackConfigPath diff --git a/packages/angular/src/generators/utils/add-jest.ts b/packages/angular/src/generators/utils/add-jest.ts index 1365ced1d5..308b89e2cf 100644 --- a/packages/angular/src/generators/utils/add-jest.ts +++ b/packages/angular/src/generators/utils/add-jest.ts @@ -11,6 +11,7 @@ export type AddJestOptions = { projectRoot: string; skipPackageJson: boolean; strict: boolean; + addPlugin?: boolean; }; export async function addJest( @@ -40,8 +41,8 @@ export async function addJest( skipSerializers: false, skipPackageJson: options.skipPackageJson, skipFormat: true, - addPlugin: false, - addExplicitTargets: true, + addPlugin: options.addPlugin ?? false, + addExplicitTargets: !options.addPlugin, }); const setupFile = joinPathFragments( diff --git a/packages/angular/src/generators/utils/add-vitest.ts b/packages/angular/src/generators/utils/add-vitest.ts index 852bfa129e..7cb5a1f9f5 100644 --- a/packages/angular/src/generators/utils/add-vitest.ts +++ b/packages/angular/src/generators/utils/add-vitest.ts @@ -6,6 +6,7 @@ export type AddVitestOptions = { projectRoot: string; skipPackageJson: boolean; strict: boolean; + addPlugin?: boolean; }; export async function addVitest( @@ -22,6 +23,6 @@ export async function addVitest( uiFramework: 'angular', testEnvironment: 'jsdom', coverageProvider: 'v8', - addPlugin: false, + addPlugin: options.addPlugin ?? false, }); }