java encode 空格_URL中存在空格encode编码问题

本文探讨了URL编码时空格被编码为`%20`和`+`的现象,解释了其原因在于不同规范的冲突。W3C标准规定查询字符串中的空格应编码为`+`,而RFC 2396建议编码为`%20`。Java的`URLEncoder.encode`方法可能导致混淆,建议在编码后替换所有`+`为`%20`以确保兼容性。提供了一个示例方法`urlEncodeURL`用于正确处理URL编码。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Loading...

## 问题

在对URL进行encode编码的时候,URL中的空格有时候被编码成`%20`,有时候被编码成加号`+`。大多数情况下,这两种编码都可以工作,但个别情况下,编码为`+`的URL存在问题,并不能正常访问。

## 原因

一个URL的基本组成部分包括协议(scheme),域名,端口号,路径和查询字符串(路径参数和锚点标记就暂不考虑了)。路径和查询字符串之间用问号?分离。

例如`http://www.example.com/index?param=1`,路径为`index`,查询字符串(Query String)为`param=1`。

以上例子中URL中关于空格的编码正是与空格所在位置相关:空格被编码成加号+的情况只会在查询字符串部分出现,而被编码成%20则可以出现在路径和查询字符串中。

造成这种混乱局面的原因在于:[W3C标准规定](http://www.w3.org/TR/html4/interact/forms.html#h-17.13.4.1),当`Content-Type`为`application/x-www-form-urlencoded`时,URL中查询参数名和参数值中空格要用加号+替代,所以几乎所有使用该规范的浏览器在表单提交后,URL查询参数中空格都会被编成加号`+`。

而在另一份规范([RFC 2396](http://www.ietf.org/rfc/rfc2396.txt),定义URI)里, URI里的保留字符都需转义成`%HH`格式(Section 3.4 Query Component),因此空格会被编码成`%20`,加号`+`本身也作为保留字而被编成`%2B`,对于某些遵循`RFC 2396`标准的应用来说,它可能不接受查询字符串中出现加号`+`,认为它是非法字符。所以一个安全的举措是URL中统一使用`%20`来编码空格字符。

## 解决方法(java)

Java中的URLEncoder本意是用来把字符串编码成`application/x-www-form-urlencoded MIME`格式字符串,也就是说仅仅适用于URL中的查询字符串部分,但是`URLEncoder`经常被用来对URL的其他部分编码,它的`encode`方法会把空格编成加号`+`,与之对应的是,`URLDecoder`的`decode`方法会把加号`+`和`%20`都解码为空格,这种做法造成了URL编码问题的混乱。

比较可靠的做法是,在调用`URLEncoder.encode`对URL进行编码后(所有加号`+`已被编码成`%2B`),再调用`replaceAll(“\\+”, “%20″)`,将所有加号`+`替换为`%20`。例子如下:

```java

public static String urlEncodeURL(String url) {

try {

String result = URLEncoder.encode(url, "UTF-8");

result = result.replaceAll("%3A", ":").replaceAll("%2F", "/").replaceAll("\\+", "%20");//+实际上是 空格 url encode而来

return result;

} catch (UnsupportedEncodingException e) {

e.printStackTrace();

}

return null;

}

```

最后修改:2020 年 04 月 02 日 10 : 58 AM

© 允许规范转载

赞赏

如果觉得我的文章对你有用,请随意赞赏

×Close

赞赏作者

扫一扫支付

png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAABS2lUWHRYTUw6Y29tLmFkb2JlLnhtcAAAAAAAPD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz4KPHg6eG1wbWV0YSB4bWxuczp4PSJhZG9iZTpuczptZXRhLyIgeDp4bXB0az0iQWRvYmUgWE1QIENvcmUgNS42LWMxMzggNzkuMTU5ODI0LCAyMDE2LzA5LzE0LTAxOjA5OjAxICAgICAgICAiPgogPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4KICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+CiA8L3JkZjpSREY+CjwveDp4bXBtZXRhPgo8P3hwYWNrZXQgZW5kPSJyIj8+IEmuOgAAAA1JREFUCJljePfx038ACXMD0ZVlJAYAAAAASUVORK5CYII=

png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAABS2lUWHRYTUw6Y29tLmFkb2JlLnhtcAAAAAAAPD94cGFja2V0IGJlZ2luPSLvu78iIGlkPSJXNU0wTXBDZWhpSHpyZVN6TlRjemtjOWQiPz4KPHg6eG1wbWV0YSB4bWxuczp4PSJhZG9iZTpuczptZXRhLyIgeDp4bXB0az0iQWRvYmUgWE1QIENvcmUgNS42LWMxMzggNzkuMTU5ODI0LCAyMDE2LzA5LzE0LTAxOjA5OjAxICAgICAgICAiPgogPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4KICA8cmRmOkRlc2NyaXB0aW9uIHJkZjphYm91dD0iIi8+CiA8L3JkZjpSREY+CjwveDp4bXBtZXRhPgo8P3hwYWNrZXQgZW5kPSJyIj8+IEmuOgAAAA1JREFUCJljePfx038ACXMD0ZVlJAYAAAAASUVORK5CYII=

支付宝支付

微信支付

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值