使用 Bun.serve 实现反向代理
一般情况下, 前端项目中会使用vite等工具作为开发服务器, 这些一般都直接支持 proxy 配置.
Bun 没有内置 proxy 相关的配置, 但可以直接使用 Bun.serve 来实现同样的效果.
主要思路
通过在 fetch 中识别到需要代理的请求, 带着原始的请求信息, 直接发起新的请求到目标服务器, 然后将响应返回给浏览器.
实例代码
此处展示的实例代码没有处理 hop-by-hop 相关的请求头, 以及一些边界情况, 但已经足够展示主要思路了.
import { fetch, serve } from "bun";
import index from "./index.html";
const server = serve({
port: 3000,
routes: {
// Serve index.html for all unmatched routes.
"/": index,
},
async fetch(req: Request) {
const url = new URL(req.url);
const targetUrl = new URL(url.pathname + url.search, "http://localhost:3001");
try {
const response = await fetch(targetUrl, {
method: req.method,
headers: req.headers,
body: req.body,
});
// Since the response is decoded,
// we need to delete encode-related fields in response header
response.headers.delete("content-encoding");
// and let browser re-calculate the length of content (since it's decoded)
response.headers.delete("content-length");
// Then return the response
return response;
} catch (err) {
console.log(err);
return new Response("Proxy target unavailable", { status: 502 });
}
},
development: process.env.NODE_ENV !== "production" && {
// Enable browser hot reloading in development
hmr: true,
// Echo console logs from the browser to the server
console: true,
},
});
console.log(`🚀 Server running at ${ server.url }`);