okhttp、okio添加参数(addParams)出现的java.lang.IllegalArgumentException:Unexpected code point
来源:互联网 发布:玩dnf网络不稳定 编辑:程序博客网 时间:2024/06/08 01:48
这是我们项目,收集到的,用户出现过不少次的一个问题。根据堆栈发现是出现在用户修改自己的个人资料时出现的。
项目的网络框架用的是okhttp,在bugly上的样子如下图
查看堆栈信息,找到抛出这个异常的地方,在okhttp的okio这个jar包的Buffer类中,的writeUtf8CodePoint()这个方法中
Buffer类的源码如下
@Override public Buffer writeUtf8CodePoint(int codePoint) { if (codePoint < 0x80) { // Emit a 7-bit code point with 1 byte. writeByte(codePoint); } else if (codePoint < 0x800) { // Emit a 11-bit code point with 2 bytes. writeByte(codePoint >> 6 | 0xc0); // 110xxxxx writeByte(codePoint & 0x3f | 0x80); // 10xxxxxx } else if (codePoint < 0x10000) { if (codePoint >= 0xd800 && codePoint <= 0xdfff) { throw new IllegalArgumentException( "Unexpected code point: " + Integer.toHexString(codePoint));//可能抛出异常的地方 A } // Emit a 16-bit code point with 3 bytes. writeByte(codePoint >> 12 | 0xe0); // 1110xxxx writeByte(codePoint >> 6 & 0x3f | 0x80); // 10xxxxxx writeByte(codePoint & 0x3f | 0x80); // 10xxxxxx } else if (codePoint <= 0x10ffff) { // Emit a 21-bit code point with 4 bytes. writeByte(codePoint >> 18 | 0xf0); // 11110xxx writeByte(codePoint >> 12 & 0x3f | 0x80); // 10xxxxxx writeByte(codePoint >> 6 & 0x3f | 0x80); // 10xxxxxx writeByte(codePoint & 0x3f | 0x80); // 10xxxxxx } else { throw new IllegalArgumentException( "Unexpected code point: " + Integer.toHexString(codePoint));//可能抛出异常的地方 B } return this; }从源码,可以看到,有两个地方可能出现这种情况,而这个方法的代码,是进行Utf-8编码时,根据规则
大于0xd800 并且小于0xdfff的范围,是做其他用的(详情可参看Unicode编码以及Utf-8等相关知识),而大于0x10ffff是超出了Unicode的编码范围的。
现在我们需要知道这个方法在哪里被调用的,以及codePoint是什么东西,怎么来的?
最终我们找到了okhttp3这个jar包中的HttpUrl这个类中的canonicalize这个方法中,该方法源码如下
static void canonicalize(Buffer out, String input, int pos, int limit, String encodeSet, boolean alreadyEncoded, boolean strict, boolean plusIsSpace, boolean asciiOnly) { Buffer utf8Buffer = null; // Lazily allocated. int codePoint; for (int i = pos; i < limit; i += Character.charCount(codePoint)) { codePoint = input.codePointAt(i); if (alreadyEncoded && (codePoint == '\t' || codePoint == '\n' || codePoint == '\f' || codePoint == '\r')) { // Skip this character. } else if (codePoint == '+' && plusIsSpace) { // Encode '+' as '%2B' since we permit ' ' to be encoded as either '+' or '%20'. out.writeUtf8(alreadyEncoded ? "+" : "%2B"); } else if (codePoint < 0x20 || codePoint == 0x7f || codePoint >= 0x80 && asciiOnly || encodeSet.indexOf(codePoint) != -1 || codePoint == '%' && (!alreadyEncoded || strict && !percentEncoded(input, i, limit))) { // Percent encode this character. if (utf8Buffer == null) { utf8Buffer = new Buffer(); } utf8Buffer.writeUtf8CodePoint(codePoint); while (!utf8Buffer.exhausted()) { int b = utf8Buffer.readByte() & 0xff; out.writeByte('%'); out.writeByte(HEX_DIGITS[(b >> 4) & 0xf]); out.writeByte(HEX_DIGITS[b & 0xf]); } } else { // This character doesn't need encoding. Just copy it over. out.writeUtf8CodePoint(codePoint); } } }通过该方法 的源码,我们就可以知道codePoint是如何来的了,如此我们就找到了出现这种问题的原因,可能是用户输入某些还不能被识别的字符,那么我们为了避免用户应用出现崩溃的情况,我们可以进行提前规避。做法如下
在出现问题的地方,对每个参数进行如下代码的检查
private boolean checkIsUnLawful(String[] input){ if (input != null && input.length> 0){ for (int i = 0; i < input.length; i++) { String length = input[i]; int codePoint; if (!TextUtils.isEmpty(length)){ for (int j = 0; j < length.length(); j += Character.charCount(codePoint)) { codePoint = length.codePointAt(j); if ((codePoint >= 0xd800 && codePoint <= 0xdfff) || codePoint > 0x10ffff) { return false; } } } } } return true; }
问题就可以解决了
0 0
- okhttp、okio添加参数(addParams)出现的java.lang.IllegalArgumentException:Unexpected code point
- OKHttp java.lang.IllegalArgumentException: Unexpected char 错误解决方法
- OKHttp java.lang.IllegalArgumentException: Unexpected url错误解决方法
- Okhttp:Fatal Exception: java.lang.IllegalArgumentException: Unexpected char 0x4e00 at 25 in header v
- Okhttp:Fatal Exception: java.lang.IllegalArgumentException:unexpected char 0x0a at28 in header value
- Okhttp关于 java.lang.NoSuchMethodError: okio.BufferedSource报错
- 异常 java.lang.IllegalArgumentException:unexpected url:
- 使用okhttp3出现java.lang.NoClassDefFoundError: okio.Buffer的错误怎么办?
- Collections.sort 排序出现的java.lang.IllegalArgumentException的异常
- 关于J2me加载图片出现的java.lang.IllegalArgumentException
- JAXB 的xjc任务时出现java.lang.IllegalArgumentException异常
- UNEXPECTED TOP-LEVEL EXCEPTION: java.lang.IllegalArgumentException: already added问题
- jbpm部署出现java.lang.IllegalArgumentException: MALFORMED
- Tomcat启动时出现java.lang.IllegalArgumentException
- 启动tomcat出现java.lang.IllegalArgumentException,解决方法
- java.lang.IllegalArgumentException 非法参数异常
- java.lang.IllegalArgumentException的解决
- java.lang.NoClassDefFoundError: okio.Buffer 错误的解决方法
- HTTP协议
- ARMv8-A系列学习笔记(2)--2.1 ARMv8-A
- docker 容器时间同步问题
- Android Studio首次git部署
- 文字检测与识别资源
- okhttp、okio添加参数(addParams)出现的java.lang.IllegalArgumentException:Unexpected code point
- Jsp的三大指令
- 安装 node
- MotionEvent中getX和getRawX的区别
- RabbitMQ的安装和配置化可视界面
- zabbix安装 报错 socket '/var/lib/mysql/mysql.sock' (13)]
- JavaScript中创建对象的几种模式
- linux下安装nginx并启动
- 过滤器的使用实现网站访问计数器