Last active
February 7, 2025 22:15
-
-
Save xfournet/068592b3d1ddd488427b874b23f707bf to your computer and use it in GitHub Desktop.
Vite support for HTTP2 and proxy
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import proxy from 'http2-proxy'; | |
import type { Plugin, ProxyOptions } from 'vite'; | |
export const pluginHttp2Proxy = (): Plugin => { | |
let routes: Record<string, string | ProxyOptions>; | |
return { | |
name: 'vite-plugin-http2-proxy', | |
config: (config) => { | |
const { server } = config; | |
routes = server?.proxy ?? {}; | |
if (server) { | |
server.proxy = undefined; | |
} | |
return config; | |
}, | |
configureServer: ({ config: { logger }, middlewares }) => { | |
Object.entries(routes).forEach(([route, target]) => { | |
if (typeof target !== 'string') { | |
throw new Error('ProxyOptions target are not supported yet, only string target are currently supported'); | |
} | |
const { protocol, hostname, port } = new URL(target); | |
const options = { | |
protocol: protocol as 'http' | 'https', | |
hostname, | |
port: Number(port), | |
proxyTimeout: 60000, | |
}; | |
middlewares.use(route, (req, res) => { | |
proxy.web(req, res, { ...options, path: req.originalUrl }, (err) => { | |
if (err) { | |
logger.error(`[http2-proxy] Error when proxying request on '${req.originalUrl}'`, { timestamp: true, error: err }); | |
} | |
}); | |
}); | |
}); | |
}, | |
}; | |
}; |
@A2E9 yes, ProxyOptions are not implemented. Can you share your proxy config ?
here is my proxy config:
'/123': { target: '/456', secure: false, rewrite: (e) => e.replace(/\/123/, '/'), configure: (proxy) => proxy.on('proxyReq', (proxyReq) => { proxyReq.setHeader('Cookie', proxyReq.getHeader('auth') || ''); }), },
Here is my version with rewrite
and configure
support.
Note that you should update your proxy config in configure()
sections
proxy.on('proxyRes', (proxyRes) => {...}
=> proxy.onRes = async (req, res, proxyRes) => {...}
import type { Http2ServerRequest } from 'http2';
import type { Plugin, ProxyOptions } from 'vite';
import http2Proxy, { type http2WebOptions as Http2WebOptions } from 'http2-proxy';
const getOptions = (proxyOptions: string | ProxyOptions) => {
if (typeof proxyOptions !== 'string') {
const { protocol, hostname, port } = new URL(proxyOptions.target);
const { proxyTimeout } = proxyOptions;
return {
protocol: protocol as 'https',
hostname,
port: Number(port),
proxyTimeout,
rejectUnauthorized: false,
};
}
const { protocol, hostname, port } = new URL(proxyOptions);
return {
protocol: protocol as 'https',
hostname,
port: Number(port),
proxyTimeout: 60000,
rejectUnauthorized: false,
};
};
export default (): Plugin => {
let routes: Record<string, string | ProxyOptions>;
return {
name: 'vite-plugin-http2-proxy',
config: (config) => {
const { server } = config;
routes = server?.proxy ?? {};
if (server) {
server.proxy = undefined;
}
return config;
},
configureServer: ({ config: { logger }, middlewares }) => {
Object.entries(routes).forEach(([route, proxyOptions]) => {
const options = getOptions(proxyOptions);
middlewares.use(route, (req, res) => {
const http2Options: Http2WebOptions = { ...options };
if (typeof proxyOptions !== 'string') {
if (proxyOptions.rewrite) {
http2Options.path = proxyOptions.rewrite(req.originalUrl);
} else {
http2Options.path = req.originalUrl;
}
if (proxyOptions.configure) {
proxyOptions.configure(http2Options, proxyOptions);
}
}
http2Proxy.web(req as Http2ServerRequest, res, http2Options, (err) => {
if (err) {
logger.error(`[http2-proxy] Error when proxying request on '${req.originalUrl}'`, {
timestamp: true,
error: err,
});
}
});
});
});
},
};
};
@c1aphas I didn’t quite understand what configure
should look like...
[vite] Internal server error: proxy.on is not a function
configure(proxy) {
// before
// proxy.on('proxyRes', (proxyRes) => {...}
// now
proxy.onRes = async (req, res, proxyRes) => {...}
}
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
@A2E9 yes, ProxyOptions are not implemented. Can you share your proxy config ?