事故现场:网络请求采用Rxjava + Retrofit,添加了日志拦截器HttpLoggingInterceptor
后台返回的数据包含字符%,直接报错
{
"server_no": 1,
"message": "查询成功!",
"result_data": {
"address": "阿克苏大家好%拉开距离看沙%敦府个"
}
}
期初认为是gson解析的问题就会奔溃,后来断定不是。看到报错
java.lang.IllegalArgumentException: URLDecoder: Illegal hex characters in escape (%) pattern : %\u
才明白是因为URLDecoder的时候:URL规范有自己的规定,%25会被转义成%! 而只有%一个字符的时候,则被URL认为是转义的标记,需要和后面两个字符一起转为一个16进制数(URL只能使用英文字母、阿拉伯数字和某些标点符号,不能使用其他文字和符号), 而现在的%后面不是URL认识的,所以就给你报错了!
解决办法:使用%25替换字符串中的%号
发现在日志拦截器HttpLoggingInterceptor中采用了URLDecoder,所以在解码之前添加下面的代码url =url.replaceAll("%(?![0-9a-fA-F]{2})", "%25");
String urlStr = URLDecoder.decode(url,"UTF-8");
这里使用了一个特殊正则表达式:零宽负向先行断言(zero-width negative lookahead assertion),模式为(?!pattern),代表字符串中的一个位置,紧接该位置之后的字符序列不能匹配pattern。%(?![0-9a-fA-F]{2})意思是'%'开始,但是后面两个字符不是数字,也不是字母。
当然你也可以去掉日志拦截器来解决这个问题,不过日志拦截器对开发者是相当重要的,呵呵。