2 * Copyright (c) 2016 Cisco 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
8 package org.opendaylight.groupbasedpolicy.renderer.ios_xe_provider.impl.manager;
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.assertTrue;
14 import static org.mockito.Matchers.any;
15 import static org.mockito.Mockito.mock;
16 import static org.mockito.Mockito.when;
17 import static org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNodeConnectionStatus.ConnectionStatus.Connected;
18 import static org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNodeConnectionStatus.ConnectionStatus.Connecting;
19 import static org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNodeConnectionStatus.ConnectionStatus.UnableToConnect;
21 import javax.annotation.Nonnull;
22 import java.util.Arrays;
23 import java.util.Collection;
24 import java.util.Collections;
25 import java.util.List;
26 import com.google.common.base.Optional;
27 import com.google.common.util.concurrent.CheckedFuture;
28 import org.junit.Before;
29 import org.junit.Test;
30 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
31 import org.opendaylight.controller.md.sal.binding.api.MountPointService;
32 import org.opendaylight.controller.md.sal.binding.api.ReadWriteTransaction;
33 import org.opendaylight.controller.md.sal.binding.api.WriteTransaction;
34 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
35 import org.opendaylight.controller.md.sal.common.api.data.ReadFailedException;
36 import org.opendaylight.controller.sal.binding.api.BindingAwareBroker;
37 import org.opendaylight.groupbasedpolicy.test.CustomDataBrokerTest;
38 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Host;
39 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.IpAddress;
40 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Ipv4Address;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.renderer.rev151103.Renderers;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.renderer.rev151103.renderers.renderer.RendererNodes;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.groupbasedpolicy.renderer.rev151103.renderers.renderer.renderer.nodes.RendererNode;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNode;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNodeBuilder;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.NetconfNodeConnectionStatus;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.netconf.node.connection.status.AvailableCapabilities;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.netconf.node.topology.rev150114.netconf.node.connection.status.AvailableCapabilitiesBuilder;
49 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NetworkTopology;
50 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.NodeId;
51 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.TopologyId;
52 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.Topology;
53 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.TopologyKey;
54 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.Node;
55 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.NodeBuilder;
56 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.NodeKey;
57 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
60 public class NodeManagerTest extends CustomDataBrokerTest {
62 private final NodeId NODE_NAME = new NodeId("testNode");
63 private final TopologyId TOPOLOGY_ID = new TopologyId("topology-netconf");
64 private final Ipv4Address IPv4_ADDRESS = new Ipv4Address("174.25.75.11");
65 private NodeManager nodeManager;
66 private DataBroker dataBroker;
70 public Collection<java.lang.Class<?>> getClassesFromModules() {
71 return Arrays.asList(Renderers.class, NetworkTopology.class, NetconfNode.class);
76 dataBroker = getDataBroker();
77 BindingAwareBroker.ProviderContext context = mock(BindingAwareBroker.ProviderContext.class);
78 MountPointService mountPointService = mock(MountPointService.class);
79 when(context.getSALService(any())).thenReturn(mountPointService);
80 nodeManager = new NodeManager(dataBroker, context);
84 public void testRegisterNewNode_connectingCase() throws Exception {
85 Node testNode = createNode(Connecting, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
86 nodeManager.syncNodes(testNode, null);
87 List<RendererNode> result = rendererNodesReader();
88 assertTrue(result.isEmpty());
94 public void testRegisterNewNode_connectedCaseNoIpAddress() throws Exception {
95 Node testNode = createNode(Connected, null, NODE_NAME, Capabilities.None);
96 nodeManager.syncNodes(testNode, null);
97 List<RendererNode> result = rendererNodesReader();
98 assertTrue(result.isEmpty());
102 public void testRegisterNewNode_connectedCaseNullCapabilities() throws Exception {
103 Node testNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.None);
104 nodeManager.syncNodes(testNode, null);
105 List<RendererNode> result = rendererNodesReader();
106 assertTrue(result.isEmpty());
110 public void testRegisterNewNode_connectedCasePartialCapabilities() throws Exception {
111 Node testNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Partial);
112 nodeManager.syncNodes(testNode, null);
113 List<RendererNode> result = rendererNodesReader();
114 assertTrue(result.isEmpty());
118 public void testRegisterNewNode_connectedCaseFullCapabilities() throws Exception {
119 Node testNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
120 nodeManager.syncNodes(testNode, null);
121 List<RendererNode> result = rendererNodesReader();
122 assertNotNull(result);
123 assertTrue(result.size() == 1);
127 public void testRegisterNewNode_unableToConnectCase() throws Exception {
128 Node testNode = createNode(UnableToConnect, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
129 nodeManager.syncNodes(testNode, null);
130 List<RendererNode> result = rendererNodesReader();
131 assertTrue(result.isEmpty());
135 public void testUpdateNode_fromConnectingToConnected() throws Exception {
136 Node oldNode = createNode(Connecting, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
137 Node newNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
138 nodeManager.syncNodes(oldNode, null);
139 List<RendererNode> result = rendererNodesReader();
140 assertTrue(result.isEmpty());
141 nodeManager.syncNodes(newNode, oldNode);
142 result = rendererNodesReader();
143 assertNotNull(result);
144 assertTrue(result.size() == 1);
150 public void testUpdateNode_fromConnectingToUnableToConnect() throws Exception {
151 Node oldNode = createNode(Connecting, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
152 Node newNode = createNode(UnableToConnect, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
153 nodeManager.syncNodes(oldNode, null);
154 List<RendererNode> result = rendererNodesReader();
155 assertTrue(result.isEmpty());
156 nodeManager.syncNodes(newNode, oldNode);
157 result = rendererNodesReader();
158 assertTrue(result.isEmpty());
162 public void testUpdateNode_fromConnectedToConnecting() throws Exception {
163 Node oldNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
164 Node newNode = createNode(Connecting, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
165 nodeManager.syncNodes(oldNode, null);
166 List<RendererNode> result = rendererNodesReader();
167 assertNotNull(result);
168 assertTrue(result.size() == 1);
169 nodeManager.syncNodes(newNode, oldNode);
170 result = rendererNodesReader();
171 assertTrue(result.isEmpty());
175 public void testUpdateNode_fromConnectedToUnableToConnect() throws Exception {
176 Node oldNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
177 Node newNode = createNode(UnableToConnect, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
178 nodeManager.syncNodes(oldNode, null);
179 List<RendererNode> result = rendererNodesReader();
180 assertNotNull(result);
181 assertTrue(result.size() == 1);
182 nodeManager.syncNodes(newNode, oldNode);
183 result = rendererNodesReader();
184 assertTrue(result.isEmpty());
188 public void testUpdateNode_fromUnableToConnectToConnecting() throws Exception {
189 Node oldNode = createNode(UnableToConnect, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
190 Node newNode = createNode(Connecting, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
191 nodeManager.syncNodes(oldNode, null);
192 List<RendererNode> result = rendererNodesReader();
193 assertTrue(result.isEmpty());
194 nodeManager.syncNodes(newNode, oldNode);
195 result = rendererNodesReader();
196 assertTrue(result.isEmpty());
200 public void testUpdateNode_fromUnableToConnectToConnected() throws Exception {
201 Node oldNode = createNode(UnableToConnect, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
202 Node newNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
203 nodeManager.syncNodes(oldNode, null);
204 List<RendererNode> result = rendererNodesReader();
205 assertTrue(result.isEmpty());
206 nodeManager.syncNodes(newNode, oldNode);
207 result = rendererNodesReader();
208 assertNotNull(result);
209 assertTrue(result.size() == 1);
213 public void testUpdateNode_advancedCase() throws Exception {
214 Node oldNode = createNode(Connecting, IPv4_ADDRESS, NODE_NAME, Capabilities.Partial);
215 nodeManager.syncNodes(oldNode, null);
216 List<RendererNode> result = rendererNodesReader();
217 // One node is connecting, partial capabilities = empty list
218 assertTrue(result.isEmpty());
219 Node newNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Partial);
220 nodeManager.syncNodes(newNode, oldNode);
221 result = rendererNodesReader();
222 // Update 1.: node is connected, still partial capabilities = empty list
223 assertTrue(result.isEmpty());
225 newNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
226 nodeManager.syncNodes(newNode, oldNode);
227 result = rendererNodesReader();
228 // Update 2.: node is connected, full capabilities = 1 entry in list
229 assertNotNull(result);
230 assertTrue(result.size() == 1);
232 newNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.None);
233 nodeManager.syncNodes(newNode, oldNode);
234 result = rendererNodesReader();
235 // Update 3.: node remains connected, but without capabilities = empty list
236 assertTrue(result.isEmpty());
239 // Advanced update Case
242 public void testRemoveNode() throws Exception {
243 Node testNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
244 nodeManager.syncNodes(testNode, null);
245 List<RendererNode> result = rendererNodesReader();
246 assertNotNull(result);
247 assertTrue(result.size() == 1);
248 nodeManager.syncNodes(null, testNode);
249 result = rendererNodesReader();
250 assertTrue(result.isEmpty());
256 public void getNodeManagementIpByMountPointIid_absentNode() {
257 NodeId testNodeId = new NodeId(NODE_NAME);
258 InstanceIdentifier mountpointIid = InstanceIdentifier.builder(NetworkTopology.class)
259 .child(Topology.class, new TopologyKey(new TopologyId(TOPOLOGY_ID)))
260 .child(Node.class, new NodeKey(testNodeId)).build();
261 java.util.Optional<String> optionalIpAddress = nodeManager.getNodeManagementIpByMountPointIid(mountpointIid);
262 assertFalse(optionalIpAddress.isPresent());
266 public void getNodeManagementIpByMountPointIid_ipV4Case() throws Exception {
268 Node testNode = createNode(Connected, IPv4_ADDRESS, NODE_NAME, Capabilities.Full);
269 InstanceIdentifier<Node> testNodeIid = InstanceIdentifier.builder(NetworkTopology.class)
270 .child(Topology.class, new TopologyKey(new TopologyId(TOPOLOGY_ID)))
271 .child(Node.class, new NodeKey(testNode.getNodeId())).build();
272 WriteTransaction wTx = dataBroker.newWriteOnlyTransaction();
273 wTx.put(LogicalDatastoreType.CONFIGURATION, testNodeIid, testNode, true);
274 wTx.submit().checkedGet();
276 java.util.Optional<String> optionalResult = nodeManager.getNodeManagementIpByMountPointIid(testNodeIid);
277 assertTrue(optionalResult.isPresent());
278 assertEquals(IPv4_ADDRESS.getValue(), optionalResult.get());
281 private Node createNode(final NetconfNodeConnectionStatus.ConnectionStatus connectionStatus,
282 final Ipv4Address ipAddress,
283 final NodeId nodeName,
284 final Capabilities choice) {
285 AvailableCapabilities capabilities = null;
288 capabilities = emptyCapabilities();
292 capabilities = partialCapabilities();
296 capabilities = fullCapabilities();
300 NetconfNodeBuilder netconfNodeBuilder = new NetconfNodeBuilder();
301 netconfNodeBuilder.setConnectionStatus(connectionStatus)
302 .setAvailableCapabilities(capabilities)
303 .setHost(new Host(new IpAddress(ipAddress)));
305 NodeBuilder nodeBuilder = new NodeBuilder();
306 nodeBuilder.setNodeId(new NodeId(nodeName))
307 .setKey(new NodeKey(new NodeId(nodeName)))
308 .addAugmentation(NetconfNode.class, netconfNodeBuilder.build());
309 return nodeBuilder.build();
314 private List<RendererNode> rendererNodesReader() throws Exception {
315 InstanceIdentifier<Renderers> renderersIid =
316 InstanceIdentifier.builder(Renderers.class).build();
317 ReadWriteTransaction rwt = dataBroker.newReadWriteTransaction();
318 CheckedFuture<Optional<Renderers>, ReadFailedException> submitFuture =
319 rwt.read(LogicalDatastoreType.OPERATIONAL, renderersIid);
320 Optional<Renderers> optionalRenderers = submitFuture.checkedGet();
321 if (optionalRenderers.isPresent()) {
322 Renderers renderers = optionalRenderers.get();
323 if (renderers != null && renderers.getRenderer() != null && !renderers.getRenderer().isEmpty()) {
324 RendererNodes writtenNodes = renderers.getRenderer().get(0).getRendererNodes();
325 if (writtenNodes != null) {
326 return writtenNodes.getRendererNode();
330 return Collections.emptyList();
333 private AvailableCapabilities emptyCapabilities() {
334 AvailableCapabilitiesBuilder availableCapabilitiesBuilder = new AvailableCapabilitiesBuilder();
335 return availableCapabilitiesBuilder.build();
338 private AvailableCapabilities partialCapabilities() {
339 final String c1 = "(urn:ios?revision=2016-03-08)ned";
340 final String c2 = "(http://tail-f.com/yang/common?revision=2015-05-22)tailf-common";
341 final String c3 = "(http://tail-f.com/yang/common?revision=2015-03-19)tailf-cli-extensions";
342 String[] capabilityList = {c1, c2, c3};
343 AvailableCapabilitiesBuilder availableCapabilitiesBuilder = new AvailableCapabilitiesBuilder();
344 availableCapabilitiesBuilder.setAvailableCapability(Arrays.asList(capabilityList));
345 return availableCapabilitiesBuilder.build();
348 private AvailableCapabilities fullCapabilities() {
349 final String c1 = "(urn:ios?revision=2016-03-08)ned";
350 final String c2 = "(http://tail-f.com/yang/common?revision=2015-05-22)tailf-common";
351 final String c3 = "(http://tail-f.com/yang/common?revision=2015-03-19)tailf-cli-extensions";
352 final String c4 = "(http://tail-f.com/yang/common?revision=2013-11-07)tailf-meta-extensions";
353 final String c5 = "(urn:ietf:params:xml:ns:yang:ietf-yang-types?revision=2013-07-15)ietf-yang-types";
354 final String c6 = "(urn:ietf:params:xml:ns:yang:ietf-inet-types?revision=2013-07-15)ietf-inet-types";
355 String[] capabilityList = {c1, c2, c3, c4, c5, c6};
356 AvailableCapabilitiesBuilder availableCapabilitiesBuilder = new AvailableCapabilitiesBuilder();
357 availableCapabilitiesBuilder.setAvailableCapability(Arrays.asList(capabilityList));
358 return availableCapabilitiesBuilder.build();
361 private enum Capabilities {None, Partial, Full}