Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 package org.ros.internal.node.service;
00018
00019 import org.jboss.netty.buffer.ChannelBuffer;
00020 import org.jboss.netty.buffer.ChannelBuffers;
00021 import org.jboss.netty.channel.ChannelHandlerContext;
00022 import org.jboss.netty.channel.MessageEvent;
00023 import org.jboss.netty.channel.SimpleChannelHandler;
00024 import org.ros.exception.ServiceException;
00025 import org.ros.internal.message.MessageBufferPool;
00026 import org.ros.message.MessageDeserializer;
00027 import org.ros.message.MessageFactory;
00028 import org.ros.message.MessageSerializer;
00029 import org.ros.node.service.ServiceResponseBuilder;
00030
00031 import java.nio.ByteBuffer;
00032 import java.nio.charset.Charset;
00033 import java.util.concurrent.ExecutorService;
00034
00038 class ServiceRequestHandler<T, S> extends SimpleChannelHandler {
00039
00040 private final ServiceDeclaration serviceDeclaration;
00041 private final ServiceResponseBuilder<T, S> responseBuilder;
00042 private final MessageDeserializer<T> deserializer;
00043 private final MessageSerializer<S> serializer;
00044 private final MessageFactory messageFactory;
00045 private final ExecutorService executorService;
00046 private final MessageBufferPool messageBufferPool;
00047
00048 public ServiceRequestHandler(ServiceDeclaration serviceDeclaration,
00049 ServiceResponseBuilder<T, S> responseBuilder, MessageDeserializer<T> deserializer,
00050 MessageSerializer<S> serializer, MessageFactory messageFactory,
00051 ExecutorService executorService) {
00052 this.serviceDeclaration = serviceDeclaration;
00053 this.deserializer = deserializer;
00054 this.serializer = serializer;
00055 this.responseBuilder = responseBuilder;
00056 this.messageFactory = messageFactory;
00057 this.executorService = executorService;
00058 messageBufferPool = new MessageBufferPool();
00059 }
00060
00061 private void handleRequest(ChannelBuffer requestBuffer, ChannelBuffer responseBuffer)
00062 throws ServiceException {
00063 T request = deserializer.deserialize(requestBuffer);
00064 S response = messageFactory.newFromType(serviceDeclaration.getType());
00065 responseBuilder.build(request, response);
00066 serializer.serialize(response, responseBuffer);
00067 }
00068
00069 private void handleSuccess(final ChannelHandlerContext ctx, ServiceServerResponse response,
00070 ChannelBuffer responseBuffer) {
00071 response.setErrorCode(1);
00072 response.setMessageLength(responseBuffer.readableBytes());
00073 response.setMessage(responseBuffer);
00074 ctx.getChannel().write(response);
00075 }
00076
00077 private void handleError(final ChannelHandlerContext ctx, ServiceServerResponse response,
00078 String message) {
00079 response.setErrorCode(0);
00080 ByteBuffer encodedMessage = Charset.forName("US-ASCII").encode(message);
00081 response.setMessageLength(encodedMessage.limit());
00082 response.setMessage(ChannelBuffers.wrappedBuffer(encodedMessage));
00083 ctx.getChannel().write(response);
00084 }
00085
00086 @Override
00087 public void messageReceived(final ChannelHandlerContext ctx, MessageEvent e) throws Exception {
00088
00089
00090
00091 final ChannelBuffer requestBuffer = ((ChannelBuffer) e.getMessage()).copy();
00092 executorService.execute(new Runnable() {
00093 @Override
00094 public void run() {
00095 ServiceServerResponse response = new ServiceServerResponse();
00096 ChannelBuffer responseBuffer = messageBufferPool.acquire();
00097 boolean success;
00098 try {
00099 handleRequest(requestBuffer, responseBuffer);
00100 success = true;
00101 } catch (ServiceException ex) {
00102 handleError(ctx, response, ex.getMessage());
00103 success = false;
00104 }
00105 if (success) {
00106 handleSuccess(ctx, response, responseBuffer);
00107 }
00108 messageBufferPool.release(responseBuffer);
00109 }
00110 });
00111 super.messageReceived(ctx, e);
00112 }
00113 }