2 * Copyright (c) 2014 Brocade Communications Systems, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
9 package org.opendaylight.openflowjava.protocol.impl.core;
11 import static org.junit.Assert.assertEquals;
12 import static org.mockito.ArgumentMatchers.any;
13 import static org.mockito.ArgumentMatchers.eq;
14 import static org.mockito.Mockito.doThrow;
15 import static org.mockito.Mockito.times;
16 import static org.mockito.Mockito.verify;
17 import static org.mockito.Mockito.when;
19 import com.google.common.collect.Lists;
20 import io.netty.channel.ChannelHandler;
21 import io.netty.channel.ChannelPipeline;
22 import io.netty.channel.group.DefaultChannelGroup;
23 import io.netty.channel.socket.SocketChannel;
24 import io.netty.handler.ssl.SslHandler;
25 import java.net.InetAddress;
26 import java.net.InetSocketAddress;
27 import java.net.UnknownHostException;
28 import javax.net.ssl.SSLEngine;
29 import org.junit.Before;
30 import org.junit.Test;
31 import org.mockito.Mock;
32 import org.mockito.MockitoAnnotations;
33 import org.opendaylight.openflowjava.protocol.api.connection.SwitchConnectionHandler;
34 import org.opendaylight.openflowjava.protocol.api.connection.TlsConfiguration;
35 import org.opendaylight.openflowjava.protocol.api.connection.TlsConfigurationImpl;
36 import org.opendaylight.openflowjava.protocol.impl.core.connection.ConnectionAdapterFactory;
37 import org.opendaylight.openflowjava.protocol.impl.core.connection.ConnectionFacade;
38 import org.opendaylight.openflowjava.protocol.impl.deserialization.DeserializationFactory;
39 import org.opendaylight.openflowjava.protocol.impl.serialization.SerializationFactory;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.KeystoreType;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.config.rev140630.PathType;
44 * Unit tests for ChannelInitializer.
48 public class PublishingChannelInitializerTest {
50 private static final int CHANNEL_OUTBOUND_QUEUE_SIZE = 1024;
51 @Mock SocketChannel mockSocketCh ;
52 @Mock ChannelPipeline mockChPipeline ;
53 @Mock SwitchConnectionHandler mockSwConnHandler ;
54 @Mock ConnectionAdapterFactory mockConnAdaptorFactory;
55 @Mock DefaultChannelGroup mockChGrp ;
56 @Mock ConnectionFacade mockConnFacade ;
60 @Mock SerializationFactory mockSerializationFactory ;
61 @Mock DeserializationFactory mockDeserializationFactory ;
63 TlsConfiguration tlsConfiguration ;
64 InetSocketAddress inetSockAddr;
65 TcpChannelInitializer pubChInitializer ;
68 * Sets up test environment.
71 public void setUp() throws Exception {
72 MockitoAnnotations.initMocks(this);
73 pubChInitializer = new TcpChannelInitializer(mockChGrp, mockConnAdaptorFactory) ;
74 pubChInitializer.setSerializationFactory(mockSerializationFactory);
75 pubChInitializer.setDeserializationFactory(mockDeserializationFactory);
76 pubChInitializer.setSwitchIdleTimeout(1) ;
77 pubChInitializer.getConnectionIterator() ;
78 pubChInitializer.setUseBarrier(true);
79 pubChInitializer.setChannelOutboundQueueSize(CHANNEL_OUTBOUND_QUEUE_SIZE);
81 when(mockChGrp.size()).thenReturn(1);
82 pubChInitializer.setSwitchConnectionHandler(mockSwConnHandler);
84 inetSockAddr = new InetSocketAddress(InetAddress.getLocalHost(), 8675);
86 when(mockConnAdaptorFactory.createConnectionFacade(mockSocketCh, null, true, CHANNEL_OUTBOUND_QUEUE_SIZE))
87 .thenReturn(mockConnFacade);
88 when(mockSocketCh.remoteAddress()).thenReturn(inetSockAddr) ;
89 when(mockSocketCh.localAddress()).thenReturn(inetSockAddr) ;
90 when(mockSocketCh.remoteAddress()).thenReturn(inetSockAddr) ;
91 when(mockSwConnHandler.accept(eq(InetAddress.getLocalHost()))).thenReturn(true) ;
92 when(mockSocketCh.pipeline()).thenReturn(mockChPipeline) ;
94 tlsConfiguration = new TlsConfigurationImpl(KeystoreType.JKS, "/selfSignedSwitch", PathType.CLASSPATH,
95 KeystoreType.JKS, "/selfSignedController", PathType.CLASSPATH,
96 Lists.newArrayList("TLS_RSA_WITH_AES_128_CBC_SHA", "TLS_RSA_WITH_AES_128_CBC_SHA256"));
101 * Test channel initialization with encryption config set.
104 public void testinitChannelEncryptionSet() {
105 pubChInitializer.setTlsConfiguration(tlsConfiguration);
106 pubChInitializer.initChannel(mockSocketCh) ;
108 verifyCommonHandlers();
109 verify(mockChPipeline, times(1)).addLast(eq(PipelineHandlers.SSL_HANDLER.name()),any(SslHandler.class)) ;
113 * Test channel initialization with null encryption config.
116 public void testinitChannelEncryptionSetNullTls() {
117 pubChInitializer.setTlsConfiguration(null);
118 pubChInitializer.initChannel(mockSocketCh) ;
120 verifyCommonHandlers();
121 verify(mockChPipeline, times(0)).addLast(eq(PipelineHandlers.SSL_HANDLER.name()),any(SslHandler.class)) ;
125 * Test channel initialization without setting the encryption.
128 public void testinitChannelEncryptionNotSet() {
129 // Without encryption, only the common
130 pubChInitializer.initChannel(mockSocketCh) ;
132 verifyCommonHandlers();
136 * Test disconnect on new connection rejected.
139 public void testinitChannelNoEncryptionAcceptFails() throws UnknownHostException {
140 when(mockSwConnHandler.accept(eq(InetAddress.getLocalHost()))).thenReturn(false) ;
141 pubChInitializer.initChannel(mockSocketCh) ;
143 verify(mockSocketCh, times(1)).disconnect();
144 verify(mockChPipeline, times(0)).addLast(any(String.class), any(ChannelHandler.class));
148 * Test channel close on exception during initialization.
151 public void testExceptionThrown() {
152 doThrow(new IllegalArgumentException()).when(mockSocketCh).pipeline() ;
153 pubChInitializer.initChannel(mockSocketCh);
155 verify(mockSocketCh, times(1)).close();
159 * All paths should install these six handlers.
161 private void verifyCommonHandlers() {
162 verify(mockChPipeline, times(1)).addLast(eq(PipelineHandlers.IDLE_HANDLER.name()),any(IdleHandler.class)) ;
163 verify(mockChPipeline, times(1)).addLast(eq(PipelineHandlers.OF_DECODER.name()),any(OFDecoder.class)) ;
164 verify(mockChPipeline, times(1)).addLast(eq(PipelineHandlers.OF_ENCODER.name()),any(OFEncoder.class)) ;
165 verify(mockChPipeline, times(1)).addLast(eq(PipelineHandlers.OF_FRAME_DECODER.name()),
166 any(OFFrameDecoder.class));
167 verify(mockChPipeline, times(1)).addLast(eq(PipelineHandlers.OF_VERSION_DETECTOR.name()),
168 any(OFVersionDetector.class));
169 verify(mockChPipeline, times(1)).addLast(eq(PipelineHandlers.DELEGATING_INBOUND_HANDLER.name()),
170 any(DelegatingInboundHandler.class));
171 assertEquals(1, pubChInitializer.size()) ;