All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.jboss.netty.handler.codec.protobuf.ProtobufDecoder Maven / Gradle / Ivy

/*
 * Copyright 2009 Red Hat, Inc.
 *
 * Red Hat licenses this file to you under the Apache License, version 2.0
 * (the "License"); you may not use this file except in compliance with the
 * License.  You may obtain a copy of the License at:
 *
 *    http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
 * License for the specific language governing permissions and limitations
 * under the License.
 */
package org.jboss.netty.handler.codec.protobuf;

import org.jboss.netty.buffer.ChannelBuffer;
import org.jboss.netty.buffer.ChannelBufferInputStream;
import org.jboss.netty.channel.Channel;
import org.jboss.netty.channel.ChannelHandler.Sharable;
import org.jboss.netty.channel.ChannelHandlerContext;
import org.jboss.netty.channel.ChannelPipeline;
import org.jboss.netty.channel.MessageEvent;
import org.jboss.netty.handler.codec.frame.FrameDecoder;
import org.jboss.netty.handler.codec.frame.LengthFieldBasedFrameDecoder;
import org.jboss.netty.handler.codec.frame.LengthFieldPrepender;
import org.jboss.netty.handler.codec.oneone.OneToOneDecoder;

import com.google.protobuf.ExtensionRegistry;
import com.google.protobuf.Message;
import com.google.protobuf.MessageLite;

/**
 * Decodes a received {@link ChannelBuffer} into a
 * Google Protocol Buffers
 * {@link Message} and {@link MessageLite}.  Please note that this decoder must
 * be used with a proper {@link FrameDecoder} such as {@link ProtobufVarint32FrameDecoder}
 * or {@link LengthFieldBasedFrameDecoder} if you are using a stream-based
 * transport such as TCP/IP.  A typical setup for TCP/IP would be:
 * 
 * {@link ChannelPipeline} pipeline = ...;
 *
 * // Decoders
 * pipeline.addLast("frameDecoder",
 *                  new {@link LengthFieldBasedFrameDecoder}(1048576, 0, 4, 0, 4));
 * pipeline.addLast("protobufDecoder",
 *                  new {@link ProtobufDecoder}(MyMessage.getDefaultInstance()));
 *
 * // Encoder
 * pipeline.addLast("frameEncoder", new {@link LengthFieldPrepender}(4));
 * pipeline.addLast("protobufEncoder", new {@link ProtobufEncoder}());
 * 
* and then you can use a {@code MyMessage} instead of a {@link ChannelBuffer} * as a message: *
 * void messageReceived({@link ChannelHandlerContext} ctx, {@link MessageEvent} e) {
 *     MyMessage req = (MyMessage) e.getMessage();
 *     MyMessage res = MyMessage.newBuilder().setText(
 *                               "Did you say '" + req.getText() + "'?").build();
 *     ch.write(res);
 * }
 * 
* * @author The Netty Project * @author Trustin Lee * * @version $Rev:231 $, $Date:2008-06-12 16:44:50 +0900 (목, 12 6월 2008) $ * * @apiviz.landmark */ @Sharable public class ProtobufDecoder extends OneToOneDecoder { private final MessageLite prototype; private final ExtensionRegistry extensionRegistry; /** * Creates a new instance. */ public ProtobufDecoder(MessageLite prototype) { this(prototype, null); } public ProtobufDecoder(MessageLite prototype, ExtensionRegistry extensionRegistry) { if (prototype == null) { throw new NullPointerException("prototype"); } this.prototype = prototype.getDefaultInstanceForType(); this.extensionRegistry = extensionRegistry; } @Override protected Object decode( ChannelHandlerContext ctx, Channel channel, Object msg) throws Exception { if (!(msg instanceof ChannelBuffer)) { return msg; } ChannelBuffer buf = (ChannelBuffer) msg; if (buf.hasArray()) { final int offset = buf.readerIndex(); if(extensionRegistry == null) { return prototype.newBuilderForType().mergeFrom( buf.array(), buf.arrayOffset() + offset, buf.readableBytes()).build(); } else { return prototype.newBuilderForType().mergeFrom( buf.array(), buf.arrayOffset() + offset, buf.readableBytes(), extensionRegistry).build(); } } else { if (extensionRegistry == null) { return prototype.newBuilderForType().mergeFrom( new ChannelBufferInputStream((ChannelBuffer) msg)).build(); } else { return prototype.newBuilderForType().mergeFrom( new ChannelBufferInputStream((ChannelBuffer) msg), extensionRegistry).build(); } } } }




© 2015 - 2025 Weber Informatics LLC | Privacy Policy