Skip to content

Commit

Permalink
Extend async function config support to vitest plugin (#303)
Browse files Browse the repository at this point in the history
  • Loading branch information
webpro committed Oct 22, 2023
1 parent 766a9a0 commit 407be68
Show file tree
Hide file tree
Showing 10 changed files with 82 additions and 69 deletions.
30 changes: 20 additions & 10 deletions fixtures/plugins/vitest/vite.config.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,23 @@
import { defineConfig } from 'vitest/config';

export default defineConfig({
test: {
environment: 'edge-runtime',
setupFiles: ['./setup.js'],
globalSetup: ['./global.ts'],
coverage: {
reporter: ['html', 'lcov'],
provider: 'c8',
},
},
export default defineConfig(async ({ mode, command }) => {
if (mode === 'development') {
return {
test: {
setupFiles: ['./setup.js'],
globalSetup: ['./global.ts'],
coverage: {
reporter: ['html', 'lcov'],
provider: 'c8',
},
},
};
}
if (mode === 'production') {
return {
test: {
environment: 'edge-runtime',
},
};
}
});
1 change: 0 additions & 1 deletion fixtures/plugins/vitest3/vite.config.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
/// <reference types="vitest" />
import react from '@vitejs/plugin-react-swc';
import path from 'path';
import { defineConfig } from 'vite';
import svgr from 'vite-plugin-svgr';
import checker from 'vite-plugin-checker';
Expand Down
19 changes: 4 additions & 15 deletions src/plugins/vite/index.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import { timerify } from '../../util/Performance.js';
import { hasDependency, load } from '../../util/plugin.js';
import { findVitestDeps } from '../vitest/index.js';
import type { ViteConfig, MODE, COMMAND } from './types.js';
import { findVitestDependencies } from '../vitest/index.js';
import type { IsPluginEnabledCallback, GenericPluginCallback } from '../../types/plugins.js';
import type { ViteConfigOrFn } from '../vitest/types.js';

// https://vitejs.dev/config/

Expand All @@ -16,22 +16,11 @@ export const isEnabled: IsPluginEnabledCallback = ({ dependencies }) => hasDepen
export const CONFIG_FILE_PATTERNS = ['vite.config.{js,ts}'];

const findViteDependencies: GenericPluginCallback = async (configFilePath, options) => {
const localConfig: ViteConfig | undefined = await load(configFilePath);
const localConfig: ViteConfigOrFn | undefined = await load(configFilePath);

if (!localConfig) return [];

if (typeof localConfig === 'function') {
const dependencies = new Set<string>();
for (const command of ['dev', 'serve', 'build'] as COMMAND[]) {
for (const mode of ['development', 'production'] as MODE[]) {
const config = await localConfig({ command, mode, ssrBuild: undefined });
findVitestDeps(config, options).forEach(dependency => dependencies.add(dependency));
}
}
return Array.from(dependencies);
}

return findVitestDeps(localConfig, options);
return findVitestDependencies(localConfig, options);
};

export const findDependencies = timerify(findViteDependencies);
16 changes: 0 additions & 16 deletions src/plugins/vite/types.ts

This file was deleted.

4 changes: 2 additions & 2 deletions src/plugins/vitest/helpers.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import type { VitestConfig } from './types.js';
import type { ViteConfig } from './types.js';

/**
* Sources:
Expand Down Expand Up @@ -31,7 +31,7 @@ export const getEnvPackageName = (env: VitestEnvironment) => {

const builtInReporters = ['default', 'verbose', 'dot', 'json', 'tap', 'tap-flat', 'junit', 'hanging-process'];

export const getExternalReporters = (reporters?: VitestConfig['test']['reporters']) =>
export const getExternalReporters = (reporters?: ViteConfig['test']['reporters']) =>
reporters
? [reporters].flat().filter(reporter => typeof reporter === 'string' && !builtInReporters.includes(reporter))
: [];
53 changes: 34 additions & 19 deletions src/plugins/vitest/index.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
import { compact } from '../../util/array.js';
import { timerify } from '../../util/Performance.js';
import { hasDependency, load } from '../../util/plugin.js';
import { toEntryPattern } from '../../util/protocols.js';
import { getEnvPackageName, getExternalReporters } from './helpers.js';
import type { VitestConfigOrFn, VitestWorkspaceConfig } from './types.js';
import type { ViteConfigOrFn, VitestWorkspaceConfig, ViteConfig, MODE, COMMAND } from './types.js';
import type {
IsPluginEnabledCallback,
GenericPluginCallback,
Expand All @@ -24,18 +23,13 @@ export const CONFIG_FILE_PATTERNS = ['vitest.config.ts', 'vitest.{workspace,proj
/** @public */
export const ENTRY_FILE_PATTERNS = ['**/*.{test,spec}.?(c|m)[jt]s?(x)'];

export const findVitestDeps = (localConfig: VitestConfigOrFn, options: GenericPluginCallbackOptions) => {
const { isProduction } = options;

localConfig = typeof localConfig === 'function' ? localConfig() : localConfig;

if (!localConfig || !localConfig.test) return [];

const findConfigDependencies = (localConfig: ViteConfig, options: GenericPluginCallbackOptions) => {
const { isProduction, config } = options;
const testConfig = localConfig.test;

const entryPatterns = (options.config?.entry ?? testConfig.include ?? ENTRY_FILE_PATTERNS).map(toEntryPattern);
const entryPatterns = (config?.entry ?? testConfig?.include ?? ENTRY_FILE_PATTERNS).map(toEntryPattern);

if (isProduction) return entryPatterns;
if (!testConfig || isProduction) return entryPatterns;

const environments = testConfig.environment ? [getEnvPackageName(testConfig.environment)] : [];
const reporters = getExternalReporters(testConfig.reporters);
Expand All @@ -45,14 +39,35 @@ export const findVitestDeps = (localConfig: VitestConfigOrFn, options: GenericPl
return [...entryPatterns, ...environments, ...reporters, ...coverage, ...setupFiles, ...globalSetup];
};

const findVitestDependencies: GenericPluginCallback = async (configFilePath, options) => {
const localConfig: VitestConfigOrFn | VitestWorkspaceConfig | undefined = await load(configFilePath);
export const findVitestDependencies = async (localConfig: ViteConfigOrFn, options: GenericPluginCallbackOptions) => {
if (!localConfig) return [];

if (typeof localConfig === 'function') {
const dependencies = new Set<string>();
for (const command of ['dev', 'serve', 'build'] as COMMAND[]) {
for (const mode of ['development', 'production'] as MODE[]) {
const config = await localConfig({ command, mode, ssrBuild: undefined });
findConfigDependencies(config, options).forEach(dependency => dependencies.add(dependency));
}
}
return Array.from(dependencies);
}

if (!localConfig.test) return [];

return findConfigDependencies(localConfig, options);
};

const findVitestWorkspaceDependencies: GenericPluginCallback = async (configFilePath, options) => {
const localConfig: ViteConfigOrFn | VitestWorkspaceConfig | undefined = await load(configFilePath);

return compact(
[localConfig]
.flat()
.flatMap(config => (!config || typeof config === 'string' ? [] : findVitestDeps(config, options)))
);
const dependencies = new Set<string>();
for (const config of [localConfig].flat()) {
if (config && typeof config !== 'string') {
(await findVitestDependencies(config, options)).forEach(dependency => dependencies.add(dependency));
}
}
return Array.from(dependencies);
};

export const findDependencies = timerify(findVitestDependencies);
export const findDependencies = timerify(findVitestWorkspaceDependencies);
22 changes: 19 additions & 3 deletions src/plugins/vitest/types.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
export interface VitestConfig {
interface VitestConfig {
test: {
include: string[];
coverage?: {
Expand All @@ -11,6 +11,22 @@ export interface VitestConfig {
};
}

export type VitestConfigOrFn = VitestConfig | (() => VitestConfig);
export interface ViteConfig extends VitestConfig {
plugins: unknown[];
}

export type COMMAND = 'dev' | 'serve' | 'build';
export type MODE = 'development' | 'production';

interface Options {
command: COMMAND;
mode: MODE;
ssrBuild?: boolean | undefined;
}

export type ViteConfigOrFn =
| ViteConfig
| ((options: Options) => ViteConfig)
| ((options: Options) => Promise<ViteConfig>);

export type VitestWorkspaceConfig = (string | VitestConfig)[];
export type VitestWorkspaceConfig = (string | ViteConfig)[];
2 changes: 1 addition & 1 deletion test/plugins/vitest.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,10 +33,10 @@ test('Find dependencies in vitest configuration (vite)', async () => {
const dependencies = await vitest.findDependencies(configFilePath, { cwd, manifest, config });
assert.deepEqual(dependencies, [
'entry:**/*.{test,spec}.?(c|m)[jt]s?(x)',
'@edge-runtime/vm',
'@vitest/coverage-c8',
'./setup.js',
'./global.ts',
'@edge-runtime/vm',
]);
});

Expand Down
2 changes: 1 addition & 1 deletion test/plugins/vitest2.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import baseCounters from '../helpers/baseCounters.js';

const cwd = resolve('fixtures/plugins/vitest2');

test('Find dependencies in vitest configuration (entry)', async () => {
test('Find dependencies in vitest configuration (entry) 2', async () => {
const { issues, counters } = await main({
...baseArguments,
cwd,
Expand Down
2 changes: 1 addition & 1 deletion test/plugins/vitest3.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import baseCounters from '../helpers/baseCounters.js';

const cwd = resolve('fixtures/plugins/vitest3');

test('Find dependencies in vitest configuration (entry)', async () => {
test('Find dependencies in vitest configuration (entry) 3', async () => {
const { issues, counters } = await main({
...baseArguments,
cwd,
Expand Down

0 comments on commit 407be68

Please sign in to comment.