Bump MRI upstreams
[netconf.git] / netconf / netconf-topology-impl / src / test / java / org / opendaylight / netconf / topology / impl / NetconfTopologyImplTest.java
1 /*
2  * Copyright (c) 2016 Cisco Systems, Inc. and others. All rights reserved.
3  *
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
7  */
8 package org.opendaylight.netconf.topology.impl;
9
10 import static org.junit.Assert.assertEquals;
11 import static org.junit.Assert.assertFalse;
12 import static org.junit.Assert.assertNotNull;
13 import static org.junit.Assert.assertNull;
14 import static org.junit.Assert.assertTrue;
15 import static org.mockito.ArgumentMatchers.any;
16 import static org.mockito.Mockito.doNothing;
17 import static org.mockito.Mockito.doReturn;
18 import static org.mockito.Mockito.mock;
19 import static org.mockito.Mockito.spy;
20 import static org.mockito.Mockito.times;
21 import static org.mockito.Mockito.verify;
22 import static org.mockito.Mockito.when;
23 import static org.opendaylight.mdsal.common.api.CommitInfo.emptyFluentFuture;
24
25 import com.google.common.util.concurrent.Futures;
26 import com.google.common.util.concurrent.ListenableFuture;
27 import com.google.common.util.concurrent.MoreExecutors;
28 import io.netty.util.concurrent.EventExecutor;
29 import java.util.Collection;
30 import java.util.HashSet;
31 import org.junit.Before;
32 import org.junit.Test;
33 import org.junit.runner.RunWith;
34 import org.mockito.Mock;
35 import org.mockito.junit.MockitoJUnitRunner;
36 import org.opendaylight.aaa.encrypt.AAAEncryptionService;
37 import org.opendaylight.controller.config.threadpool.ScheduledThreadPool;
38 import org.opendaylight.controller.config.threadpool.ThreadPool;
39 import org.opendaylight.mdsal.binding.api.DataBroker;
40 import org.opendaylight.mdsal.binding.api.DataObjectModification;
41 import org.opendaylight.mdsal.binding.api.DataTreeModification;
42 import org.opendaylight.mdsal.binding.api.RpcProviderService;
43 import org.opendaylight.mdsal.binding.api.WriteTransaction;
44 import org.opendaylight.mdsal.common.api.LogicalDatastoreType;
45 import org.opendaylight.mdsal.dom.api.DOMMountPointService;
46 import org.opendaylight.netconf.client.NetconfClientDispatcher;
47 import org.opendaylight.netconf.client.NetconfClientSessionListener;
48 import org.opendaylight.netconf.client.conf.NetconfClientConfiguration;
49 import org.opendaylight.netconf.client.conf.NetconfReconnectingClientConfiguration;
50 import org.opendaylight.netconf.sal.connect.api.SchemaResourceManager;
51 import org.opendaylight.netconf.sal.connect.netconf.listener.NetconfDeviceCapabilities;
52 import org.opendaylight.netconf.sal.connect.netconf.schema.mapping.BaseNetconfSchemas;
53 import org.opendaylight.netconf.sal.connect.netconf.schema.mapping.DefaultBaseNetconfSchemas;
54 import org.opendaylight.netconf.topology.spi.AbstractNetconfTopology;
55 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Host;
56 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.IpAddress;
57 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Ipv4Address;
58 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.PortNumber;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNode;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNodeBuilder;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.netconf.node.connection.parameters.Protocol.Name;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.netconf.node.connection.parameters.ProtocolBuilder;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.netconf.node.credentials.credentials.LoginPasswordBuilder;
64 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NetworkTopology;
65 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NetworkTopologyBuilder;
66 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NodeId;
67 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.TopologyId;
68 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.Topology;
69 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.TopologyBuilder;
70 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.TopologyKey;
71 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.Node;
72 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.NodeBuilder;
73 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.NodeKey;
74 import org.opendaylight.yangtools.yang.binding.DataObject;
75 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
76 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier.IdentifiableItem;
77 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier.PathArgument;
78 import org.opendaylight.yangtools.yang.common.Uint16;
79 import org.opendaylight.yangtools.yang.common.Uint32;
80 import org.opendaylight.yangtools.yang.parser.api.YangParserException;
81 import org.opendaylight.yangtools.yang.parser.impl.DefaultYangParserFactory;
82
83 @RunWith(MockitoJUnitRunner.StrictStubs.class)
84 public class NetconfTopologyImplTest {
85
86     private static final NodeId NODE_ID = new NodeId("testing-node");
87     private static final String TOPOLOGY_ID = "testing-topology";
88
89     @Mock
90     private NetconfClientDispatcher mockedClientDispatcher;
91
92     @Mock
93     private EventExecutor mockedEventExecutor;
94
95     @Mock
96     private ScheduledThreadPool mockedKeepaliveExecutor;
97
98     @Mock
99     private ThreadPool mockedProcessingExecutor;
100
101     @Mock
102     private SchemaResourceManager mockedResourceManager;
103
104     @Mock
105     private DataBroker dataBroker;
106
107     @Mock
108     private DOMMountPointService mountPointService;
109
110     @Mock
111     private AAAEncryptionService encryptionService;
112
113     @Mock
114     private RpcProviderService rpcProviderService;
115
116     private TestingNetconfTopologyImpl topology;
117     private TestingNetconfTopologyImpl spyTopology;
118
119     @Before
120     public void setUp() {
121         when(mockedProcessingExecutor.getExecutor()).thenReturn(MoreExecutors.newDirectExecutorService());
122
123         topology = new TestingNetconfTopologyImpl(TOPOLOGY_ID, mockedClientDispatcher, mockedEventExecutor,
124             mockedKeepaliveExecutor, mockedProcessingExecutor, mockedResourceManager, dataBroker, mountPointService,
125             encryptionService, rpcProviderService);
126
127         spyTopology = spy(topology);
128     }
129
130     @Test
131     public void testInit() {
132         final WriteTransaction wtx = mock(WriteTransaction.class);
133         when(dataBroker.newWriteOnlyTransaction()).thenReturn(wtx);
134         doNothing().when(wtx)
135                 .merge(any(LogicalDatastoreType.class), any(InstanceIdentifier.class), any(DataObject.class));
136         doReturn(emptyFluentFuture()).when(wtx).commit();
137         topology.init();
138
139         //verify initialization of topology
140         final InstanceIdentifier<NetworkTopology> networkTopologyId =
141                 InstanceIdentifier.builder(NetworkTopology.class).build();
142         final Topology topo = new TopologyBuilder().setTopologyId(new TopologyId(TOPOLOGY_ID)).build();
143         final NetworkTopology networkTopology = new NetworkTopologyBuilder().build();
144         verify(wtx).merge(LogicalDatastoreType.CONFIGURATION, networkTopologyId, networkTopology);
145         verify(wtx).merge(LogicalDatastoreType.OPERATIONAL, networkTopologyId, networkTopology);
146         verify(wtx).merge(LogicalDatastoreType.CONFIGURATION,
147                 networkTopologyId.child(Topology.class, new TopologyKey(new TopologyId(TOPOLOGY_ID))), topo);
148         verify(wtx).merge(LogicalDatastoreType.OPERATIONAL,
149                 networkTopologyId.child(Topology.class, new TopologyKey(new TopologyId(TOPOLOGY_ID))), topo);
150     }
151
152     @Test
153     public void testOnDataTreeChange() {
154
155         final DataObjectModification<Node> newNode = mock(DataObjectModification.class);
156         when(newNode.getModificationType()).thenReturn(DataObjectModification.ModificationType.WRITE);
157
158         NodeKey key = new NodeKey(NODE_ID);
159         PathArgument pa = IdentifiableItem.of(Node.class, key);
160         when(newNode.getIdentifier()).thenReturn(pa);
161
162         final NodeBuilder nn = new NodeBuilder()
163                 .withKey(key)
164                 .addAugmentation(new NetconfNodeBuilder()
165                     .setHost(new Host(new IpAddress(new Ipv4Address("127.0.0.1"))))
166                     .setPort(new PortNumber(Uint16.valueOf(9999)))
167                     .setReconnectOnChangedSchema(true)
168                     .setDefaultRequestTimeoutMillis(Uint32.valueOf(1000))
169                     .setBetweenAttemptsTimeoutMillis(Uint16.valueOf(100))
170                     .setKeepaliveDelay(Uint32.valueOf(1000))
171                     .setTcpOnly(true)
172                     .setCredentials(new LoginPasswordBuilder()
173                         .setUsername("testuser")
174                         .setPassword("testpassword")
175                         .build())
176                     .build());
177
178         when(newNode.getDataAfter()).thenReturn(nn.build());
179
180
181         final Collection<DataTreeModification<Node>> changes = new HashSet<>();
182         final DataTreeModification<Node> ch = mock(DataTreeModification.class);
183         when(ch.getRootNode()).thenReturn(newNode);
184         changes.add(ch);
185         spyTopology.onDataTreeChanged(changes);
186         verify(spyTopology).connectNode(NetconfTopologyImpl.getNodeId(pa), nn.build());
187
188         when(newNode.getModificationType()).thenReturn(DataObjectModification.ModificationType.DELETE);
189         spyTopology.onDataTreeChanged(changes);
190         verify(spyTopology).disconnectNode(NetconfTopologyImpl.getNodeId(pa));
191
192         when(newNode.getModificationType()).thenReturn(DataObjectModification.ModificationType.SUBTREE_MODIFIED);
193         spyTopology.onDataTreeChanged(changes);
194
195         //one in previous creating and deleting node and one in updating
196         verify(spyTopology, times(2)).disconnectNode(NetconfTopologyImpl.getNodeId(pa));
197         verify(spyTopology, times(2)).connectNode(NetconfTopologyImpl.getNodeId(pa), nn.build());
198
199
200     }
201
202     @Test
203     public void testGetClientConfig() {
204         final NetconfClientSessionListener sessionListener = mock(NetconfClientSessionListener.class);
205
206         final NetconfNode testingNode = new NetconfNodeBuilder()
207                 .setHost(new Host(new IpAddress(new Ipv4Address("127.0.0.1"))))
208                 .setPort(new PortNumber(Uint16.valueOf(9999)))
209                 .setReconnectOnChangedSchema(true)
210                 .setDefaultRequestTimeoutMillis(Uint32.valueOf(1000))
211                 .setBetweenAttemptsTimeoutMillis(Uint16.valueOf(100))
212                 .setKeepaliveDelay(Uint32.valueOf(1000))
213                 .setTcpOnly(true)
214                 .setCredentials(new LoginPasswordBuilder()
215                         .setUsername("testuser").setPassword("testpassword").build())
216                 .build();
217         final NetconfReconnectingClientConfiguration configuration =
218                 spyTopology.getClientConfig(sessionListener, testingNode);
219         assertEquals(NetconfClientConfiguration.NetconfClientProtocol.TCP, configuration.getProtocol());
220         assertNotNull(configuration.getAuthHandler());
221         assertNull(configuration.getSslHandlerFactory());
222
223
224         final NetconfNode testingNode2 = new NetconfNodeBuilder()
225                 .setHost(new Host(new IpAddress(new Ipv4Address("127.0.0.1"))))
226                 .setPort(new PortNumber(Uint16.valueOf(9999)))
227                 .setReconnectOnChangedSchema(true)
228                 .setDefaultRequestTimeoutMillis(Uint32.valueOf(1000))
229                 .setBetweenAttemptsTimeoutMillis(Uint16.valueOf(100))
230                 .setKeepaliveDelay(Uint32.valueOf(1000))
231                 .setTcpOnly(false)
232                 .setCredentials(new LoginPasswordBuilder()
233                         .setUsername("testuser").setPassword("testpassword").build())
234                 .build();
235         final NetconfReconnectingClientConfiguration configuration2 =
236                 spyTopology.getClientConfig(sessionListener, testingNode2);
237         assertEquals(NetconfClientConfiguration.NetconfClientProtocol.SSH, configuration2.getProtocol());
238         assertNotNull(configuration2.getAuthHandler());
239         assertNull(configuration2.getSslHandlerFactory());
240
241
242         final NetconfNode testingNode3 = new NetconfNodeBuilder()
243                 .setHost(new Host(new IpAddress(new Ipv4Address("127.0.0.1"))))
244                 .setPort(new PortNumber(Uint16.valueOf(9999)))
245                 .setReconnectOnChangedSchema(true)
246                 .setDefaultRequestTimeoutMillis(Uint32.valueOf(1000))
247                 .setBetweenAttemptsTimeoutMillis(Uint16.valueOf(100))
248                 .setKeepaliveDelay(Uint32.valueOf(1000))
249                 .setTcpOnly(false)
250                 .setProtocol(new ProtocolBuilder().setName(Name.SSH).build())
251                 .setCredentials(new LoginPasswordBuilder()
252                         .setUsername("testuser").setPassword("testpassword").build())
253                 .build();
254         final NetconfReconnectingClientConfiguration configuration3 =
255                 spyTopology.getClientConfig(sessionListener, testingNode3);
256         assertEquals(NetconfClientConfiguration.NetconfClientProtocol.SSH, configuration3.getProtocol());
257         assertNotNull(configuration3.getAuthHandler());
258         assertNull(configuration3.getSslHandlerFactory());
259
260
261         final NetconfNode testingNode4 = new NetconfNodeBuilder()
262                 .setHost(new Host(new IpAddress(new Ipv4Address("127.0.0.1"))))
263                 .setPort(new PortNumber(Uint16.valueOf(9999)))
264                 .setReconnectOnChangedSchema(true)
265                 .setDefaultRequestTimeoutMillis(Uint32.valueOf(1000))
266                 .setBetweenAttemptsTimeoutMillis(Uint16.valueOf(100))
267                 .setKeepaliveDelay(Uint32.valueOf(1000))
268                 .setTcpOnly(false)
269                 .setProtocol(new ProtocolBuilder().setName(Name.TLS).build())
270                 .setCredentials(new LoginPasswordBuilder()
271                         .setUsername("testuser").setPassword("testpassword").build())
272                 .build();
273         final NetconfReconnectingClientConfiguration configuration4 =
274                 spyTopology.getClientConfig(sessionListener, testingNode4);
275         assertEquals(NetconfClientConfiguration.NetconfClientProtocol.TLS, configuration4.getProtocol());
276         assertNull(configuration4.getAuthHandler());
277         assertNotNull(configuration4.getSslHandlerFactory());
278     }
279
280     public static class TestingNetconfTopologyImpl extends NetconfTopologyImpl {
281         private static final BaseNetconfSchemas BASE_SCHEMAS;
282
283         static {
284             try {
285                 BASE_SCHEMAS = new DefaultBaseNetconfSchemas(new DefaultYangParserFactory());
286             } catch (YangParserException e) {
287                 throw new ExceptionInInitializerError(e);
288             }
289         }
290
291         public TestingNetconfTopologyImpl(final String topologyId, final NetconfClientDispatcher clientDispatcher,
292                                           final EventExecutor eventExecutor,
293                                           final ScheduledThreadPool keepaliveExecutor,
294                                           final ThreadPool processingExecutor,
295                                           final SchemaResourceManager schemaRepositoryProvider,
296                                           final DataBroker dataBroker, final DOMMountPointService mountPointService,
297                                           final AAAEncryptionService encryptionService,
298                                           final RpcProviderService rpcProviderService) {
299             super(topologyId, clientDispatcher, eventExecutor, keepaliveExecutor,
300                   processingExecutor, schemaRepositoryProvider, dataBroker,
301                   mountPointService, encryptionService, rpcProviderService, BASE_SCHEMAS);
302         }
303
304         @Override
305         public ListenableFuture<NetconfDeviceCapabilities> connectNode(final NodeId nodeId, final Node configNode) {
306             return Futures.immediateFuture(new NetconfDeviceCapabilities());
307         }
308
309         @Override
310         public ListenableFuture<Void> disconnectNode(final NodeId nodeId) {
311             return Futures.immediateFuture(null);
312         }
313     }
314
315     @Test
316     public void hideCredentialsTest() {
317         final String userName = "admin";
318         final String password = "pa$$word";
319         final Node node = new NodeBuilder()
320                 .addAugmentation(new NetconfNodeBuilder()
321                     .setHost(new Host(new IpAddress(new Ipv4Address("127.0.0.1"))))
322                     .setPort(new PortNumber(Uint16.valueOf(9999)))
323                     .setReconnectOnChangedSchema(true)
324                     .setDefaultRequestTimeoutMillis(Uint32.valueOf(1000))
325                     .setBetweenAttemptsTimeoutMillis(Uint16.valueOf(100))
326                     .setKeepaliveDelay(Uint32.valueOf(1000))
327                     .setTcpOnly(false)
328                     .setProtocol(new ProtocolBuilder().setName(Name.TLS).build())
329                     .setCredentials(new LoginPasswordBuilder()
330                         .setUsername(userName)
331                         .setPassword(password)
332                         .build())
333                     .build())
334                 .setNodeId(NodeId.getDefaultInstance("junos"))
335                 .build();
336         final String transformedNetconfNode = AbstractNetconfTopology.hideCredentials(node);
337         assertTrue(transformedNetconfNode.contains("credentials=***"));
338         assertFalse(transformedNetconfNode.contains(userName));
339         assertFalse(transformedNetconfNode.contains(password));
340     }
341 }