feat(testing): remove tsConfig and copyFiles options from the @nx/cypress:cypress executor (#30870)
Removes the previously deprecated and unused `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor. BREAKING CHANGE: The previously deprecated and unused `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor were removed.
This commit is contained in:
parent
9ae691ede8
commit
8d0c7f6349
@ -1312,6 +1312,16 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"migrations": {
|
"migrations": {
|
||||||
|
"/nx-api/cypress/migrations/remove-tsconfig-and-copy-files-options-from-cypress-executor": {
|
||||||
|
"description": "Removes the `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor.",
|
||||||
|
"file": "generated/packages/cypress/migrations/remove-tsconfig-and-copy-files-options-from-cypress-executor.json",
|
||||||
|
"hidden": false,
|
||||||
|
"name": "remove-tsconfig-and-copy-files-options-from-cypress-executor",
|
||||||
|
"version": "21.0.0-beta.10",
|
||||||
|
"originalFilePath": "/packages/cypress",
|
||||||
|
"path": "/nx-api/cypress/migrations/remove-tsconfig-and-copy-files-options-from-cypress-executor",
|
||||||
|
"type": "migration"
|
||||||
|
},
|
||||||
"/nx-api/cypress/migrations/set-inject-document-domain": {
|
"/nx-api/cypress/migrations/set-inject-document-domain": {
|
||||||
"description": "Replaces the `experimentalSkipDomainInjection` configuration option with the new `injectDocumentDomain` configuration option.",
|
"description": "Replaces the `experimentalSkipDomainInjection` configuration option with the new `injectDocumentDomain` configuration option.",
|
||||||
"file": "generated/packages/cypress/migrations/set-inject-document-domain.json",
|
"file": "generated/packages/cypress/migrations/set-inject-document-domain.json",
|
||||||
|
|||||||
@ -1304,6 +1304,16 @@
|
|||||||
}
|
}
|
||||||
],
|
],
|
||||||
"migrations": [
|
"migrations": [
|
||||||
|
{
|
||||||
|
"description": "Removes the `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor.",
|
||||||
|
"file": "generated/packages/cypress/migrations/remove-tsconfig-and-copy-files-options-from-cypress-executor.json",
|
||||||
|
"hidden": false,
|
||||||
|
"name": "remove-tsconfig-and-copy-files-options-from-cypress-executor",
|
||||||
|
"version": "21.0.0-beta.10",
|
||||||
|
"originalFilePath": "/packages/cypress",
|
||||||
|
"path": "cypress/migrations/remove-tsconfig-and-copy-files-options-from-cypress-executor",
|
||||||
|
"type": "migration"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"description": "Replaces the `experimentalSkipDomainInjection` configuration option with the new `injectDocumentDomain` configuration option.",
|
"description": "Replaces the `experimentalSkipDomainInjection` configuration option with the new `injectDocumentDomain` configuration option.",
|
||||||
"file": "generated/packages/cypress/migrations/set-inject-document-domain.json",
|
"file": "generated/packages/cypress/migrations/set-inject-document-domain.json",
|
||||||
|
|||||||
@ -31,13 +31,6 @@
|
|||||||
"description": "Recompile and run tests when files change.",
|
"description": "Recompile and run tests when files change.",
|
||||||
"default": false
|
"default": false
|
||||||
},
|
},
|
||||||
"tsConfig": {
|
|
||||||
"x-deprecated": "This option no longer has any effect. Cypress supports typescript out of the box. Add any options directly to <projectRoot>/tsconfig.json or <projectRoot>/cypress/tsconfig.json",
|
|
||||||
"type": "string",
|
|
||||||
"description": "The path of the Cypress tsconfig configuration json file.",
|
|
||||||
"x-completion-type": "file",
|
|
||||||
"x-completion-glob": "tsconfig.*.json"
|
|
||||||
},
|
|
||||||
"devServerTarget": {
|
"devServerTarget": {
|
||||||
"type": "string",
|
"type": "string",
|
||||||
"description": "Dev server target to run tests against."
|
"description": "Dev server target to run tests against."
|
||||||
@ -51,7 +44,7 @@
|
|||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
"description": "Hide the browser instead of running headed.",
|
"description": "Hide the browser instead of running headed.",
|
||||||
"default": false,
|
"default": false,
|
||||||
"x-deprecated": "Cypress runs headless by default. Use the --watch flag to control head/headless behavior instead."
|
"x-deprecated": "Cypress runs headless by default. Use the --watch flag to control head/headless behavior instead. It will be removed in Nx v22."
|
||||||
},
|
},
|
||||||
"exit": {
|
"exit": {
|
||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
@ -90,12 +83,6 @@
|
|||||||
"type": "string",
|
"type": "string",
|
||||||
"description": "A comma delimited glob string that is provided to the Cypress runner to specify which spec files to run. i.e. `**examples/**,**actions.spec**`."
|
"description": "A comma delimited glob string that is provided to the Cypress runner to specify which spec files to run. i.e. `**examples/**,**actions.spec**`."
|
||||||
},
|
},
|
||||||
"copyFiles": {
|
|
||||||
"type": "string",
|
|
||||||
"description": "A regex string that is used to choose what additional integration files to copy to the dist folder.",
|
|
||||||
"x-deprecated": "No longer used since cypress supports typescript out of the box. If specified, it will be ignored.",
|
|
||||||
"x-priority": "internal"
|
|
||||||
},
|
|
||||||
"ciBuildId": {
|
"ciBuildId": {
|
||||||
"oneOf": [{ "type": "string" }, { "type": "number" }],
|
"oneOf": [{ "type": "string" }, { "type": "number" }],
|
||||||
"description": "A unique identifier for a run to enable grouping or parallelization."
|
"description": "A unique identifier for a run to enable grouping or parallelization."
|
||||||
|
|||||||
@ -0,0 +1,12 @@
|
|||||||
|
{
|
||||||
|
"name": "remove-tsconfig-and-copy-files-options-from-cypress-executor",
|
||||||
|
"version": "21.0.0-beta.10",
|
||||||
|
"description": "Removes the `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor.",
|
||||||
|
"implementation": "/packages/cypress/src/migrations/update-21-0-0/remove-tsconfig-and-copy-files-options-from-cypress-executor.ts",
|
||||||
|
"aliases": [],
|
||||||
|
"hidden": false,
|
||||||
|
"path": "/packages/cypress",
|
||||||
|
"schema": null,
|
||||||
|
"type": "migration",
|
||||||
|
"examplesFile": "#### Remove `tsConfig` and `copyFiles` Options from Cypress Executor\n\nRemoves the previously deprecated and unused `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor configuration in all projects.\n\n#### Examples\n\nRemove the options from the project configuration:\n\n{% tabs %}\n{% tab label=\"Before\" %}\n\n```json {% fileName=\"apps/app1-e2e/project.json\" highlightLines=[7,8] %}\n{\n \"targets\": {\n \"e2e\": {\n \"executor\": \"@nx/cypress:cypress\",\n \"options\": {\n \"cypressConfig\": \"apps/app1-e2e/cypress.config.ts\",\n \"tsConfig\": \"apps/app1-e2e/tsconfig.json\",\n \"copyFiles\": \"**/*.spec.ts\",\n \"devServerTarget\": \"app1:serve\"\n }\n }\n }\n}\n```\n\n{% /tab %}\n\n{% tab label=\"After\" %}\n\n```json {% fileName=\"apps/app1-e2e/project.json\" %}\n{\n \"targets\": {\n \"e2e\": {\n \"executor\": \"@nx/cypress:cypress\",\n \"options\": {\n \"cypressConfig\": \"apps/app1-e2e/cypress.config.ts\",\n \"devServerTarget\": \"app1:serve\"\n }\n }\n }\n}\n```\n\n{% /tab %}\n{% /tabs %}\n\nRemove the options from a target default using the `@nx/cypress:cypress` executor:\n\n{% tabs %}\n{% tab label=\"Before\" %}\n\n```json {% fileName=\"nx.json\" highlightLines=[7,8] %}\n{\n \"targetDefaults\": {\n \"e2e\": {\n \"cache\": true,\n \"executor\": \"@nx/cypress:cypress\",\n \"options\": {\n \"tsConfig\": \"{projectRoot}/tsconfig.json\",\n \"copyFiles\": \"**/*.spec.ts\"\n }\n }\n }\n}\n```\n\n{% /tab %}\n\n{% tab label=\"After\" %}\n\n```json {% fileName=\"nx.json\" %}\n{\n \"targetDefaults\": {\n \"e2e\": {\n \"cache\": true,\n \"executor\": \"@nx/cypress:cypress\"\n }\n }\n}\n```\n\n{% /tab %}\n{% /tabs %}\n\nRemove the options from a target default using the `@nx/cypress:cypress` executor as the key:\n\n{% tabs %}\n{% tab label=\"Before\" %}\n\n```json {% fileName=\"nx.json\" highlightLines=[6,7] %}\n{\n \"targetDefaults\": {\n \"@nx/cypress:cypress\": {\n \"cache\": true,\n \"options\": {\n \"tsConfig\": \"{projectRoot}/tsconfig.json\",\n \"copyFiles\": \"**/*.spec.ts\"\n }\n }\n }\n}\n```\n\n{% /tab %}\n\n{% tab label=\"After\" %}\n\n```json {% fileName=\"nx.json\" %}\n{\n \"targetDefaults\": {\n \"@nx/cypress:cypress\": {\n \"cache\": true\n }\n }\n}\n```\n\n{% /tab %}\n{% /tabs %}\n"
|
||||||
|
}
|
||||||
@ -41,6 +41,11 @@
|
|||||||
},
|
},
|
||||||
"description": "Updates the module specifier for the Component Testing `mount` function.",
|
"description": "Updates the module specifier for the Component Testing `mount` function.",
|
||||||
"implementation": "./src/migrations/update-20-8-0/update-component-testing-mount-imports"
|
"implementation": "./src/migrations/update-20-8-0/update-component-testing-mount-imports"
|
||||||
|
},
|
||||||
|
"remove-tsconfig-and-copy-files-options-from-cypress-executor": {
|
||||||
|
"version": "21.0.0-beta.10",
|
||||||
|
"description": "Removes the `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor.",
|
||||||
|
"implementation": "./src/migrations/update-21-0-0/remove-tsconfig-and-copy-files-options-from-cypress-executor"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"packageJsonUpdates": {
|
"packageJsonUpdates": {
|
||||||
|
|||||||
@ -22,7 +22,6 @@ describe('Cypress builder', () => {
|
|||||||
const cypressOptions: CypressExecutorOptions = {
|
const cypressOptions: CypressExecutorOptions = {
|
||||||
cypressConfig: 'apps/my-app-e2e/cypress.json',
|
cypressConfig: 'apps/my-app-e2e/cypress.json',
|
||||||
parallel: false,
|
parallel: false,
|
||||||
tsConfig: 'apps/my-app-e2e/tsconfig.json',
|
|
||||||
devServerTarget: 'my-app:serve',
|
devServerTarget: 'my-app:serve',
|
||||||
exit: true,
|
exit: true,
|
||||||
record: false,
|
record: false,
|
||||||
@ -270,7 +269,6 @@ A generator to migrate from v8 to v10 is provided. See https://nx.dev/cypress/v1
|
|||||||
const { success } = await cypressExecutor(
|
const { success } = await cypressExecutor(
|
||||||
{
|
{
|
||||||
cypressConfig: 'apps/my-app-e2e/cypress.json',
|
cypressConfig: 'apps/my-app-e2e/cypress.json',
|
||||||
tsConfig: 'apps/my-app-e2e/tsconfig.json',
|
|
||||||
devServerTarget: undefined,
|
devServerTarget: undefined,
|
||||||
headless: true,
|
headless: true,
|
||||||
exit: true,
|
exit: true,
|
||||||
|
|||||||
@ -15,7 +15,8 @@ export interface CypressExecutorOptions extends Json {
|
|||||||
devServerTarget?: string;
|
devServerTarget?: string;
|
||||||
headed?: boolean;
|
headed?: boolean;
|
||||||
/**
|
/**
|
||||||
* @deprecated use watch instead
|
* @deprecated Cypress runs headless by default. Use the --watch flag to
|
||||||
|
* control head/headless behavior instead. It will be removed in Nx v22.
|
||||||
**/
|
**/
|
||||||
headless?: boolean;
|
headless?: boolean;
|
||||||
exit?: boolean;
|
exit?: boolean;
|
||||||
@ -26,10 +27,6 @@ export interface CypressExecutorOptions extends Json {
|
|||||||
browser?: string;
|
browser?: string;
|
||||||
env?: Record<string, string>;
|
env?: Record<string, string>;
|
||||||
spec?: string;
|
spec?: string;
|
||||||
/**
|
|
||||||
* @deprecated no longer used since cypress supports typescript out of the box
|
|
||||||
**/
|
|
||||||
copyFiles?: string;
|
|
||||||
ciBuildId?: string | number;
|
ciBuildId?: string | number;
|
||||||
group?: string;
|
group?: string;
|
||||||
ignoreTestFiles?: string | string[];
|
ignoreTestFiles?: string | string[];
|
||||||
|
|||||||
@ -31,13 +31,6 @@
|
|||||||
"description": "Recompile and run tests when files change.",
|
"description": "Recompile and run tests when files change.",
|
||||||
"default": false
|
"default": false
|
||||||
},
|
},
|
||||||
"tsConfig": {
|
|
||||||
"x-deprecated": "This option no longer has any effect. Cypress supports typescript out of the box. Add any options directly to <projectRoot>/tsconfig.json or <projectRoot>/cypress/tsconfig.json",
|
|
||||||
"type": "string",
|
|
||||||
"description": "The path of the Cypress tsconfig configuration json file.",
|
|
||||||
"x-completion-type": "file",
|
|
||||||
"x-completion-glob": "tsconfig.*.json"
|
|
||||||
},
|
|
||||||
"devServerTarget": {
|
"devServerTarget": {
|
||||||
"type": "string",
|
"type": "string",
|
||||||
"description": "Dev server target to run tests against."
|
"description": "Dev server target to run tests against."
|
||||||
@ -51,7 +44,7 @@
|
|||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
"description": "Hide the browser instead of running headed.",
|
"description": "Hide the browser instead of running headed.",
|
||||||
"default": false,
|
"default": false,
|
||||||
"x-deprecated": "Cypress runs headless by default. Use the --watch flag to control head/headless behavior instead."
|
"x-deprecated": "Cypress runs headless by default. Use the --watch flag to control head/headless behavior instead. It will be removed in Nx v22."
|
||||||
},
|
},
|
||||||
"exit": {
|
"exit": {
|
||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
@ -90,12 +83,6 @@
|
|||||||
"type": "string",
|
"type": "string",
|
||||||
"description": "A comma delimited glob string that is provided to the Cypress runner to specify which spec files to run. i.e. `**examples/**,**actions.spec**`."
|
"description": "A comma delimited glob string that is provided to the Cypress runner to specify which spec files to run. i.e. `**examples/**,**actions.spec**`."
|
||||||
},
|
},
|
||||||
"copyFiles": {
|
|
||||||
"type": "string",
|
|
||||||
"description": "A regex string that is used to choose what additional integration files to copy to the dist folder.",
|
|
||||||
"x-deprecated": "No longer used since cypress supports typescript out of the box. If specified, it will be ignored.",
|
|
||||||
"x-priority": "internal"
|
|
||||||
},
|
|
||||||
"ciBuildId": {
|
"ciBuildId": {
|
||||||
"oneOf": [
|
"oneOf": [
|
||||||
{
|
{
|
||||||
|
|||||||
@ -0,0 +1,121 @@
|
|||||||
|
#### Remove `tsConfig` and `copyFiles` Options from Cypress Executor
|
||||||
|
|
||||||
|
Removes the previously deprecated and unused `tsConfig` and `copyFiles` options from the `@nx/cypress:cypress` executor configuration in all projects.
|
||||||
|
|
||||||
|
#### Examples
|
||||||
|
|
||||||
|
Remove the options from the project configuration:
|
||||||
|
|
||||||
|
{% tabs %}
|
||||||
|
{% tab label="Before" %}
|
||||||
|
|
||||||
|
```json {% fileName="apps/app1-e2e/project.json" highlightLines=[7,8] %}
|
||||||
|
{
|
||||||
|
"targets": {
|
||||||
|
"e2e": {
|
||||||
|
"executor": "@nx/cypress:cypress",
|
||||||
|
"options": {
|
||||||
|
"cypressConfig": "apps/app1-e2e/cypress.config.ts",
|
||||||
|
"tsConfig": "apps/app1-e2e/tsconfig.json",
|
||||||
|
"copyFiles": "**/*.spec.ts",
|
||||||
|
"devServerTarget": "app1:serve"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
{% /tab %}
|
||||||
|
|
||||||
|
{% tab label="After" %}
|
||||||
|
|
||||||
|
```json {% fileName="apps/app1-e2e/project.json" %}
|
||||||
|
{
|
||||||
|
"targets": {
|
||||||
|
"e2e": {
|
||||||
|
"executor": "@nx/cypress:cypress",
|
||||||
|
"options": {
|
||||||
|
"cypressConfig": "apps/app1-e2e/cypress.config.ts",
|
||||||
|
"devServerTarget": "app1:serve"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
{% /tab %}
|
||||||
|
{% /tabs %}
|
||||||
|
|
||||||
|
Remove the options from a target default using the `@nx/cypress:cypress` executor:
|
||||||
|
|
||||||
|
{% tabs %}
|
||||||
|
{% tab label="Before" %}
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" highlightLines=[7,8] %}
|
||||||
|
{
|
||||||
|
"targetDefaults": {
|
||||||
|
"e2e": {
|
||||||
|
"cache": true,
|
||||||
|
"executor": "@nx/cypress:cypress",
|
||||||
|
"options": {
|
||||||
|
"tsConfig": "{projectRoot}/tsconfig.json",
|
||||||
|
"copyFiles": "**/*.spec.ts"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
{% /tab %}
|
||||||
|
|
||||||
|
{% tab label="After" %}
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"targetDefaults": {
|
||||||
|
"e2e": {
|
||||||
|
"cache": true,
|
||||||
|
"executor": "@nx/cypress:cypress"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
{% /tab %}
|
||||||
|
{% /tabs %}
|
||||||
|
|
||||||
|
Remove the options from a target default using the `@nx/cypress:cypress` executor as the key:
|
||||||
|
|
||||||
|
{% tabs %}
|
||||||
|
{% tab label="Before" %}
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" highlightLines=[6,7] %}
|
||||||
|
{
|
||||||
|
"targetDefaults": {
|
||||||
|
"@nx/cypress:cypress": {
|
||||||
|
"cache": true,
|
||||||
|
"options": {
|
||||||
|
"tsConfig": "{projectRoot}/tsconfig.json",
|
||||||
|
"copyFiles": "**/*.spec.ts"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
{% /tab %}
|
||||||
|
|
||||||
|
{% tab label="After" %}
|
||||||
|
|
||||||
|
```json {% fileName="nx.json" %}
|
||||||
|
{
|
||||||
|
"targetDefaults": {
|
||||||
|
"@nx/cypress:cypress": {
|
||||||
|
"cache": true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
{% /tab %}
|
||||||
|
{% /tabs %}
|
||||||
@ -0,0 +1,326 @@
|
|||||||
|
import 'nx/src/internal-testing-utils/mock-project-graph';
|
||||||
|
|
||||||
|
import {
|
||||||
|
addProjectConfiguration,
|
||||||
|
readJson,
|
||||||
|
readProjectConfiguration,
|
||||||
|
updateJson,
|
||||||
|
type NxJsonConfiguration,
|
||||||
|
type ProjectConfiguration,
|
||||||
|
type Tree,
|
||||||
|
} from '@nx/devkit';
|
||||||
|
import { createTreeWithEmptyWorkspace } from '@nx/devkit/testing';
|
||||||
|
import migration from './remove-tsconfig-and-copy-files-options-from-cypress-executor';
|
||||||
|
|
||||||
|
describe('remove-tsconfig-and-copy-files-options-from-cypress-executor', () => {
|
||||||
|
let tree: Tree;
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
tree = createTreeWithEmptyWorkspace({ layout: 'apps-libs' });
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove tsConfig and copyFiles from default options', async () => {
|
||||||
|
const projectConfig: ProjectConfiguration = {
|
||||||
|
root: 'apps/app1-e2e',
|
||||||
|
sourceRoot: 'apps/app1-e2e/src',
|
||||||
|
projectType: 'application',
|
||||||
|
targets: {
|
||||||
|
e2e: {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
cypressConfig: 'apps/app1-e2e/cypress.config.ts',
|
||||||
|
tsConfig: 'apps/app1-e2e/tsconfig.json',
|
||||||
|
copyFiles: '**/*.spec.ts',
|
||||||
|
devServerTarget: 'app1:serve',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
addProjectConfiguration(tree, 'app1-e2e', projectConfig);
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const updatedConfig = readProjectConfiguration(tree, 'app1-e2e');
|
||||||
|
expect(updatedConfig.targets.e2e.options).toEqual({
|
||||||
|
cypressConfig: 'apps/app1-e2e/cypress.config.ts',
|
||||||
|
devServerTarget: 'app1:serve',
|
||||||
|
});
|
||||||
|
expect('tsConfig' in updatedConfig.targets.e2e.options).toEqual(false);
|
||||||
|
expect('copyFiles' in updatedConfig.targets.e2e.options).toEqual(false);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove tsConfig and copyFiles from configurations', async () => {
|
||||||
|
const projectConfig: ProjectConfiguration = {
|
||||||
|
root: 'apps/app1-e2e',
|
||||||
|
sourceRoot: 'apps/app1-e2e/src',
|
||||||
|
projectType: 'application',
|
||||||
|
targets: {
|
||||||
|
e2e: {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
cypressConfig: 'apps/app1-e2e/cypress.config.ts',
|
||||||
|
devServerTarget: 'app1:serve',
|
||||||
|
},
|
||||||
|
configurations: {
|
||||||
|
production: {
|
||||||
|
devServerTarget: 'app1:serve:production',
|
||||||
|
tsConfig: 'apps/app1-e2e/tsconfig.prod.json',
|
||||||
|
copyFiles: '**/*.prod.spec.ts',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
addProjectConfiguration(tree, 'app1-e2e', projectConfig);
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const updatedConfig = readProjectConfiguration(tree, 'app1-e2e');
|
||||||
|
expect(updatedConfig.targets.e2e.configurations.production).toEqual({
|
||||||
|
devServerTarget: 'app1:serve:production',
|
||||||
|
});
|
||||||
|
expect(
|
||||||
|
'tsConfig' in updatedConfig.targets.e2e.configurations.production
|
||||||
|
).toEqual(false);
|
||||||
|
expect(
|
||||||
|
'copyFiles' in updatedConfig.targets.e2e.configurations.production
|
||||||
|
).toEqual(false);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle projects without the deprecated options', async () => {
|
||||||
|
const projectConfig: ProjectConfiguration = {
|
||||||
|
root: 'apps/app2-e2e',
|
||||||
|
sourceRoot: 'apps/app2-e2e/src',
|
||||||
|
projectType: 'application',
|
||||||
|
targets: {
|
||||||
|
e2e: {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
cypressConfig: 'apps/app2-e2e/cypress.config.ts',
|
||||||
|
devServerTarget: 'app2:serve',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
addProjectConfiguration(tree, 'app2-e2e', projectConfig);
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const updatedConfig = readProjectConfiguration(tree, 'app2-e2e');
|
||||||
|
expect(updatedConfig.targets.e2e.options).toEqual({
|
||||||
|
cypressConfig: 'apps/app2-e2e/cypress.config.ts',
|
||||||
|
devServerTarget: 'app2:serve',
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle projects with multiple targets using cypress executor', async () => {
|
||||||
|
const projectConfig: ProjectConfiguration = {
|
||||||
|
root: 'apps/app3-e2e',
|
||||||
|
sourceRoot: 'apps/app3-e2e/src',
|
||||||
|
projectType: 'application',
|
||||||
|
targets: {
|
||||||
|
e2e: {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
cypressConfig: 'apps/app3-e2e/cypress.config.ts',
|
||||||
|
tsConfig: 'apps/app3-e2e/tsconfig.json',
|
||||||
|
devServerTarget: 'app3:serve',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
ct: {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
cypressConfig: 'apps/app3-e2e/cypress.config.ts',
|
||||||
|
copyFiles: '**/*.ct.spec.ts',
|
||||||
|
devServerTarget: 'app3:serve-ct',
|
||||||
|
testingType: 'component',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
addProjectConfiguration(tree, 'app3-e2e', projectConfig);
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const updatedConfig = readProjectConfiguration(tree, 'app3-e2e');
|
||||||
|
expect(updatedConfig.targets.e2e.options).toEqual({
|
||||||
|
cypressConfig: 'apps/app3-e2e/cypress.config.ts',
|
||||||
|
devServerTarget: 'app3:serve',
|
||||||
|
});
|
||||||
|
expect(updatedConfig.targets.ct.options).toEqual({
|
||||||
|
cypressConfig: 'apps/app3-e2e/cypress.config.ts',
|
||||||
|
devServerTarget: 'app3:serve-ct',
|
||||||
|
testingType: 'component',
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove tsConfig and copyFiles options in nx.json target defaults for a target with the cypress executor', async () => {
|
||||||
|
updateJson<NxJsonConfiguration>(tree, 'nx.json', (json) => {
|
||||||
|
json.targetDefaults ??= {};
|
||||||
|
json.targetDefaults.e2e = {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
cypressConfig: '{projectRoot}/cypress.config.ts',
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.json',
|
||||||
|
copyFiles: '**/*.spec.ts',
|
||||||
|
devServerTarget: '{projectName}:serve',
|
||||||
|
},
|
||||||
|
configurations: {
|
||||||
|
production: {
|
||||||
|
devServerTarget: '{projectName}:serve:production',
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.prod.json',
|
||||||
|
copyFiles: '**/*.prod.spec.ts',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
return json;
|
||||||
|
});
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const nxJson = readJson<NxJsonConfiguration>(tree, 'nx.json');
|
||||||
|
expect(nxJson.targetDefaults.e2e.options).toStrictEqual({
|
||||||
|
cypressConfig: '{projectRoot}/cypress.config.ts',
|
||||||
|
devServerTarget: '{projectName}:serve',
|
||||||
|
});
|
||||||
|
expect(nxJson.targetDefaults.e2e.options.tsConfig).toBeUndefined();
|
||||||
|
expect(nxJson.targetDefaults.e2e.options.copyFiles).toBeUndefined();
|
||||||
|
expect(nxJson.targetDefaults.e2e.configurations.production).toStrictEqual({
|
||||||
|
devServerTarget: '{projectName}:serve:production',
|
||||||
|
});
|
||||||
|
expect(
|
||||||
|
nxJson.targetDefaults.e2e.configurations.production.tsConfig
|
||||||
|
).toBeUndefined();
|
||||||
|
expect(
|
||||||
|
nxJson.targetDefaults.e2e.configurations.production.copyFiles
|
||||||
|
).toBeUndefined();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove tsConfig and copyFiles options in nx.json target defaults for the cypress executor', async () => {
|
||||||
|
updateJson<NxJsonConfiguration>(tree, 'nx.json', (json) => {
|
||||||
|
json.targetDefaults ??= {};
|
||||||
|
json.targetDefaults['@nx/cypress:cypress'] = {
|
||||||
|
options: {
|
||||||
|
cypressConfig: '{projectRoot}/cypress.config.ts',
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.json',
|
||||||
|
copyFiles: '**/*.spec.ts',
|
||||||
|
devServerTarget: '{projectName}:serve',
|
||||||
|
},
|
||||||
|
configurations: {
|
||||||
|
production: {
|
||||||
|
devServerTarget: '{projectName}:serve:production',
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.prod.json',
|
||||||
|
copyFiles: '**/*.prod.spec.ts',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
return json;
|
||||||
|
});
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const nxJson = readJson<NxJsonConfiguration>(tree, 'nx.json');
|
||||||
|
expect(nxJson.targetDefaults['@nx/cypress:cypress'].options).toStrictEqual({
|
||||||
|
cypressConfig: '{projectRoot}/cypress.config.ts',
|
||||||
|
devServerTarget: '{projectName}:serve',
|
||||||
|
});
|
||||||
|
expect(
|
||||||
|
nxJson.targetDefaults['@nx/cypress:cypress'].options.tsConfig
|
||||||
|
).toBeUndefined();
|
||||||
|
expect(
|
||||||
|
nxJson.targetDefaults['@nx/cypress:cypress'].options.copyFiles
|
||||||
|
).toBeUndefined();
|
||||||
|
expect(
|
||||||
|
nxJson.targetDefaults['@nx/cypress:cypress'].configurations.production
|
||||||
|
).toStrictEqual({
|
||||||
|
devServerTarget: '{projectName}:serve:production',
|
||||||
|
});
|
||||||
|
expect(
|
||||||
|
nxJson.targetDefaults['@nx/cypress:cypress'].configurations.production
|
||||||
|
.tsConfig
|
||||||
|
).toBeUndefined();
|
||||||
|
expect(
|
||||||
|
nxJson.targetDefaults['@nx/cypress:cypress'].configurations.production
|
||||||
|
.copyFiles
|
||||||
|
).toBeUndefined();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove empty options and configurations objects from project configuration', async () => {
|
||||||
|
const projectConfig: ProjectConfiguration = {
|
||||||
|
root: 'apps/app4-e2e',
|
||||||
|
sourceRoot: 'apps/app4-e2e/src',
|
||||||
|
projectType: 'application',
|
||||||
|
targets: {
|
||||||
|
e2e: {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
tsConfig: 'apps/app4-e2e/tsconfig.json',
|
||||||
|
copyFiles: '**/*.spec.ts',
|
||||||
|
},
|
||||||
|
configurations: {
|
||||||
|
production: {
|
||||||
|
tsConfig: 'apps/app4-e2e/tsconfig.prod.json',
|
||||||
|
copyFiles: '**/*.prod.spec.ts',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
addProjectConfiguration(tree, 'app4-e2e', projectConfig);
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const updatedConfig = readProjectConfiguration(tree, 'app4-e2e');
|
||||||
|
expect(updatedConfig.targets.e2e.options).toBeUndefined();
|
||||||
|
expect(updatedConfig.targets.e2e.configurations).toBeUndefined();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove empty targetDefault object from nx.json when using a target name as the key', async () => {
|
||||||
|
updateJson<NxJsonConfiguration>(tree, 'nx.json', (json) => {
|
||||||
|
json.targetDefaults = {};
|
||||||
|
json.targetDefaults.e2e = {
|
||||||
|
executor: '@nx/cypress:cypress',
|
||||||
|
options: {
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.json',
|
||||||
|
copyFiles: '**/*.spec.ts',
|
||||||
|
},
|
||||||
|
configurations: {
|
||||||
|
production: {
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.prod.json',
|
||||||
|
copyFiles: '**/*.prod.spec.ts',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
return json;
|
||||||
|
});
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const nxJson = readJson<NxJsonConfiguration>(tree, 'nx.json');
|
||||||
|
expect(nxJson.targetDefaults).toBeUndefined();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should remove empty targetDefault object from nx.json when using the cypress executor as the key', async () => {
|
||||||
|
updateJson<NxJsonConfiguration>(tree, 'nx.json', (json) => {
|
||||||
|
json.targetDefaults = {};
|
||||||
|
json.targetDefaults['@nx/cypress:cypress'] = {
|
||||||
|
options: {
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.json',
|
||||||
|
copyFiles: '**/*.spec.ts',
|
||||||
|
},
|
||||||
|
configurations: {
|
||||||
|
production: {
|
||||||
|
tsConfig: '{projectRoot}/tsconfig.prod.json',
|
||||||
|
copyFiles: '**/*.prod.spec.ts',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
return json;
|
||||||
|
});
|
||||||
|
|
||||||
|
await migration(tree);
|
||||||
|
|
||||||
|
const nxJson = readJson<NxJsonConfiguration>(tree, 'nx.json');
|
||||||
|
expect(nxJson.targetDefaults).toBeUndefined();
|
||||||
|
});
|
||||||
|
});
|
||||||
@ -0,0 +1,105 @@
|
|||||||
|
import {
|
||||||
|
formatFiles,
|
||||||
|
type ProjectConfiguration,
|
||||||
|
readNxJson,
|
||||||
|
readProjectConfiguration,
|
||||||
|
type TargetConfiguration,
|
||||||
|
type Tree,
|
||||||
|
updateNxJson,
|
||||||
|
updateProjectConfiguration,
|
||||||
|
} from '@nx/devkit';
|
||||||
|
import { forEachExecutorOptions } from '@nx/devkit/src/generators/executor-options-utils';
|
||||||
|
import type { CypressExecutorOptions } from '../../executors/cypress/cypress.impl';
|
||||||
|
|
||||||
|
const EXECUTOR_TO_MIGRATE = '@nx/cypress:cypress';
|
||||||
|
|
||||||
|
export default async function (tree: Tree) {
|
||||||
|
// update options from project configs
|
||||||
|
forEachExecutorOptions<CypressExecutorOptions>(
|
||||||
|
tree,
|
||||||
|
EXECUTOR_TO_MIGRATE,
|
||||||
|
(options, project, target, configuration) => {
|
||||||
|
if (options.tsConfig === undefined && options.copyFiles === undefined) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const projectConfiguration = readProjectConfiguration(tree, project);
|
||||||
|
if (configuration) {
|
||||||
|
updateConfiguration(
|
||||||
|
projectConfiguration.targets[target],
|
||||||
|
configuration
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
updateOptions(projectConfiguration.targets[target]);
|
||||||
|
}
|
||||||
|
|
||||||
|
updateProjectConfiguration(tree, project, projectConfiguration);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
|
||||||
|
// update options from nx.json target defaults
|
||||||
|
const nxJson = readNxJson(tree);
|
||||||
|
if (nxJson.targetDefaults) {
|
||||||
|
for (const [targetOrExecutor, targetConfig] of Object.entries(
|
||||||
|
nxJson.targetDefaults
|
||||||
|
)) {
|
||||||
|
if (
|
||||||
|
targetOrExecutor !== EXECUTOR_TO_MIGRATE &&
|
||||||
|
targetConfig.executor !== EXECUTOR_TO_MIGRATE
|
||||||
|
) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (targetConfig.options) {
|
||||||
|
updateOptions(targetConfig);
|
||||||
|
}
|
||||||
|
|
||||||
|
Object.keys(targetConfig.configurations ?? {}).forEach((config) => {
|
||||||
|
updateConfiguration(targetConfig, config);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (
|
||||||
|
!Object.keys(targetConfig).length ||
|
||||||
|
(Object.keys(targetConfig).length === 1 &&
|
||||||
|
Object.keys(targetConfig)[0] === 'executor')
|
||||||
|
) {
|
||||||
|
delete nxJson.targetDefaults[targetOrExecutor];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!Object.keys(nxJson.targetDefaults).length) {
|
||||||
|
delete nxJson.targetDefaults;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
updateNxJson(tree, nxJson);
|
||||||
|
}
|
||||||
|
|
||||||
|
await formatFiles(tree);
|
||||||
|
}
|
||||||
|
|
||||||
|
function updateOptions(target: TargetConfiguration) {
|
||||||
|
delete target.options.tsConfig;
|
||||||
|
delete target.options.copyFiles;
|
||||||
|
|
||||||
|
if (!Object.keys(target.options).length) {
|
||||||
|
delete target.options;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function updateConfiguration(
|
||||||
|
target: TargetConfiguration,
|
||||||
|
configuration: string
|
||||||
|
) {
|
||||||
|
delete target.configurations[configuration].tsConfig;
|
||||||
|
delete target.configurations[configuration].copyFiles;
|
||||||
|
if (
|
||||||
|
!Object.keys(target.configurations[configuration]).length &&
|
||||||
|
(!target.defaultConfiguration ||
|
||||||
|
target.defaultConfiguration !== configuration)
|
||||||
|
) {
|
||||||
|
delete target.configurations[configuration];
|
||||||
|
}
|
||||||
|
if (!Object.keys(target.configurations).length) {
|
||||||
|
delete target.configurations;
|
||||||
|
}
|
||||||
|
}
|
||||||
Loading…
x
Reference in New Issue
Block a user