【问题标题】:Passing request parameters as UTF-8 encoded strings [duplicate]将请求参数作为 UTF-8 编码字符串传递 [重复]
【发布时间】:2012-06-15 16:47:06
【问题描述】:

我正在创建一个简单的登录页面,我想将登录名和密码参数作为 UTF-8 编码字符串传递。正如您在下面的代码中看到的,第一行是我将编码设置为 UTF-8 的地方,但这似乎没有意义,因为它不起作用。当我使用带有重音符号的登录名和密码参数时,结果页面会收到奇怪的字符。

如何以适用于所有浏览器的方式正确设置字符编码?

<%@page contentType="text/html" pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
        <title>My Page</title>
    </head>

    <body>
        <h1>Welcome to My Page</h1>

        <form name="login" action="login.jsp" method="POST">
            Login:<br/>
            <input type="text" name="login" value="" /><br/>
            Password:<br/>
            <input type="password" name="password" value="" /><br/>
            <br/>
            <input type="submit" value="Login" /><br/>
        </form>

    </body>
</html>

【问题讨论】:

  • 你的请求字符编码好像不是UTF-8,

标签: jsp servlets utf-8 character-encoding


【解决方案1】:

pageEncoding 仅设置响应字符编码和 HTTP Content-Type 标头的 charset 属性。基本上,它告诉服务器在将 JSP 生成的字符发送到客户端之前将其解码为 UTF-8,并且标头告诉客户端使用 UTF-8 对它们进行编码,并且在同一页面中的任何表单时也使用它提交回服务器。 contentType 已经默认为 text/html,所以下面就足够了:

<%@page pageEncoding="UTF-8"%>

当通过 HTTP 提供页面时,将忽略 HTML 元标记。它仅在页面被客户端保存为本地磁盘系统上的 HTML 文件并然后在浏览器中由file:// URI 打开时使用。

在您的特定情况下,HTTP 请求正文编码显然未设置为 UTF-8。请求正文编码需要由 servlet 中的 ServletRequest#setCharacterEncoding() 或过滤器设置第一次调用 request.getXxx() 之前,在请求中涉及的任何 servlet 或过滤器中进行。

request.setCharacterEncoding("UTF-8");
String login = request.getParameter("login");
String password = request.getParameter("password");
// ...

另见:

【讨论】:

  • 越南语怎么样?也使用UTF-8 ?
  • 我认为你应该在jsp页面中设置编码也喜欢: ......因为我尝试仅在请求中设置它但不起作用,但在两者中都设置时效果很好。
  • @Ahmed: &lt;%@page pageEncoding="UTF-8"%&gt; 足以设置响应编码。
【解决方案2】:

示例字符编码:

<%@ page language="java" pageEncoding="utf8" contentType="text/html;charset=UTF-8" %>

【讨论】:

  • 这并不比 OP 已经拥有的更好,这根本无法解决具体问题。 language 已经默认为 Java,pageEncoding 将在 Content-Type 标头中隐式设置 charset 属性。基本上,整个contentType 也是多余的,因为它已经默认为text/html。单独&lt;%@page pageEncoding="UTF-8"%&gt; 绰绰有余。
【解决方案3】:

在某些情况下调用 ServletRequest#setCharacterEncoding() 仍然会失败。

如果您的容器仔细遵循 servlet 规范(与 tomcat 一样),它将默认将 post 参数解释为 ISO-8859-1。这可能会在 UTF-8 字符(例如我最近处理的案例中的日语)到达您的代码之前出现乱码,尤其是如果您有一个使用 getParameter()getParameters() 检查请求参数的 servlet 过滤器。这两种方法强制对参数进行解码,并且解码只进行一次。

如果您有查看请求参数的过滤器,这里是如何在 Tomcat 中解决此问题的链接。人们会希望查看文档以了解他们的特定容器。

http://wiki.apache.org/tomcat/FAQ/CharacterEncoding#Q1

其中的关键是:

添加

useBodyEncodingForURI="true" URIEncoding="UTF-8"

到 Tomcat 的 server.xml 中的 Context 元素并添加

  <filter>
    <filter-name>Character Encoding Filter</filter-name>
    <filter-class>org.apache.catalina.filters.SetCharacterEncodingFilter</filter-class>
    <init-param>
      <param-name>encoding</param-name>
      <param-value>UTF-8</param-value>
    </init-param>
  </filter>
  <filter-mapping>
    <filter-name>Character Encoding Filter</filter-name>
    <url-pattern>/*</url-pattern>
  </filter-mapping>

与在 web.xml 中调用 getParameter() 或 getParameters() 的任何过滤器一样。我发现虽然上面的链接使上下文元素的两个属性看起来像是替代品,但 useBodyEncodingForURI 一个是绝对必要的,否则tomcat不会为查询字符串设置编码。来自 tomcat 7.0.42 中的 Request.java:

boolean useBodyEncodingForURI = connector.getUseBodyEncodingForURI();
if (enc != null) {
    parameters.setEncoding(enc);
    if (useBodyEncodingForURI) {
        parameters.setQueryStringEncoding(enc);
    }
} else {
    parameters.setEncoding
        (org.apache.coyote.Constants.DEFAULT_CHARACTER_ENCODING);
    if (useBodyEncodingForURI) {
        parameters.setQueryStringEncoding
            (org.apache.coyote.Constants.DEFAULT_CHARACTER_ENCODING);
    }
}

【讨论】:

  • 查询字符串是URI的一部分,因此设置&lt;Connector&gt;元素URIEncoding属性也意味着查询字符串的using the same encoding。所以它们确实是替代品。
【解决方案4】:

问题取决于使用哪个应用程序服务器。甚至页面都是正确设置的,例如对于 UTF8,尝试以正确的形式(根据预期的语言)获取参数不会产生良好的结果,即 request.getParameter(...) 返回非预期字符,因为参数的默认代码页大多是 8859-1。这意味着,参数的代码页独立于 JSP 页面的代码页,参数的默认代码页会影响结果。我发现的最好的描述在这里: [1]: http://docs.cksource.com/CKFinder_2.x/Developers_Guide/Java/Configuration/URI_Encoding。 在某些应用程序服务器中,“request.setCharacterEncoding(...)”无效。您必须在描述符中设置参数编码。最复杂的是JBoss,Apache Tomcat,中间是Glassfish。更好的是 WebLogic,最好的是 Jetty(UTF-8 是默认设置)。在我的情况下,我必须创建 glassfish-web.xml 描述符并将参数编码标签放在那里。就我而言(GlassFish):

<glassfish-web-app error-url="">
  <!-- request.setCharacterEncoding("UTF-8") not functioning -->
  <parameter-encoding default-charset="UTF-8" />
</glassfish-web-app>

【讨论】:

    【解决方案5】:

    我最近遇到了这个问题,在这里找不到答案。我正在使用 Weblogic,大多数解决方案都是针对 Tomcat 的。

    要使编码与 Weblogic 一起使用,您必须将其放入您的 weblogic.xml

    <charset-params> 
        <input-charset> 
            <resource-path>/*</resource-path> 
            <java-charset-name>UTF-8</java-charset-name> 
        </input-charset> 
    </charset-params>
    

    来源:weblogic.xml docs

    注意:我的 _JAVA_OPTIONS 中也有这些选项,但不知道它们是否必要。

    -Dweblogic.webservice.i18n.charset=utf-8 
    -Dfile.encoding=UTF-8
    

    【讨论】:

      猜你喜欢
      • 2012-09-11
      • 2011-08-09
      • 2014-01-18
      • 2011-08-27
      • 2012-06-10
      • 1970-01-01
      • 1970-01-01
      • 2016-11-01
      相关资源
      最近更新 更多