java.net.URI构造器不编码&字符,如何正确传递包含&的查询参数
Java java.net.URI构造包含&的查询参数值的正确方案
问题根因
java.net.URI的多参数构造器URI(String scheme, String userInfo, String host, int port, String path, String query, String fragment)的设计逻辑是:将传入的query参数视为已经完成参数结构拼接的查询串,只会对其中不符合URI规范的非法字符执行编码,不会处理&、=这类查询串的合法结构分隔符。
如果自行提前将参数值内的&编码为%26再传入该构造器,构造器会识别到%为需要编码的非法字符,将其转义为%25,最终得到错误的%2526编码结果。
正确实现方案
使用JDK自带的URLEncoder单独对每个查询参数的键、值做编码,拼接为完整查询串后,通过URI.create()方法创建URI实例即可,该方法不会对已拼接完成的合法URI字符串做二次编码。
示例代码如下:
import java.net.URI; import java.net.URLEncoder; import java.nio.charset.StandardCharsets; // 业务参数定义 String scheme = "https"; String host = "www.anexample.com"; int port = 443; String path = "/hello/v5/letscheck/image/down"; String nameParamValue = "tom&jerry"; String episodeParamValue = "2"; // 单独编码每个参数的键与值 String encodedNameKey = URLEncoder.encode("name", StandardCharsets.UTF_8); String encodedNameVal = URLEncoder.encode(nameParamValue, StandardCharsets.UTF_8); String encodedEpisodeKey = URLEncoder.encode("episode", StandardCharsets.UTF_8); String encodedEpisodeVal = URLEncoder.encode(episodeParamValue, StandardCharsets.UTF_8); // 拼接完整的URL字符串 String queryPart = String.format("%s=%s&%s=%s", encodedNameKey, encodedNameVal, encodedEpisodeKey, encodedEpisodeVal); String fullUrl = String.format("%s://%s:%d%s?%s", scheme, host, port, path, queryPart); // 创建URI实例 URI uri = URI.create(fullUrl);
最终生成的URI查询部分为name=tom%26jerry&episode=2,符合预期,&作为参数值的一部分可以正常传递。
内容的提问来源于stack exchange,提问作者VaV
相关产品推荐
相关产品推荐

