网络编码/解码Java对象

时间:2014-11-28 21:33:37

标签: java serialization netty

我正在使用Netty 3.9。我有一个简单的客户端服务器设置,我从http://en.wikipedia.org/wiki/Netty_%28software%29#Netty_TCP_Example获得。我已经扩展了示例,将Java搜索计划对象从客户端发送到服务器

搜索计划对象是第三方对象,具有序列化和反序列化的方法。序列化将对象写入byte []数组。我的客户管道工厂看起来像这样:

this.bootstrap.setPipelineFactory(new ChannelPipelineFactory() {
        @Override
        public ChannelPipeline getPipeline() throws Exception {
            return Channels.pipeline(
                    new StringDecoder(CharsetUtil.UTF_8),
                    new StringEncoder(CharsetUtil.UTF_8),
                    new DelimiterBasedFrameDecoder(
                            ALLOWED_CHARACTER_BUFFER_SIZE, Delimiters
                                    .lineDelimiter()),

                    /* We also add our Clients own ChannelHandler. */
                    new ClientChannelHandler());
        }
    });

我认为StringDecoder和StringEncoder是不正确的。我想我需要某种ByteEncoder / Decoder,我看不到。我需要写这些吗?我尝试将此代码转换为客户端上的String

 byte[] byteVersion = searchPlanRepo.serialize(missionNum);  // serialize the search plan
 searchPlanStr = new String(byteVersion, StandardCharsets.UTF_8);

但在服务器上无论我做什么来“反序列化”我失败的对象。我不断收到错误消息:

“java.lang.ClassCastException:java.lang.String无法强制转换为payload.mission.SearchPlanType”

我的问题:

  1. 我需要自定义字节编码器/解码器吗?有没有例子?
  2. 序列化似乎很简单:字节数组到字符串但从字符串到字节数组的反序列化不起作用。我相信我错过了一些东西。有人能指出我正确的方向吗?
  3. 感谢您花时间阅读本文。 :)

    菲尔

2 个答案:

答案 0 :(得分:1)

您可以查看序列化编解码器:

http://netty.io/3.9/api/org/jboss/netty/handler/codec/serialization/package-summary.html

关于相关示例:

https://github.com/netty/netty/tree/3.9/src/main/java/org/jboss/netty/example/objectecho

它们说明了如何序列化/反序列化对象。当然,如果它更具体,你也可以编写自己的编解码器。

答案 1 :(得分:1)

我查看了示例ObjectDecoder和ObjectEncoder示例,这解决了我的问题。我更改了客户端上的管道代码,现在我可以发出我的任务了。以下是客户/发件人的代码:

this.bootstrap.setPipelineFactory(new ChannelPipelineFactory() {

        @Override
        public ChannelPipeline getPipeline() throws Exception {
            return Channels.pipeline(
                    new ObjectEncoder(),
                    new ObjectDecoder(ClassResolvers
                            .cacheDisabled(getClass().getClassLoader())),
                    new ClientChannelHandler());
        }
    });

服务器/接收器上的pipelineFactory代码几乎相同。唯一的区别是每一方的处理程序。客户端使用ClientChannelHandler,它只是从服务器记录消息。服务器使用ServerChannelHandler接收任务并将其转换为正确的Java类型,以便我可以操作它。