在Java中编码URL查询参数
如何编码查询参数在Java中的URL? 我知道,这似乎是一个显而易见的问题。
有两个细节我不确定:
- 空格是否应该被编码为“+”或“%20”? 在chrome中,如果我input“http://google.com/foo=?bar me”,chrome会将其更改为使用%20进行编码
- 将冒号“:”编码为%3B是否必要/正确? Chrome没有。
笔记:
-
java.net.URLEncoder.encode
似乎不起作用,它似乎是编码数据被提交表单。 例如,它将空格编码为+
而不是%20
,并对不需要的冒号进行编码。 -
java.net.URI
不编码查询参数
java.net.URLEncoder.encode(String s, String encoding)
也可以帮忙。 它遵循HTML表单编码application/x-www-form-urlencoded
。
URLEncoder.encode(query, "UTF-8");
另一方面, 百分比编码 (也称为URL编码 )使用%20
编码空间。 冒号是一个保留的字符,所以:
编码后仍然是冒号。
编辑: URIUtil
不再在更新的版本中可用,更好的答案在Java – 编码的url或辛迪先生在这个线程。
Apache httpclient的URIUtil
真的很有用,虽然有一些select
URIUtil.encodeQuery(url);
例如,它将空格编码为“+”而不是“%20”
两者在正确的背景下完全有效 。 虽然如果你真的喜欢你可以发出一个stringreplace。
在查询中不需要将冒号编码为%3B,尽pipe这样做不是非法的。
URI = scheme ":" hier-part [ "?" query ] [ "#" fragment ] query = *( pchar / "/" / "?" ) pchar = unreserved / pct-encoded / sub-delims / ":" / "@" unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~" pct-encoded = "%" HEXDIG HEXDIG sub-delims = "!" / "$" / "&" / "'" / "(" / ")" / "*" / "+" / "," / ";" / "="
似乎只有百分比编码的空间是有效的,因为我怀疑空间是ALPHA还是DIGIT
请参阅URI规范了解更多细节。
不幸的是,URLEncoder.encode()不会生成有效的百分比编码(如http://tools.ietf.org/html/rfc3986#section-2.1中所述; )。
URLEncoder.encode()编码的一切都很好, 除了空间编码为“+”。 我所能find的所有Java URI编码器都只公开了对查询,片段,path部分等进行编码的方法 – 但是不要公开“原始”编码。 这是不幸的,因为片段和查询被允许将空间编码为+,所以我们不想使用它们。 path编码正确,但首先是“规范化”,所以我们不能用它来“通用”编码。
我可以想出最好的解决scheme:
return URLEncoder.encode(raw, "UTF-8").replaceAll("\\+", "%20");
如果replaceAll()
对你来说太慢了,我猜是另一种方法是滚动你自己的编码器…
编辑:我有这个代码在这里第一不适当编码“?”,“&”,“=”:
//don't use - doesn't properly encode "?", "&", "=" new URI(null, null, null, raw, null).toString().substring(1);
内置的Java URLEncoder正在做它应该做的,你应该使用它。
“+”或“%20”都是URL中空格字符的有效替代。 任何一个将工作。
一个“:” 应该被编码,因为它是一个分隔符。 即http:// foo或ftp:// bar 。 事实上,一个特定的浏览器可以处理它,当它没有编码并不正确。 你应该编码他们。
作为一个良好的做法,一定要使用带有字符编码参数的方法。 UTF-8通常在那里使用,但你应该明确地提供它。
URLEncoder.encode(yourUrl, "UTF-8");