Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor: use vite-node to load globalSetup #624

Merged
merged 4 commits into from
Jan 27, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions .editorconfig
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
root = true

[*]
charset = utf-8
indent_style = space
indent_size = 2
end_of_line = lf
insert_final_newline = true
trim_trailing_whitespace = true
1 change: 1 addition & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
* text=auto eol=lf
46 changes: 22 additions & 24 deletions packages/vitest/src/node/plugins/globalSetup.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import type { Plugin, ViteDevServer } from 'vite'
import type { Plugin } from 'vite'
import { ViteNodeRunner } from 'vite-node/client'
import type { Vitest } from '../core'
import { toArray } from '../../utils'

interface GlobalSetupFile {
Expand All @@ -7,13 +9,25 @@ interface GlobalSetupFile {
teardown?: Function
}

async function loadGlobalSetupFiles(server: ViteDevServer): Promise<GlobalSetupFile[]> {
async function loadGlobalSetupFiles(ctx: Vitest): Promise<GlobalSetupFile[]> {
const node = ctx.vitenode
const server = ctx.server
const runner = new ViteNodeRunner({
root: server.config.root,
base: server.config.base,
fetchModule(id) {
return node.fetchModule(id)
},
resolveId(id, importer) {
return node.resolveId(id, importer)
},
})
Comment on lines +15 to +24
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could we also reuse the vite-node server?

Copy link
Contributor Author

@dominikg dominikg Jan 25, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

you mean the runner? The only 2 instances i found of that are in the cli not exposed/sharable and in execute but thats wrapped in VitestRunner and we don't want/need mocking for globalSetup files 🤔

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, never mind, I misread :P

const globalSetupFiles = toArray(server.config.test?.globalSetup)
return Promise.all(globalSetupFiles.map(file => loadGlobalSetupFile(file, server)))
return Promise.all(globalSetupFiles.map(file => loadGlobalSetupFile(file, runner)))
}

async function loadGlobalSetupFile(file: string, server: ViteDevServer): Promise<GlobalSetupFile> {
const m = await server.ssrLoadModule(file)
async function loadGlobalSetupFile(file: string, runner: ViteNodeRunner): Promise<GlobalSetupFile> {
const m = await runner.executeFile(file)
for (const exp of ['default', 'setup', 'teardown']) {
if (m[exp] != null && typeof m[exp] !== 'function')
throw new Error(`invalid export in globalSetup file ${file}: ${exp} must be a function`)
Expand All @@ -36,33 +50,17 @@ async function loadGlobalSetupFile(file: string, server: ViteDevServer): Promise
}
}

export const GlobalSetupPlugin = (): Plugin => {
let server: ViteDevServer
export const GlobalSetupPlugin = (ctx: Vitest): Plugin => {
let globalSetupFiles: GlobalSetupFile[]
return {
name: 'vitest:global-setup-plugin',
enforce: 'pre',

// @ts-expect-error ssr is still flagged as alpha
config(config) {
if (config.test?.globalSetup) {
return {
ssr: {
noExternal: true, // needed so ssrLoadModule call doesn't initialize server._ssrExternals
},
}
}
},

configureServer(_server) {
server = _server
},

async buildStart() {
if (!server.config.test?.globalSetup)
if (!ctx.server.config.test?.globalSetup)
return

globalSetupFiles = await loadGlobalSetupFiles(server)
globalSetupFiles = await loadGlobalSetupFiles(ctx)
for (const globalSetupFile of globalSetupFiles) {
const teardown = await globalSetupFile.setup?.()
if (teardown == null || !!globalSetupFile.teardown)
Expand Down
2 changes: 1 addition & 1 deletion packages/vitest/src/node/plugins/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ export async function VitestPlugin(options: UserConfig = {}, viteOverrides: Vite
},
},
MocksPlugin(),
GlobalSetupPlugin(),
GlobalSetupPlugin(ctx),
options.ui
? await UIPlugin()
: null,
Expand Down
1 change: 1 addition & 0 deletions test/global-setup/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Hello Vitest
16 changes: 16 additions & 0 deletions test/global-setup/setupFiles/another-vite-instance.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import { createServer } from 'vite'
import { resolve } from 'pathe'

export async function setup() {
const server = await createServer({
root: resolve(__dirname, '..'),
server: {
port: 9988,
},
})

await server.listen(9988)
return async() => {
await server.close()
}
}
20 changes: 8 additions & 12 deletions test/global-setup/test/global-setup.test.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,12 @@
import http from 'http'

async function sendRequest(host: string, port: number) {
return new Promise<string>((resolve) => {
http.request({ host, port }, (res) => {
let data = ''
res.on('data', d => data += d)
res.on('end', () => resolve(data))
}).end()
})
}
import fetch from 'node-fetch'

test('server running', async() => {
const res = await sendRequest('127.0.0.1', 9876)
const res = await (await fetch('http://localhost:9876')).text()
expect(res).toBe('Hello Vitest\n')
})

test('vite instance running', async() => {
const res = await (await fetch('http://localhost:9988')).text()
expect(res).toContain('<script type="module" src="/@vite/client">')
expect(res).toContain('Hello Vitest\n')
})
1 change: 1 addition & 0 deletions test/global-setup/vitest.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ export default defineConfig({
'./setupFiles/default-export.js',
'./setupFiles/named-exports.js',
'./setupFiles/ts-with-imports.ts',
'./setupFiles/another-vite-instance.ts',
],
},
})