diff --git a/src/node/config.ts b/src/node/config.ts index f29effff47c47c..3ae445ef89cc57 100644 --- a/src/node/config.ts +++ b/src/node/config.ts @@ -23,10 +23,10 @@ import { ServerPlugin } from './server' import { Resolver, supportedExts } from './resolver' import { Transform, CustomBlockTransform } from './transform' import { DepOptimizationOptions } from './optimizer' -import { IKoaProxiesOptions } from 'koa-proxies' import { ServerOptions } from 'https' import { lookupFile } from './utils' import { Options as RollupTerserOptions } from 'rollup-plugin-terser' +import { ProxiesOptions } from './server/serverPluginProxy' export type PreprocessLang = NonNullable< SFCStyleCompileOptions['preprocessLang'] @@ -198,7 +198,7 @@ export interface ServerConfig extends SharedConfig { * } * ``` */ - proxy?: Record + proxy?: Record /** * A plugin function that configures the dev server. Receives a server plugin * context object just like the internal server plguins. Can also be an array diff --git a/src/node/server/serverPluginProxy.ts b/src/node/server/serverPluginProxy.ts index 5c301fd21bccde..9764ccda3d0dd6 100644 --- a/src/node/server/serverPluginProxy.ts +++ b/src/node/server/serverPluginProxy.ts @@ -1,7 +1,10 @@ import { ServerPlugin } from '.' import { URL } from 'url' +import { IKoaProxiesOptions } from 'koa-proxies' -export const proxyPlugin: ServerPlugin = ({ app, config }) => { +export type ProxiesOptions = IKoaProxiesOptions & { ws: boolean } + +export const proxyPlugin: ServerPlugin = ({ app, config, server }) => { if (!config.proxy) { return } @@ -12,8 +15,9 @@ export const proxyPlugin: ServerPlugin = ({ app, config }) => { Object.keys(options).forEach((path) => { let opts = options[path] if (typeof opts === 'string') { - opts = { target: opts } + opts = { target: opts } as ProxiesOptions } + if (opts.ws) return opts.logs = (ctx, target) => { debug( `${ctx.req.method} ${(ctx.req as any).oldPath} proxy to -> ${new URL( @@ -24,4 +28,15 @@ export const proxyPlugin: ServerPlugin = ({ app, config }) => { } app.use(proxy(path, opts)) }) + + server.on('upgrade', (req, socket, head) => { + if (req.headers['sec-websocket-protocol'] !== 'vite-hmr') { + for (const path in options) { + let opts = options[path] + if (typeof opts === 'object' && opts.ws) { + proxy.proxy.ws(req, socket, head, opts) + } + } + } + }) }