公司构建了自己的推送系统,我们的app的推送也有极光推送改为了自己的推送。在使用我们自己的推送的过程中,推送纯文字一切正常,但如果推送内容中含有特殊表情(比如这样的
),在一部分Android机器(红米3,努比亚)上就会出现异常。异常如下:
JNI DETECTED ERROR IN APPLICATION: input is not valid Modified UTF-8: illegal start byte 0xfe。
我再网上百度了下产生的原因如下:这个异常是由于Java虚拟机内部的 dalvik/vm/CheckJni.c中的 checkUtfString函数抛出的,JVM的这个接口不支持四个字节的UTF8字符。在我的仔细检查下找到了问题发生的地方 :
jstring msg= (*env)->NewStringUTF(env, msg);
而这msg就是jni调用java方法返回给客户端的需要处理的一个JSONString。在网上也有人给出了解决方法(调用函数之前,对接口传入的字符串进行过滤。可以参考这个链接http://www.mobibrw.com/2016/2859)。但这个方法我们不可以使用(产品要求昵称可以含有表情)。Google了好久,发现了一个解决方法:让jni返回给java层byte[] ,在java层将byte[]转换成String字符串然后处理。果然在我的尝试下这个问题就这样解决了。
修改后的关键代码如下
jni层的处理如下
jmethodID g_mid = (*env)->GetMethodID(env, g_clazz,"callback","(Ljava/lang/String;[B)V");
jbyteArray byteArray = (*env)->NewByteArray(env,payload_size);
(*env)->SetByteArrayRegion(env,byteArray, 0, payload_size, payload);
(*env)->CallVoidMethod(env, g_obj, g_mid, jappid, byteArray);
java层jni调用的方法如下
public void callback(String appId, byte[] data) {
if(data==null) return;
String msg=new String(data);
if (!TextUtils.isEmpty(saveLog(GPushClient.getLogFilePath(), msg);
Intent intent = new Intent();
intent.setAction(GPushClient.MESSAGE_RECEIVED_ACTION);
intent.putExtra(GPushClient.EXTRA, msg);
mContext.sendBroadcast(intent);
}
}
第一次发博客,有什么不正确的欢迎指正,有什么疑问也可以联系我邮箱:972876901@qq.com