feat(vite): update vite-tsconfig-paths (#13714)
This commit is contained in:
parent
e470b6e259
commit
45ce3b2a0a
File diff suppressed because one or more lines are too long
@ -178,7 +178,6 @@ export default defineConfig({
|
||||
react(),
|
||||
ViteTsConfigPathsPlugin({
|
||||
root: '../../',
|
||||
projects: ['tsconfig.base.json'],
|
||||
}),
|
||||
],
|
||||
});
|
||||
@ -221,7 +220,6 @@ export default mergeConfig(baseConfig, {
|
||||
react(),
|
||||
ViteTsConfigPathsPlugin({
|
||||
root: '../../',
|
||||
projects: ['tsconfig.base.json'],
|
||||
}),
|
||||
],
|
||||
});
|
||||
|
||||
@ -1 +1,21 @@
|
||||
{}
|
||||
{
|
||||
"schematics": {
|
||||
"update-vite-tsconfig-paths": {
|
||||
"cli": "nx",
|
||||
"version": "15.3.1-beta.0",
|
||||
"description": "Update vite-tsconfig-paths to 4.0.1 and remove projects property from vite.config.ts.",
|
||||
"factory": "./src/migrations/update-15-3-1/update-vite-tsconfig-paths"
|
||||
}
|
||||
},
|
||||
"packageJsonUpdates": {
|
||||
"15.3.1-beta.0": {
|
||||
"version": "15.3.1-beta.0",
|
||||
"packages": {
|
||||
"vite-tsconfig-paths": {
|
||||
"version": "^4.0.1",
|
||||
"alwaysAddToPackageJson": true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
12
packages/vite/migrations.spec.ts
Normal file
12
packages/vite/migrations.spec.ts
Normal file
@ -0,0 +1,12 @@
|
||||
import path = require('path');
|
||||
import json = require('./migrations.json');
|
||||
|
||||
describe('Vite migrations', () => {
|
||||
it('should have valid paths', () => {
|
||||
Object.values(json.schematics).forEach((m) => {
|
||||
expect(() =>
|
||||
require.resolve(path.join(__dirname, `${m.factory}.ts`))
|
||||
).not.toThrow();
|
||||
});
|
||||
});
|
||||
});
|
||||
@ -13,7 +13,7 @@ Object {
|
||||
"jsdom": "~20.0.3",
|
||||
"vite": "^3.0.5",
|
||||
"vite-plugin-eslint": "^1.6.0",
|
||||
"vite-tsconfig-paths": "^3.5.2",
|
||||
"vite-tsconfig-paths": "^4.0.1",
|
||||
"vitest": "^0.25.1",
|
||||
},
|
||||
"name": "test-name",
|
||||
|
||||
@ -106,7 +106,7 @@ describe('vitest generator', () => {
|
||||
/// <reference types=\\"vitest\\" />
|
||||
import { defineConfig } from 'vite';
|
||||
import react from '@vitejs/plugin-react';
|
||||
import tsconfigPaths from 'vite-tsconfig-paths';
|
||||
import viteTsConfigPaths from 'vite-tsconfig-paths';
|
||||
|
||||
|
||||
export default defineConfig({
|
||||
@ -118,9 +118,8 @@ describe('vitest generator', () => {
|
||||
plugins: [
|
||||
|
||||
react(),
|
||||
tsconfigPaths({
|
||||
viteTsConfigPaths({
|
||||
root: '../../',
|
||||
projects: ['tsconfig.base.json'],
|
||||
}),
|
||||
],
|
||||
|
||||
@ -150,7 +149,7 @@ describe('vitest generator', () => {
|
||||
/// <reference types=\\"vitest\\" />
|
||||
import { defineConfig } from 'vite';
|
||||
import react from '@vitejs/plugin-react';
|
||||
import tsconfigPaths from 'vite-tsconfig-paths';
|
||||
import viteTsConfigPaths from 'vite-tsconfig-paths';
|
||||
|
||||
|
||||
export default defineConfig({
|
||||
@ -162,9 +161,8 @@ describe('vitest generator', () => {
|
||||
plugins: [
|
||||
|
||||
react(),
|
||||
tsconfigPaths({
|
||||
viteTsConfigPaths({
|
||||
root: '../../',
|
||||
projects: ['tsconfig.base.json'],
|
||||
}),
|
||||
],
|
||||
|
||||
|
||||
@ -0,0 +1,35 @@
|
||||
import { addDependenciesToPackageJson, Tree } from '@nrwl/devkit';
|
||||
import { createTreeWithEmptyV1Workspace } from '@nrwl/devkit/testing';
|
||||
import { mockViteReactAppGenerator } from '../../utils/test-utils';
|
||||
import {
|
||||
getTsSourceFile,
|
||||
removeProjectsFromViteTsConfigPaths,
|
||||
} from './update-vite-tsconfig-paths';
|
||||
|
||||
describe('remove projects from vite-tsconfig-paths', () => {
|
||||
let tree: Tree;
|
||||
|
||||
beforeEach(() => {
|
||||
tree = createTreeWithEmptyV1Workspace();
|
||||
mockViteReactAppGenerator(tree);
|
||||
const existing = 'existing';
|
||||
const existingVersion = '1.0.0';
|
||||
addDependenciesToPackageJson(
|
||||
tree,
|
||||
{ 'vite-tsconfig-paths': '^3.6.0', [existing]: existingVersion },
|
||||
{ [existing]: existingVersion }
|
||||
);
|
||||
});
|
||||
|
||||
it('should remove the projects attribute from vite-tsconfig-paths', async () => {
|
||||
await removeProjectsFromViteTsConfigPaths(tree);
|
||||
|
||||
const file = getTsSourceFile(
|
||||
tree,
|
||||
'apps/my-test-react-vite-app/vite.config.ts'
|
||||
);
|
||||
|
||||
expect(file.getText().includes('tsconfig.base.json')).toBeFalsy();
|
||||
expect(file.getText().includes('projects')).toBeFalsy();
|
||||
});
|
||||
});
|
||||
@ -0,0 +1,100 @@
|
||||
import {
|
||||
applyChangesToString,
|
||||
ChangeType,
|
||||
formatFiles,
|
||||
joinPathFragments,
|
||||
readProjectConfiguration,
|
||||
Tree,
|
||||
workspaceRoot,
|
||||
} from '@nrwl/devkit';
|
||||
|
||||
import { forEachExecutorOptions } from '@nrwl/workspace/src/utilities/executor-options-utils';
|
||||
import { findNodes } from 'nx/src/utils/typescript';
|
||||
import ts = require('typescript');
|
||||
|
||||
export async function removeProjectsFromViteTsConfigPaths(tree: Tree) {
|
||||
findAllProjectsWithViteConfig(tree);
|
||||
await formatFiles(tree);
|
||||
}
|
||||
|
||||
function findAllProjectsWithViteConfig(tree: Tree): void {
|
||||
forEachExecutorOptions(tree, '@nrwl/vite:build', (options, project) => {
|
||||
const projectConfiguration = readProjectConfiguration(tree, project);
|
||||
const viteConfig = normalizeConfigFilePathWithTree(
|
||||
tree,
|
||||
projectConfiguration.root,
|
||||
options?.['configFile'],
|
||||
workspaceRoot
|
||||
);
|
||||
if (viteConfig) {
|
||||
const file = getTsSourceFile(tree, viteConfig);
|
||||
const appFileContent = tree.read(viteConfig, 'utf-8');
|
||||
let newContents = appFileContent;
|
||||
const defineConfig = findNodes(file, [ts.SyntaxKind.CallExpression]);
|
||||
let startOfProjects, endOfProjects;
|
||||
defineConfig.forEach((node) => {
|
||||
if (node.getText().startsWith('defineConfig')) {
|
||||
node.getChildren().forEach((defineConfigContentNode) => {
|
||||
// Make sure it's the one we are looking for
|
||||
// We cannot assume that it's called tsConfigPaths
|
||||
// So make sure it includes `projects` and `root`
|
||||
if (
|
||||
defineConfigContentNode.getText().includes('projects') &&
|
||||
defineConfigContentNode.getText().includes('root')
|
||||
) {
|
||||
findNodes(defineConfigContentNode, [
|
||||
ts.SyntaxKind.PropertyAssignment,
|
||||
]).forEach((nodePA) => {
|
||||
if (nodePA.getText().startsWith('projects')) {
|
||||
startOfProjects = nodePA.getStart();
|
||||
endOfProjects = nodePA.getEnd();
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
if (startOfProjects && endOfProjects) {
|
||||
newContents = applyChangesToString(newContents, [
|
||||
{
|
||||
type: ChangeType.Delete,
|
||||
start: startOfProjects,
|
||||
length: endOfProjects - startOfProjects + 1,
|
||||
},
|
||||
]);
|
||||
tree.write(viteConfig, newContents);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
export function getTsSourceFile(host: Tree, path: string): ts.SourceFile {
|
||||
const buffer = host.read(path);
|
||||
if (!buffer) {
|
||||
throw new Error(`Could not read TS file (${path}).`);
|
||||
}
|
||||
const content = buffer.toString();
|
||||
const source = ts.createSourceFile(
|
||||
path,
|
||||
content,
|
||||
ts.ScriptTarget.Latest,
|
||||
true
|
||||
);
|
||||
|
||||
return source;
|
||||
}
|
||||
|
||||
function normalizeConfigFilePathWithTree(
|
||||
tree: Tree,
|
||||
projectRoot: string,
|
||||
configFile?: string,
|
||||
workspaceRoot?: string
|
||||
): string {
|
||||
return configFile
|
||||
? joinPathFragments(`${workspaceRoot}/${configFile}`)
|
||||
: tree.exists(joinPathFragments(`${projectRoot}/vite.config.ts`))
|
||||
? joinPathFragments(`${projectRoot}/vite.config.ts`)
|
||||
: tree.exists(joinPathFragments(`${projectRoot}/vite.config.js`))
|
||||
? joinPathFragments(`${projectRoot}/vite.config.js`)
|
||||
: undefined;
|
||||
}
|
||||
@ -405,16 +405,13 @@ export function writeViteConfig(tree: Tree, options: Schema) {
|
||||
host: 'localhost',
|
||||
},`;
|
||||
|
||||
const projectsTsConfig = tree.exists('tsconfig.base.json')
|
||||
? "'tsconfig.base.json'"
|
||||
: '';
|
||||
switch (options.uiFramework) {
|
||||
case 'react':
|
||||
viteConfigContent = `
|
||||
${options.includeVitest ? '/// <reference types="vitest" />' : ''}
|
||||
import { defineConfig } from 'vite';
|
||||
import react from '@vitejs/plugin-react';
|
||||
import tsconfigPaths from 'vite-tsconfig-paths';
|
||||
import viteTsConfigPaths from 'vite-tsconfig-paths';
|
||||
${
|
||||
options.includeLib
|
||||
? `import dts from 'vite-plugin-dts';\nimport { join } from 'path';`
|
||||
@ -426,9 +423,8 @@ ${options.includeVitest ? '/// <reference types="vitest" />' : ''}
|
||||
plugins: [
|
||||
${options.includeLib ? dtsPlugin : ''}
|
||||
react(),
|
||||
tsconfigPaths({
|
||||
viteTsConfigPaths({
|
||||
root: '${offsetFromRoot(projectConfig.root)}',
|
||||
projects: [${projectsTsConfig}],
|
||||
}),
|
||||
],
|
||||
${buildOption}
|
||||
@ -440,7 +436,7 @@ ${options.includeVitest ? '/// <reference types="vitest" />' : ''}
|
||||
viteConfigContent = `
|
||||
${options.includeVitest ? '/// <reference types="vitest" />' : ''}
|
||||
import { defineConfig } from 'vite';
|
||||
import tsconfigPaths from 'vite-tsconfig-paths';
|
||||
import viteTsConfigPaths from 'vite-tsconfig-paths';
|
||||
${
|
||||
options.includeLib
|
||||
? `import dts from 'vite-plugin-dts';\nimport { join } from 'path';`
|
||||
@ -451,9 +447,8 @@ ${options.includeVitest ? '/// <reference types="vitest" />' : ''}
|
||||
${serverOption}
|
||||
plugins: [
|
||||
${options.includeLib ? dtsPlugin : ''}
|
||||
tsconfigPaths({
|
||||
viteTsConfigPaths({
|
||||
root: '${offsetFromRoot(projectConfig.root)}',
|
||||
projects: [${projectsTsConfig}],
|
||||
}),
|
||||
],
|
||||
${buildOption}
|
||||
|
||||
@ -4,6 +4,7 @@ import {
|
||||
logger,
|
||||
parseTargetString,
|
||||
readTargetOptions,
|
||||
Tree,
|
||||
} from '@nrwl/devkit';
|
||||
import { existsSync } from 'fs';
|
||||
import { join, relative } from 'path';
|
||||
@ -32,9 +33,9 @@ export async function getBuildAndSharedConfig(
|
||||
root: projectRoot,
|
||||
base: options.base,
|
||||
configFile: normalizeConfigFilePath(
|
||||
projectRoot,
|
||||
options.configFile,
|
||||
context.root,
|
||||
projectRoot
|
||||
context.root
|
||||
),
|
||||
plugins: [replaceFiles(options.fileReplacements)],
|
||||
build: getViteBuildOptions(
|
||||
@ -45,9 +46,9 @@ export async function getBuildAndSharedConfig(
|
||||
}
|
||||
|
||||
export function normalizeConfigFilePath(
|
||||
configFile: string,
|
||||
workspaceRoot: string,
|
||||
projectRoot: string
|
||||
projectRoot: string,
|
||||
configFile?: string,
|
||||
workspaceRoot?: string
|
||||
): string {
|
||||
return configFile
|
||||
? joinPathFragments(`${workspaceRoot}/${configFile}`)
|
||||
|
||||
@ -0,0 +1,53 @@
|
||||
{
|
||||
"name": "my-test-react-vite-app",
|
||||
"$schema": "../../node_modules/nx/schemas/project-schema.json",
|
||||
"root": "apps/my-test-react-vite-app",
|
||||
"sourceRoot": "apps/my-test-react-vite-app/src",
|
||||
"projectType": "application",
|
||||
"targets": {
|
||||
"build": {
|
||||
"executor": "@nrwl/vite:build",
|
||||
"outputs": ["{options.outputPath}"],
|
||||
"defaultConfiguration": "production",
|
||||
"options": {
|
||||
"outputPath": "dist/apps/my-test-react-vite-app"
|
||||
},
|
||||
"configurations": {
|
||||
"development": {},
|
||||
"production": {}
|
||||
}
|
||||
},
|
||||
"serve": {
|
||||
"executor": "@nrwl/vite:dev-server",
|
||||
"defaultConfiguration": "development",
|
||||
"options": {
|
||||
"buildTarget": "my-test-react-vite-app:build"
|
||||
},
|
||||
"configurations": {
|
||||
"development": {
|
||||
"buildTarget": "my-test-react-vite-app:build:development",
|
||||
"hmr": true
|
||||
},
|
||||
"production": {
|
||||
"buildTarget": "my-test-react-vite-app:build:production",
|
||||
"hmr": false
|
||||
}
|
||||
}
|
||||
},
|
||||
"test": {
|
||||
"executor": "@nrwl/vite:test",
|
||||
"outputs": ["{projectRoot}/coverage"],
|
||||
"options": {
|
||||
"passWithNoTests": true
|
||||
}
|
||||
},
|
||||
"lint": {
|
||||
"executor": "@nrwl/linter:eslint",
|
||||
"outputs": ["{options.outputFile}"],
|
||||
"options": {
|
||||
"lintFilePatterns": ["apps/my-test-react-vite-app/**/*.{ts,tsx,js,jsx}"]
|
||||
}
|
||||
}
|
||||
},
|
||||
"tags": []
|
||||
}
|
||||
@ -1,7 +1,139 @@
|
||||
import { Tree, writeJson } from '@nrwl/devkit';
|
||||
import * as reactAppConfig from './test-files/react-project.config.json';
|
||||
import * as reactViteConfig from './test-files/react-vite-project.config.json';
|
||||
import * as webAppConfig from './test-files/web-project.config.json';
|
||||
|
||||
export function mockViteReactAppGenerator(tree: Tree): Tree {
|
||||
const appName = 'my-test-react-vite-app';
|
||||
|
||||
tree.write(
|
||||
`apps/${appName}/src/main.tsx`,
|
||||
`import ReactDOM from 'react-dom';\n`
|
||||
);
|
||||
|
||||
tree.write(
|
||||
`apps/${appName}/tsconfig.json`,
|
||||
`{
|
||||
"compilerOptions": {
|
||||
"jsx": "react-jsx",
|
||||
"allowJs": false,
|
||||
"esModuleInterop": false,
|
||||
"allowSyntheticDefaultImports": true,
|
||||
"strict": true,
|
||||
"types": ["vite/client"]
|
||||
},
|
||||
"files": [],
|
||||
"include": [],
|
||||
"references": [
|
||||
{
|
||||
"path": "./tsconfig.app.json"
|
||||
},
|
||||
{
|
||||
"path": "./tsconfig.spec.json"
|
||||
}
|
||||
],
|
||||
"extends": "../../tsconfig.base.json"
|
||||
}
|
||||
`
|
||||
);
|
||||
tree.write(
|
||||
`apps/${appName}/tsconfig.app.json`,
|
||||
`{
|
||||
"extends": "./tsconfig.json",
|
||||
"compilerOptions": {
|
||||
"outDir": "../../dist/out-tsc",
|
||||
"types": ["node"]
|
||||
},
|
||||
"files": [
|
||||
"../../node_modules/@nrwl/react/typings/cssmodule.d.ts",
|
||||
"../../node_modules/@nrwl/react/typings/image.d.ts"
|
||||
],
|
||||
"exclude": [
|
||||
"src/**/*.spec.ts",
|
||||
"src/**/*.test.ts",
|
||||
"src/**/*.spec.tsx",
|
||||
"src/**/*.test.tsx",
|
||||
"src/**/*.spec.js",
|
||||
"src/**/*.test.js",
|
||||
"src/**/*.spec.jsx",
|
||||
"src/**/*.test.jsx"
|
||||
],
|
||||
"include": ["src/**/*.js", "src/**/*.jsx", "src/**/*.ts", "src/**/*.tsx"]
|
||||
}
|
||||
`
|
||||
);
|
||||
|
||||
tree.write(
|
||||
`apps/${appName}/index.html`,
|
||||
`<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<title>Rv1</title>
|
||||
<base href="/" />
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<link rel="icon" type="image/x-icon" href="/favicon.ico" />
|
||||
<link rel="stylesheet" href="/src/styles.css" />
|
||||
</head>
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
<script type="module" src="/src/main.tsx"></script>
|
||||
</body>
|
||||
</html>`
|
||||
);
|
||||
|
||||
tree.write(
|
||||
`apps/${appName}/vite.config.ts`,
|
||||
`/// <reference types="vitest" />
|
||||
import { defineConfig } from 'vite';
|
||||
import react from '@vitejs/plugin-react';
|
||||
import tsconfigPaths from 'vite-tsconfig-paths';
|
||||
|
||||
export default defineConfig({
|
||||
server: {
|
||||
port: 4200,
|
||||
host: 'localhost',
|
||||
},
|
||||
plugins: [
|
||||
react(),
|
||||
tsconfigPaths({
|
||||
root: '../../',
|
||||
projects: ['tsconfig.base.json'],
|
||||
}),
|
||||
],
|
||||
|
||||
test: {
|
||||
globals: true,
|
||||
cache: {
|
||||
dir: '../../node_modules/.vitest',
|
||||
},
|
||||
environment: 'jsdom',
|
||||
include: ['src/**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}'],
|
||||
},
|
||||
});
|
||||
`
|
||||
);
|
||||
|
||||
writeJson(tree, 'workspace.json', {
|
||||
projects: {
|
||||
'my-test-react-vite-app': {
|
||||
...reactViteConfig,
|
||||
root: `apps/${appName}`,
|
||||
projectType: 'application',
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
writeJson(tree, `apps/${appName}/project.json`, {
|
||||
...reactViteConfig,
|
||||
root: `apps/${appName}`,
|
||||
projectType: 'application',
|
||||
});
|
||||
|
||||
return tree;
|
||||
}
|
||||
|
||||
export function mockReactAppGenerator(tree: Tree): Tree {
|
||||
const appName = 'my-test-react-app';
|
||||
|
||||
@ -84,20 +216,15 @@ export function mockReactAppGenerator(tree: Tree): Tree {
|
||||
</html>`
|
||||
);
|
||||
|
||||
writeJson(
|
||||
tree,
|
||||
'workspace.json',
|
||||
|
||||
{
|
||||
projects: {
|
||||
'my-test-react-app': {
|
||||
...reactAppConfig,
|
||||
root: `apps/${appName}`,
|
||||
projectType: 'application',
|
||||
},
|
||||
writeJson(tree, 'workspace.json', {
|
||||
projects: {
|
||||
'my-test-react-app': {
|
||||
...reactAppConfig,
|
||||
root: `apps/${appName}`,
|
||||
projectType: 'application',
|
||||
},
|
||||
}
|
||||
);
|
||||
},
|
||||
});
|
||||
|
||||
writeJson(tree, `apps/${appName}/project.json`, {
|
||||
...reactAppConfig,
|
||||
|
||||
@ -6,7 +6,7 @@ export const vitestUiVersion = '^0.9.3';
|
||||
export const vitePluginReactVersion = '^2.2.0';
|
||||
export const vitePluginVueVersion = '^3.2.0';
|
||||
export const vitePluginVueJsxVersion = '^2.1.1';
|
||||
export const viteTsConfigPathsVersion = '^3.5.2';
|
||||
export const viteTsConfigPathsVersion = '^4.0.1';
|
||||
export const jsdomVersion = '~20.0.3';
|
||||
export const vitePluginDtsVersion = '~1.7.1';
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user