You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用OkHttp库处理ISO-8859-1编码网页的问题求助

解决OkHttp请求ISO-8859-1编码网页的乱码问题

我来帮你搞定这个编码问题,之前处理类似场景时踩过不少坑,下面是针对性的解决方案:

首先得明确问题根源:OkHttp默认会从响应的Content-Type头里提取字符编码来解析响应体,但如果服务器返回的响应头没正确携带charset=ISO-8859-1,或者和页面meta标签的编码不一致,就会导致解析出的文本乱码。咱们可以通过手动指定编码来绕过这个自动检测的问题。

方案一:直接手动指定编码解析

最稳妥的方式是直接获取响应体的原始字节数组,然后用ISO-8859-1编码转换为字符串,完全绕过OkHttp的自动编码判断:

OkHttpClient client = new OkHttpClient();

Request request = new Request.Builder()
        .url(webpage)
        .get()
        .addHeader("upgrade-insecure-requests", "1")
        .addHeader("user-agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36")
        .build();

try (Response response = client.newCall(request).execute()) {
    if (!response.isSuccessful()) throw new IOException("Unexpected code " + response);

    // 获取响应体的原始字节数组
    byte[] rawBytes = response.body().bytes();
    // 用ISO-8859-1编码转换为字符串
    String decodedContent = new String(rawBytes, StandardCharsets.ISO_8859_1);

    // 现在decodedContent就是正确编码的页面内容了
    System.out.println(decodedContent);
} catch (IOException e) {
    e.printStackTrace();
}

方案二:先检测响应头编码,再降级到ISO-8859-1

如果想更严谨,先尝试从响应头提取编码,只有当提取失败或者编码不匹配时,再手动指定ISO-8859-1:

try (Response response = client.newCall(request).execute()) {
    if (!response.isSuccessful()) throw new IOException("Unexpected code " + response);

    ResponseBody body = response.body();
    String targetCharset = StandardCharsets.ISO_8859_1.name();

    // 尝试从Content-Type头获取编码
    MediaType mediaType = body.contentType();
    if (mediaType != null && mediaType.charset() != null) {
        String headerCharset = mediaType.charset().name();
        // 如果响应头编码不是ISO-8859-1,咱们还是强制用页面声明的编码
        if (!headerCharset.equalsIgnoreCase(targetCharset)) {
            targetCharset = StandardCharsets.ISO_8859_1.name();
        }
    }

    String decodedContent = new String(body.bytes(), targetCharset);
    System.out.println(decodedContent);
} catch (IOException e) {
    e.printStackTrace();
}

关键注意事项

  • 绝对不要直接用response.body().string()方法,这个方法会依赖响应头的编码解析,当响应头和页面实际编码不一致时必然乱码。
  • 代码里用了try-with-resources语法,会自动关闭Response和ResponseBody,避免资源泄漏,这个细节一定要注意。

内容的提问来源于stack exchange,提问作者Mr. Kevin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 09:46:09