【问题标题】:Error parsing application/x-www-form-urlencoded with Unicode post data使用 Unicode 发布数据解析 application/x-www-form-urlencoded 时出错
【发布时间】:2025-12-26 18:25:07
【问题描述】:

当数据是 unicode 并且我得到时,Play 拒绝接受 POST 请求:

解析应用程序/x-www-form-urlencoded 时出错

我的印象是一切都很好,直到我尝试使用希伯来语而不是英语的文本请求,所以使用

的请求
value=hey

工作正常,但有

的请求
value=%u05D4%u05D9%u05D9

失败。

我找到了something about it,但他说他通过更改 play/api/mvc/ContentType.scala 使其工作,这是我想避免的。

有什么想法吗?
谢谢!


编辑

我知道编码不符合 application/x-www-form-urlencoded 的标准,但这是我需要处理的情况,目前无法更改客户端,它使用 javascript escape 方法。

我正在寻找后端方面的解决方案,即 Play 解决方案。
找到一个可以在 java 中实现的解决方案会很好,但现在看起来解决方案是编写我自己的 BodyParser(在 scala 中)。

【问题讨论】:

  • 我从未见过那种特殊的编码方式——你有参考建议它应该可以工作吗?
  • 我们正在使用我们拥有的旧系统,当 Play 代理它时会发生此特定错误。它使用 Flask 并且在这方面没有问题,flask 接受这种编码。我在转义后写的是希伯来语中的“嘿”:escape("היי")
  • 这并不能真正回答我的问题。支持它的一件事并不意味着它是一种标准的做事方式......
  • 嗯,在将字符串发送到服务器之前转义字符串是一种常见做法,因为除此之外没有其他文本操作,我认为它符合标准,不是吗?
  • 是的,转义是常见的做法——但我之前没有见过%u 表单或 URL 编码。这就是为什么我要求参考它。 Wikipedia 建议使用 UTF-8 八位字节序列的普通 %xx 编码通常会更好。

标签: java post playframework playframework-2.0


【解决方案1】:

根据我的研究,在application/x-www-form-urlencoded 正文中处理 Unicode 的正确方法是将 Unicode 转换为文档默认字符集中的字节(即 UTF-8),然后对字节进行 URL 编码(即 %-encode )。

当然,就规范而言,您当前正在执行的操作(使用 '%uxxxx' 序列)不是有效的编码。 (你不能像那样把东西从空中拉出来......并期望它起作用。)

参考资料:


我注意到您通过浏览器的控制台发现了这种转义语法。以下是 MSDN 关于 Javascript escape() 方法的说明:

“escape 和 unescape 函数不适用于非 ASCII 字符,已被弃用。在 JavaScript 1.5 及更高版本中,使用 encodeURI、decodeURI、encodeURIComponent 和 decodeURIComponent。”

我认为“不能正常工作”意味着他们使用了浏览器无法识别的非标准转义语法。教训:阅读规范而不是依赖实验。

【讨论】:

  • 是的,虽然 escape 已弃用且不应使用,但我目前无法更改它,因为它来自客户端,我无法更改它。由于我们在播放之前使用了不同的后端(烧瓶),并且它起作用了,切换到播放有点破坏了服务。我正在寻找的是如何在播放方面处理它,并且看起来就像我必须实现自己的 BodyParser
  • @NitzanTomer - 如果你必须生活在这些限制中,你可能是对的。但是,它以前有效的事实并不意味着它以前是正确的。发送标准无法识别的转义序列可以说是一种破坏行为,即使它“有效”。标准的重点是每个人/一切都应该遵循它们。
  • 我完全同意,只是客户端目前不在我们手中.. 将来可能会改变,但现在它是软件的第三方和平,他们正在使用@987654326 @.. 所以基本上我正在寻找一个可以让我处理愚蠢的解决方案。
  • 更好的是,我们将停止使用它们:)