【问题标题】:When asked to send in UTF-8, Mozilla Firefox sends me UTF-16 data (breaking my servlet)当被要求以 UTF-8 发送时,Mozilla Firefox 向我发送 UTF-16 数据(破坏了我的 servlet)
【发布时间】:2014-01-03 22:17:17
【问题描述】:

我的 Web 服务器出现来自 Mozilla Firefox 浏览器的内容的问题。我试图弄清楚我必须对网页配置做些什么才能使其行为与 Chrome 或 MSIE11 浏览器相同。 我有一个正确设置其标题的网页:

<html>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

在文本字段中,我可以粘贴“高位”文本。我选择的测试字符串是

 ƉǮ…Ł    

这是(带有斜线的大写-D)、(带有标记的三类字符)、省略号和(带有斜线的大写-L)。它是 UTF-16 格式。

然后我将其提交给服务器。这是 Mozilla 请求标头:

POST /portal/SalesOrderServlet HTTP/1.1
Host: localhost:8080
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:26.0) Gecko/20100101 Firefox/26.0
Accept: application/json, text/javascript, */*; q=0.01
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
X-Requested-With: XMLHttpRequest
Referer: http://localhost:8080/portal/salesOrderEdit.jsp?sequence=1508667&req=r88a_3414
Content-Length: 21321
Cookie: JSESSIONID=8283746DD2158665EADD586BFC9B6250
Connection: keep-alive
Pragma: no-cache
Cache-Control: no-cache

这是 Chrome 请求标头:

POST /portal/SalesOrderServlet HTTP/1.1
Host: localhost:8080
Connection: keep-alive
Content-Length: 21320
Accept: application/json, text/javascript, */*; q=0.01
Origin: http://localhost:8080
X-Requested-With: XMLHttpRequest
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/31.0.1650.63 Safari/537.36
Content-Type: application/x-www-form-urlencoded
Referer: http://localhost:8080/portal/salesOrderEdit.jsp?sequence=1508667&req=r88a_3414
Accept-Encoding: gzip,deflate,sdch
Accept-Language: en-US,en;q=0.8
Cookie: JSESSIONID=BECCA9297706D45011D67DF82498FD66

数据通过 AJAX 调用以 JSON 格式发送到服务器。认真编辑,Firefox 和 Chrome 看起来都是这样的:

jsonContent:[{"name":"formData","value":"{\"hold_ae_question\":false, [snip] \"op_notes\":\"Ð?…L\", [snip] }"}]

在服务器(Tomcat,使用 Java 5 版本)上,我从请求中提取数据:

HaloJsonObject ajaxCall = JSONUtilities.jsonify(request);

String strContent = ajaxCall.getString("jsonContent");

HaloJsonObject jsonContent = JSONUtilities.createHaloJsonObjectFromString(strContent);

“HaloJsonObject”是 JSONObject 的薄包装。此处包含支持功能,因为无论如何我都会被问到它们:

public static HaloJsonObject jsonify(HttpServletRequest request) {
    Enumeration<String> enums = request.getParameterNames();
    JSONObject json = new JSONObject();

    while(enums.hasMoreElements()) {
        String paramName = enums.nextElement();
        String paramValue = request.getParameter(paramName);

        try {
            json.put(paramName, paramValue);
        } catch (JSONException e) {
            // log stuff
        }
    }

    return new HaloJsonObject(json, JSONObject.getNames(json));
}

public static HaloJsonObject createHaloJsonObjectFromString(String source) {
    return convertFormArrayToObject(HaloJsonArray.createJsonArrayFromString(source));
}

public static HaloJsonObject convertFormArrayToObject(JSONArray formDataArray) {
    HaloJsonObject json = new HaloJsonObject();

    for(int i = 0; i < formDataArray.length(); i++) {
        JSONObject jo = new JSONObject();            

        try {
             jo = formDataArray.getJSONObject(i);
             json.put(jo.getString("name"), jo.getString("value"));
        } catch (JSONException e) {
            // log stuff
        }
    }

    return json;
}

public static JSONArray createJsonArrayFromString(String array) {
    JSONArray json = null;

    try {
        json = new JSONArray(array);
    } catch (JSONException e) {
        json = new JSONArray();
    }

    return json;
}

一旦数据被解析为“jsonContent”,Eclipse 调试器就会以这种方式显示它:

当来自 Firefox 时,它看起来像:

Ð?…L

当来自 Chrome 时,它​​看起来像:

Æ\u0089Ç®â\u0080¦Å\u0081    

Æ?Ç®â?¦Å

取决于您在哪里使用该值以及 toString() 如何处理它。任何一种表示都是字符串的 UTF-8 值。

这对我来说是一场灾难,因为我的 JDBC 连接器讨厌 UTF-16 格式。

为什么看似相同的调用(一个来自 Chrome,另一个来自 Firefox)会产生不同的结果?

谢谢, 杰罗姆。

【问题讨论】:

    标签: json google-chrome firefox utf-8 utf-16


    【解决方案1】:

    在我看来是个误会。我没有明确调用 jQuery 的 $.ajaxSetup(),并且 jQuery 文档说 $.ajax() 的 contentType 的默认值是“application/x-www-form-urlencoded; charset=UTF-8”。但是,如果没有显式设置,Firefox 浏览器有 UTF-8 子句,而 Chrome 浏览器没有。

    当我在 $.ajax() 调用中使用 UTF-8 明确设置 contentType 时,我看到两个浏览器的行为相同,即之前的 Firefox 行为。顺便说一句,虽然数据传输是通过 UTF-8 进行的,但在服务器中,数据字段是用 UTF-16 值填充的。从那里我必须安排将数据保存到数据库中,可能通过将它们转换为 UTF-8。

    感谢您的关注。 杰罗姆。

    【讨论】:

      猜你喜欢
      • 2021-03-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-06-30
      • 2016-06-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多