Dart编写的代理服务器返回HTML而非网页问题求助
问题解决:Dart代理服务器转发HTML后浏览器显示源码
你的问题核心是没有转发目标服务器返回的响应头,浏览器因为缺少Content-Type这类关键头信息,不知道收到的内容是HTML,所以直接显示源码了。下面是具体的修复方案:
关键修复点
- 转发目标响应的状态码
- 完整转发所有响应头(尤其是
Content-Type) - 用字节流写入响应内容,避免编码或二进制内容(如图片)出错
修复后的代码
import 'package:http/http.dart' as http; import 'dart:io'; void launchProxy() async { var server = await HttpServer.bind('localhost', 8080); await server.forEach((HttpRequest request) async { // 处理请求头:用逗号拼接多值header,比替换[]更规范 final headers = <String, String>{}; request.headers.forEach((name, values) { headers.putIfAbsent(name, () => values.join(',')); }); if (request.method == 'GET') { final response = await http.get(request.uri, headers: headers); // 1. 转发状态码 request.response.statusCode = response.statusCode; // 2. 转发所有响应头 response.headers.forEach((name, values) { request.response.headers.set(name, values.join(',')); }); // 3. 用字节流写入内容,兼容文本和二进制资源 request.response.add(response.bodyBytes); await request.response.close(); } else if (request.method == 'POST') { final bodyBytes = await request.first; final response = await http.post(request.uri, headers: headers, body: bodyBytes); // 同样的转发逻辑 request.response.statusCode = response.statusCode; response.headers.forEach((name, values) { request.response.headers.set(name, values.join(',')); }); request.response.add(response.bodyBytes); await request.response.close(); } // 其他方法可参照上述逻辑添加 }); }
修复说明
- 响应头转发:目标服务器返回的
Content-Type: text/html; charset=utf-8会告诉浏览器“这是HTML内容,要渲染”,之前的代码没传这个头,浏览器只能把内容当纯文本显示。 - 状态码转发:比如404、500这类状态码也需要正确传递,保证浏览器能识别错误状态。
- 字节流写入:
response.body会把内容转成字符串,对于图片、视频这类二进制资源会出错,用bodyBytes直接传递原始字节更可靠。
内容的提问来源于stack exchange,提问作者user3554868
相关产品推荐
相关产品推荐

