java 如何解码 获取 url 参数 接收到 throw BeanParam编码的浏览器视角编码的服务器透视图坚果壳

2022-09-04 23:02:09

我收到对此 Web 服务的 GET 响应

@GET
@Path("/nnnnnn")
public Response pfpfpfpf(@BeanParam NNNNNN n)

该类具有:NNNNN

@QueryParam("parameter")
private String parameter;

为此,有一个get和set。parameter

我发送了一个带有查询参数的get请求,它正在自动绑定到我的选项NNNNN,一切都很棒。

但是,现在我在查询网址中发送日语字符串。在发送之前,我用UTF-8对参数进行编码,并且我必须使用UTF-8对它们进行解码。

但我的问题是我应该在哪里调用URLDecoder?我试图在该参数的获取器中调用它,但它不起作用,我一直有类似的东西而不是日语字符C3%98%C2%B4%C3%98%C2


答案 1

对我有用的解决方案是:

在 servlet 上,我应该这样做:

request.setCharacterEncoding("UTF-8");

然后在html页面上,我不得不添加这个:

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

答案 2

这是一个好问题,对于系统之间如何处理(编码和解码)信息存在许多潜在的疑问。

在我继续之前,我必须说对字符集,编码等有一个公平的理解。您可能想阅读此答案以快速抬头。

这必须从2个角度来看 - 浏览器和服务器。

编码的浏览器视角

每个浏览器都会呈现信息/文本,现在要呈现信息/文本,它必须知道如何解释这些位/字节,以便它可以正确呈现(阅读我的答案的第3个项目符号,即相同的位如何表示不同编码方案中的不同字符)。

浏览器页面编码

  • 每个浏览器都有一个与之关联的默认编码。检查如何查看浏览器的默认编码
  • 如果未在 HTML 页面上指定任何编码,则浏览器的默认编码将生效,并将按照这些编码规则呈现页面。因此,如果默认编码是ASCII,并且您使用的是日语或中文或Unicode补充平面中的字符,那么您将看到垃圾值。
  • 您可以告诉浏览器不使用您的默认编码方案,而是使用这个编码方案按网站呈现,使用.<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
    • 这正是你所做的/发现的,你很好,因为这个标签基本上覆盖了浏览器的默认编码。
    • 达到相同效果的另一种方法是不要使用此元标记,而只需更改浏览器的默认编码,您仍然会没事的。但不建议这样做,建议在 JSP 中使用元标记。Content-Type

尝试使用浏览器默认编码,并使用下面的简单HTML进行标记。meta

<!DOCTYPE html>
<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
    </head>
    <body>
        の, は, でした <br></br>
        昨夜, 最高
    </body>        
</html>

编码的服务器透视图

服务器还应该知道如何解释传入的数据流,这基本上意味着要使用哪种编码方案(服务器部分很棘手,因为有几种可能性)。从这里阅读以下内容

提交已输入到 HTML 表单中的数据时,将使用方法 GET 或 POST 或过去通过电子邮件对表单字段名称和值进行编码,并在 HTTP 请求消息中发送到服务器。默认情况下使用的编码基于通用 URI 百分比编码规则的非常早期版本,并进行了许多修改,例如换行符规范化以及将空格替换为“+”而不是“%20”。以这种方式编码的MIME类型的数据是appplication/x-www-form-urlencoded的,它目前在HTML和XForms规范中被定义(仍然以非常过时的方式)。此外,CGI 规范还包含有关 Web 服务器如何解码此类型数据并使其可供应用程序使用的规则。

这同样有2个部分,即服务器应如何解码传入的请求流以及应如何对传出响应流进行编码。

根据用例,有几种方法可以做到这一点,例如:

  • HTTP 请求和响应对象中有 一些方法,如 ,可用于设置编码。setCharacterEncodingsetContentType
    • 这正是您在案例中所做的,您已经告诉服务器使用UTF-8编码方案来解码请求数据,因为我期望高级Unicode补充平面字符。但这还不是全部,请在下面阅读更多内容。
  • 使用 JVM 属性(如 )在服务器或 JVM 级别设置编码。阅读本文,了解如何设置服务器编码。-Dfile.encoding=utf8

在你的情况下,你从URL的查询字符串中提取日语字符,查询字符串是HTTP请求对象的一部分,所以使用你能够得到所需的编码结果。request.setCharacterEncoding("UTF-8");

但同样不适用于URL编码,这与请求编码(您的情况)不同。考虑以下示例,在两者中,即使在使用后,您也无法看到所需的编码效果,因为在这里您想要URL编码,因为URL将类似于并且在此URL中没有查询字符串。sysoutrequest.setCharacterEncoding("UTF-8");http://localhost:7001/springapp/forms/executorTest/encodingTest/hellothere 昨夜, 最高

@RequestMapping(value="/encodingTest/{quertStringValue}", method=RequestMethod.GET)
    public ModelAndView encodingTest(@PathVariable("quertStringValue") String quertStringValue, ModelMap model, HttpServletRequest request) throws UnsupportedEncodingException {
        System.out.println("############### quertStringValue " + quertStringValue);
        request.setCharacterEncoding("UTF-8");
        System.out.println("############### quertStringValue " + quertStringValue);
        return new ModelAndView("ThreadInfo", "ThreadInfo", "@@@@@@@ This is my encoded output " + quertStringValue);
    }

根据您使用的框架,您可能需要其他配置来为请求或 URL 指定字符编码,以便在请求尚未指定编码时可以应用自己的编码,或者在任何情况下强制实施编码。这很有用,因为当前的浏览器通常不设置字符编码,即使在 HTML 页面或表单中指定也是如此。

在春季,有用于配置请求编码的功能。阅读这个基于这一事实的类似有趣的问题org.springframework.web.filter.CharacterEncodingFilter

坚果壳

每个计算机程序无论是应用程序服务器,Web服务器,浏览器,IDE等都只理解位,因此它需要知道如何解释位以使其具有预期的意义,因为根据所使用的编码,相同的位可以表示不同的字符。这就是“编码”通过提供唯一标识符来表示字符来发挥作用的地方,以便所有计算机程序,各种操作系统等都知道确切的正确方法来解释它。


推荐