在 Android 中使用 MessagePack
有人尝试过在 Android 应用中使用 MessagePack
吗?
是否可以?我尝试使用 msgpack-java
中的 Jar 并收到以下异常:
Caused by: java.lang.ExceptionInInitializerError
at org.msgpack.Packer.pack(Packer.java:532)
at org.msgpack.MessagePack.pack(MessagePack.java:31)
... 15 more
Caused by: java.lang.ExceptionInInitializerError
at org.msgpack.template.TemplateRegistry.<clinit>(TemplateRegistry.java:38)
... 17 more
Caused by: java.lang.VerifyError: org.msgpack.template.BeansFieldEntryReader
at org.msgpack.template.builder.BeansTemplateBuilder.<init (BeansTemplateBuilder.java:42)
at org.msgpack.template.builder.BuilderSelectorRegistry.initForJava(BuilderSelectorRegistry.java:73)
at org.msgpack.template.builder.BuilderSelectorRegistry.<clinit>(BuilderSelectorRegistry.java:38)
... 18 more
代码我使用的非常简单
PrintWriter out = new PrintWriter(socket.getOutputStream());
Message msg = new Message();
msg.body = "asdasdasd";
msg.from = "qwe";
msg.to = "ttt";
byte[] bytes = MessagePack.pack(msg);
out.print(bytes);
out.flush();
,我有 javassist.jar
、msgpack-0.5.2.jar
、slf4j-api-1.6.2.jar
和slf4j-jdk14-1.6.2.jar
在我的 lib
目录中。
在我的服务器应用程序中,此代码可以与相同的库配合使用。
Has someone tried to use MessagePack
with an Android app?
Is it possible? I have tried to use the Jar from msgpack-java
and received the following Exception:
Caused by: java.lang.ExceptionInInitializerError
at org.msgpack.Packer.pack(Packer.java:532)
at org.msgpack.MessagePack.pack(MessagePack.java:31)
... 15 more
Caused by: java.lang.ExceptionInInitializerError
at org.msgpack.template.TemplateRegistry.<clinit>(TemplateRegistry.java:38)
... 17 more
Caused by: java.lang.VerifyError: org.msgpack.template.BeansFieldEntryReader
at org.msgpack.template.builder.BeansTemplateBuilder.<init (BeansTemplateBuilder.java:42)
at org.msgpack.template.builder.BuilderSelectorRegistry.initForJava(BuilderSelectorRegistry.java:73)
at org.msgpack.template.builder.BuilderSelectorRegistry.<clinit>(BuilderSelectorRegistry.java:38)
... 18 more
The code that I use is very simple
PrintWriter out = new PrintWriter(socket.getOutputStream());
Message msg = new Message();
msg.body = "asdasdasd";
msg.from = "qwe";
msg.to = "ttt";
byte[] bytes = MessagePack.pack(msg);
out.print(bytes);
out.flush();
I have javassist.jar
, msgpack-0.5.2.jar
, slf4j-api-1.6.2.jar
and slf4j-jdk14-1.6.2.jar
in my lib
directory.
In my server application this code works fine with the same libraries.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
(希望)最终更新
msgpack:
0.6.8
在Android上运行没有任何问题msgpack-rpc:
0.7.0
适用于 Android,但有一个警告。具体来说,您需要将以下内容添加到 API 级别 8 (Android 2.2.1) 的
onCreate
中,甚至可能更低:由于 此错误。
如果您想查看一个简单的示例,这里有两个为此目的设置的项目:
以前的版本
更新:截至 0.6.7 msgpack 应该与 Android 兼容(存在一个小的依赖排除问题)。检查下面的 msgpack-rpc 文本(将来也可能会进行调整)。
注意:如果您还使用 msgpack-rpc,则需要执行以下操作以下步骤:
NettyEventLoop 替换是由于以下问题造成的:
http://markmail.org/message/ypa3nrr64kzsyfsa。
重要提示:我只测试了同步通信。异步可能不起作用。
以下是 msgpack 无法在
0.6.7
之前的 Android 上运行的原因:错误的原因是 MessagePack 使用了几个未包含在 Android 中的 java.beans 类。安卓 SDK。您可能正在使用 MessagePackBeans 注释。
这与此处描述的问题类似, 此处概述了一般解决方案。不幸的是,在我们的例子中,它需要重建 msgpack。这就是我所做的(您几乎肯定可以跳过步骤 5 和 8,但我还没有尝试过这种方式):
应该可以做到这一点。使用您的示例代码和我自己的数据类,我成功地打包和解包数据。
整个重命名仪式是由于 DEX 编译器抱怨 java.* 包命名这一事实造成的。
(Hopefully) FINAL UPDATE
msgpack :
0.6.8
works on Android without any problemsmsgpack-rpc :
0.7.0
works on Android with one caveat.Specifically, you need to add the following to
onCreate
for API Level 8 (Android 2.2.1), and possibly lower:due to this bug.
If you want to see a simple example, here's a pair of projects set up for this purpose:
Previous Versions
UPDATE: as of 0.6.7 msgpack should be compatible with Android (there is a small dependency exclusion issue). Check the text below for msgpack-rpc (which also might be adapted in the future).
NOTE: If you're also using msgpack-rpc, you need to do the following steps:
The NettyEventLoop replacement is due to this issue:
http://markmail.org/message/ypa3nrr64kzsyfsa .
Important: I've only tested synchronous communication. Asynchronous might not work.
And here's the reason for msgpack not working with Android prior to
0.6.7
:The reason for the error is that MessagePack uses several java.beans classes that are not included in the Android SDK. You're probably using the MessagePackBeans annotation.
This is a similar problem to the one described here, for which the general solution is outlined here. Unfortunately, in our case it requires a rebuild of msgpack. Here's what I did (you can almost certainly skip Steps 5 and 8, but I haven't tried it that way) :
That should do it. Using your example code, and my own data class, I was successfully able to pack and unpack data.
The entire renaming ritual is due to the fact that the DEX compiler complains about java.* package naming.
有一个严重的 msgpack 错误,表明使用 msgpack 打包的数据将在 Dalvik VM 上损坏。 http://jira.msgpack.org/browse/MSGPACK-51
There is a critical msgpack bug saying data packed with msgpack will get corrupted on the Dalvik VM. http://jira.msgpack.org/browse/MSGPACK-51
@TheTerribleSwiftTomato 和 MessagePack 核心团队正在不断努力让 MessagePack 在 Android 上运行,请参阅相关的 GitHub 问题。 @TheTerribleSwiftTomato 的答案中提到的修复可以在此处找到。
更新
我已经设法让它至少在 Android 上运行,方法是(煞费苦心地)添加当前构建成功所需的所有必要的
javassist
类。大小额外增加了600KB
,但至少看起来有效。总而言之,它似乎在某种程度上可以在 Android 上运行,最终查看有关 Message Pack 的鲜为人知的资源,例如其 用户组 及其 Wiki了解更多信息。顺便说一句,请务必使用 HTTP 请求库(例如 LoopJ 的 Android Async HTTP 或 Apache 的 HttpClient),它可以处理二进制数据。
最后但并非最不重要的一点是,如果您对这个
jar
感兴趣,您可以联系我,它使 MessagePack 看起来可以在 Android 上运行 - 当然,感谢 @TheTerribleSwiftTomato,他提供了上面的修复程序!There is an ongoing effort by @TheTerribleSwiftTomato and the MessagePack core team to get MessagePack working on Android, please see the related GitHub issue. The fix mentioned in @TheTerribleSwiftTomato's answer is to be found here.
Update
I've managed to get it at least running on Android by (painstakingly) adding all the necessary
javassist
Classes which are currently required for the build to succeed. An extra600KB
gain in size, yet at least it seems to work. All in all, it appears to be working to some extent on Android, eventually check out the lesser-known resources about Message Pack such as its User Group and its Wiki for more information.On a side-note, be sure to use a HTTP Request Library (such as LoopJ's Android Async HTTP or Apache's HttpClient) which can handle binary data.
Last but not least you can ping me if there is interest in this
jar
which makes MessagePack seemingly work on Android – credits go out of course to @TheTerribleSwiftTomato who supplied the fix above!我建议你把这个写在主 proguard-rules 文件中 -
I suggest you write this in the main proguard-rules file-