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