- now throws IllegalArgumentException. This is just logged and pushed into Future, the Future delegates the information further to upper ODL layers
Change-Id: I64ac1e4904e8837ab5b26572235bdaf5fac984da
Signed-off-by: Michal Polkorab <michal.polkorab@pantheon.sk>
break;
}
- final ChannelFuture p = channel.write(h.takeMessage());
final GenericFutureListener<Future<Void>> l = h.takeListener();
+ final ChannelFuture p = channel.write(new MessageListenerWrapper(h.takeMessage(), l));
if (l != null) {
p.addListener(l);
}
--- /dev/null
+/*\r
+ * Copyright (c) 2014 Pantheon Technologies s.r.o. and others. All rights reserved.\r
+ *\r
+ * This program and the accompanying materials are made available under the\r
+ * terms of the Eclipse Public License v1.0 which accompanies this distribution,\r
+ * and is available at http://www.eclipse.org/legal/epl-v10.html\r
+ */\r
+\r
+package org.opendaylight.openflowjava.protocol.impl.connection;\r
+\r
+import io.netty.util.concurrent.Future;\r
+import io.netty.util.concurrent.GenericFutureListener;\r
+\r
+import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.OfHeader;\r
+\r
+/**\r
+ * Wraps outgoing message and includes listener attached to this message. This object\r
+ * is sent to OFEncoder. When OFEncoder fails to serialize the message,\r
+ * listener is filled with exception. The exception is then delegated to upper ODL layers. \r
+ * @author michal.polkorab\r
+ */\r
+public class MessageListenerWrapper {\r
+\r
+ private OfHeader msg;\r
+ private GenericFutureListener<Future<Void>> listener;\r
+\r
+ /**\r
+ * @param msg outgoing message\r
+ * @param listener listener attached to channel.write(msg) Future\r
+ */\r
+ public MessageListenerWrapper(Object msg, GenericFutureListener<Future<Void>> listener) {\r
+ this.msg = (OfHeader) msg;\r
+ this.listener = listener;\r
+ }\r
+\r
+ /**\r
+ * @return outgoing message (downstream)\r
+ */\r
+ public OfHeader getMsg() {\r
+ return msg;\r
+ }\r
+\r
+ \r
+ /**\r
+ * @return listener listening on message sending success / failure\r
+ */\r
+ public GenericFutureListener<Future<Void>> getListener() {\r
+ return listener;\r
+ }\r
+}
\ No newline at end of file
import io.netty.buffer.ByteBuf;
import io.netty.channel.ChannelHandlerContext;
import io.netty.handler.codec.MessageToByteEncoder;
+import io.netty.util.concurrent.Future;
+import org.opendaylight.openflowjava.protocol.impl.connection.MessageListenerWrapper;
import org.opendaylight.openflowjava.protocol.impl.serialization.SerializationFactory;
-import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.OfHeader;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
* @author michal.polkorab
* @author timotej.kubas
*/
-public class OFEncoder extends MessageToByteEncoder<OfHeader> {
+public class OFEncoder extends MessageToByteEncoder<MessageListenerWrapper> {
private static final Logger LOGGER = LoggerFactory.getLogger(OFEncoder.class);
private SerializationFactory serializationFactory;
}
@Override
- protected void encode(ChannelHandlerContext ctx, OfHeader msg, ByteBuf out)
+ protected void encode(ChannelHandlerContext ctx, MessageListenerWrapper wrapper, ByteBuf out)
throws Exception {
LOGGER.trace("Encoding");
try {
- serializationFactory.messageToBuffer(msg.getVersion(), out, msg);
+ serializationFactory.messageToBuffer(wrapper.getMsg().getVersion(), out, wrapper.getMsg());
} catch(Exception e) {
- LOGGER.error("Message serialization failed");
- LOGGER.error(e.getMessage(), e);
+ LOGGER.warn("Message serialization failed: {}", e.getMessage());
+ Future<Void> newFailedFuture = ctx.newFailedFuture(e);
+ wrapper.getListener().operationComplete(newFailedFuture);
out.clear();
return;
}
OFGeneralDeserializer deserializer = registry.get(key);
if (deserializer == null) {
throw new NullPointerException("Deserializer for key: " + key.toString()
- + " was not found");
+ + " was not found - please verify that all needed deserializers ale loaded correctly");
}
return (DESERIALIZER_TYPE) deserializer;
}
public void registerDeserializer(MessageCodeKey key,
OFGeneralDeserializer deserializer) {
if ((key == null) || (deserializer == null)) {
- throw new NullPointerException("MessageCodeKey or Deserializer is null");
+ throw new IllegalArgumentException("MessageCodeKey or Deserializer is null");
}
if (deserializer instanceof DeserializerRegistryInjector) {
((DeserializerRegistryInjector) deserializer).injectDeserializerRegistry(this);
@Override
public boolean unregisterDeserializer(MessageCodeKey key) {
if (key == null) {
- throw new NullPointerException("MessageCodeKey is null");
+ throw new IllegalArgumentException("MessageCodeKey is null");
}
OFGeneralDeserializer deserializer = registry.remove(key);
if (deserializer == null) {
MessageTypeKey<KEY_TYPE> msgTypeKey) {
OFGeneralSerializer serializer = registry.get(msgTypeKey);
if (serializer == null) {
- throw new NullPointerException("Serializer for key: " + msgTypeKey.toString()
- + " was not found");
+ throw new IllegalArgumentException("Serializer for key: {}" + msgTypeKey.toString()
+ + " was not found - please verify that you are using correct message"
+ + " combination (e.g. OF v1.0 message to OF v1.0 device)");
}
return (SERIALIZER_TYPE) serializer;
}
public <KEY_TYPE> void registerSerializer(
MessageTypeKey<KEY_TYPE> msgTypeKey, OFGeneralSerializer serializer) {
if ((msgTypeKey == null) || (serializer == null)) {
- throw new NullPointerException("MessageTypeKey or Serializer is null");
+ throw new IllegalArgumentException("MessageTypeKey or Serializer is null");
}
if (serializer instanceof SerializerRegistryInjector) {
((SerializerRegistryInjector) serializer).injectSerializerRegistry(this);
@Override
public <KEY_TYPE> boolean unregisterSerializer(MessageTypeKey<KEY_TYPE> msgTypeKey) {
if (msgTypeKey == null) {
- throw new NullPointerException("MessageTypeKey is null");
+ throw new IllegalArgumentException("MessageTypeKey is null");
}
OFGeneralSerializer serializer = registry.remove(msgTypeKey);
if (serializer == null) {
import static org.mockito.Mockito.when;
import io.netty.buffer.ByteBuf;
import io.netty.channel.ChannelHandlerContext;
+import io.netty.util.concurrent.Future;
+import io.netty.util.concurrent.GenericFutureListener;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
+import org.opendaylight.openflowjava.protocol.api.util.EncodeConstants;
+import org.opendaylight.openflowjava.protocol.impl.connection.MessageListenerWrapper;
import org.opendaylight.openflowjava.protocol.impl.serialization.SerializationFactory;
import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.OfHeader;
import org.opendaylight.yangtools.yang.binding.DataObject;
@Mock ChannelHandlerContext mockChHndlrCtx ;
@Mock SerializationFactory mockSerializationFactory ;
+ @Mock MessageListenerWrapper wrapper;
@Mock OfHeader mockMsg ;
@Mock ByteBuf mockOut ;
+ @Mock Future<Void> future;
+ @Mock GenericFutureListener<Future<Void>> listener;
OFEncoder ofEncoder = new OFEncoder() ;
@Test
public void testEncodeSuccess() {
when(mockOut.readableBytes()).thenReturn(1);
+ when(wrapper.getMsg()).thenReturn(mockMsg);
+ when(wrapper.getMsg().getVersion()).thenReturn((short) EncodeConstants.OF13_VERSION_ID);
try {
- ofEncoder.encode(mockChHndlrCtx, mockMsg, mockOut);
+ ofEncoder.encode(mockChHndlrCtx, wrapper, mockOut);
} catch (Exception e) {
Assert.fail();
}
*/
@Test
public void testEncodeSerializationException() {
+ when(wrapper.getMsg()).thenReturn(mockMsg);
+ when(wrapper.getListener()).thenReturn(listener);
+ when(wrapper.getMsg().getVersion()).thenReturn((short) EncodeConstants.OF13_VERSION_ID);
doThrow(new IllegalArgumentException()).when(mockSerializationFactory).messageToBuffer(anyShort(),any(ByteBuf.class), any(DataObject.class));
try {
- ofEncoder.encode(mockChHndlrCtx, mockMsg, mockOut);
+ ofEncoder.encode(mockChHndlrCtx, wrapper, mockOut);
} catch (Exception e) {
Assert.fail();
}
@Test
public void testEncodeSerializesNoBytes() {
when(mockOut.readableBytes()).thenReturn(0);
+ when(wrapper.getMsg()).thenReturn(mockMsg);
+ when(wrapper.getMsg().getVersion()).thenReturn((short) EncodeConstants.OF13_VERSION_ID);
try {
- ofEncoder.encode(mockChHndlrCtx, mockMsg, mockOut);
+ ofEncoder.encode(mockChHndlrCtx, wrapper, mockOut);
} catch (Exception e) {
Assert.fail();
}