2 * Copyright (c) 2016 Red Hat, 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.netvirt.utils.netvirt.it.utils;
11 import java.io.IOException;
12 import java.util.HashMap;
14 import java.util.UUID;
16 import com.google.common.collect.Maps;
17 import org.junit.Assert;
18 import org.opendaylight.netvirt.openstack.netvirt.translator.NeutronNetwork;
19 import org.opendaylight.netvirt.openstack.netvirt.translator.NeutronPort;
20 import org.opendaylight.netvirt.openstack.netvirt.translator.NeutronSecurityGroup;
21 import org.opendaylight.netvirt.openstack.netvirt.translator.NeutronSubnet;
22 import org.opendaylight.netvirt.utils.neutron.utils.NeutronUtils;
23 import org.opendaylight.ovsdb.utils.southbound.utils.SouthboundUtils;
24 import org.opendaylight.yang.gen.v1.urn.tbd.params.xml.ns.yang.network.topology.rev131021.network.topology.topology.Node;
27 * A utility class used in integration tests that need to create neutron networks with some ports.
28 * Please see NetvirtIT#testNeutronNet for an example of how this class is used
30 public class NeutronNetItUtil {
32 public final String tenantId;
33 public final String id;
34 public final String subnetId;
35 public NeutronNetwork neutronNetwork;
36 public NeutronSubnet neutronSubnet;
37 public String segId = "100";
42 public SouthboundUtils southboundUtils;
43 public NeutronUtils neutronUtils;
46 * Information about a port created using createPort() - fields should be pretty self explanatory
48 public class PortInfo {
49 public PortInfo(String name, long ofPort) {
52 this.ip = ipFor(ofPort);
53 this.mac = macFor(ofPort);
57 public NeutronPort neutronPort;
64 * Maps port names (the ones you pass in to createPort() to their PortInfo objects
66 public Map<String, PortInfo> portInfoByName = new HashMap<String, PortInfo>();
69 * Construct a new NeutronNetItUtil.
70 * @param southboundUtils used to create termination points
71 * @param tenantId tenant ID
73 public NeutronNetItUtil(SouthboundUtils southboundUtils, String tenantId) {
74 this(southboundUtils, tenantId, "101", "f4:00:00:0f:00:", "10.0.0.", "10.0.0.0/24");
78 * Construct a new NeutronNetItUtil.
79 * @param southboundUtils used to create termination points
80 * @param tenantId tenant ID
81 * @param segId the segmentation id to use for the neutron network
82 * @param macPfx the first characters of the mac addresses generated for ports. Format is "f7:00:00:0f:00:"
83 * @param ipPfx the first characters of the ip addresses generated for ports. Format is "10.0.0."
84 * @param cidr the cidr for this network, e.g., "10.0.0.0/24"
86 public NeutronNetItUtil(SouthboundUtils southboundUtils, String tenantId,
87 String segId, String macPfx, String ipPfx, String cidr) {
88 this.tenantId = tenantId;
94 this.id = UUID.randomUUID().toString();
95 this.subnetId = UUID.randomUUID().toString();
97 this.southboundUtils = southboundUtils;
98 neutronUtils = new NeutronUtils();
99 neutronNetwork = null;
100 neutronSubnet = null;
104 * Create the network and subnet.
106 public void create() {
107 neutronNetwork = neutronUtils.createNeutronNetwork(id, tenantId, "vxlan", segId);
108 neutronSubnet = neutronUtils.createNeutronSubnet(subnetId, tenantId, id, "10.0.0.0/24");
112 * Clean up all created neutron objects.
114 public void destroy() {
115 for (PortInfo portInfo : portInfoByName.values()) {
116 neutronUtils.removeNeutronPort(portInfo.neutronPort.getID());
118 //TODO: probably more polite to clean up everything else as well...
119 //TODO: for now just assume that the docker image will be recreated
120 //TODO: before each test
121 portInfoByName.clear();
123 if (neutronSubnet != null) {
124 neutronUtils.removeNeutronSubnet(neutronSubnet.getID());
125 neutronSubnet = null;
128 if (neutronNetwork != null) {
129 neutronUtils.removeNeutronNetwork(neutronNetwork.getID());
130 neutronNetwork = null;
135 * Create a port on the network. The deviceOwner will be set to "compute:None".
136 * @param bridge bridge where the port will be created on OVS
137 * @param portName name for this port
138 * @throws InterruptedException if we're interrupted while waiting for objects to be created
140 public void createPort(Node bridge, String portName) throws InterruptedException, IOException {
141 createPort(bridge, portName, "compute:None");
145 * Create a port on the network. The deviceOwner will be set to "compute:None".
146 * @param bridge bridge where the port will be created on OVS
147 * @param portName name for this port
148 * @param owner deviceOwner, e.g., "network:dhcp"
149 * @param secGroups Optional NeutronSecurityGroup objects see NeutronUtils.createNeutronSecurityGroup()
150 * @throws InterruptedException if we're interrupted while waiting for objects to be created
152 public void createPort(Node bridge, String portName, String owner, NeutronSecurityGroup... secGroups)
153 throws InterruptedException, IOException {
154 PortInfo portInfo = buildPortInfo(portName);
155 doCreatePort(bridge, portInfo, owner, "internal", secGroups);
158 protected PortInfo buildPortInfo(String portName) {
159 Assert.assertFalse("Can't have two ports with the same name", portInfoByName.containsKey(portName));
161 long idx = portInfoByName.size() + 1;
162 Assert.assertTrue(idx < 256);
163 return new PortInfo(portName, idx);
166 protected void doCreatePort(Node bridge, PortInfo portInfo, String owner,
167 String portType, NeutronSecurityGroup ... secGroups) throws InterruptedException {
169 String portId = UUID.randomUUID().toString();
170 portInfo.neutronPort = neutronUtils.createNeutronPort(
171 id, subnetId, portId, owner, portInfo.ip, portInfo.mac, secGroups);
173 //TBD: Use NotifyingDataChangeListener
176 Map<String, String> externalIds = Maps.newHashMap();
177 externalIds.put("attached-mac", portInfo.mac);
178 externalIds.put("iface-id", portId);
179 southboundUtils.addTerminationPoint(bridge, portInfo.name, portType, null, externalIds, portInfo.ofPort);
181 portInfoByName.put(portInfo.name, portInfo);
185 * Get the mac address for the n'th port created on this network (starts at 1).
186 * @param portNum index of port created
187 * @return the mac address
189 public String macFor(long portNum) {
190 return macPfx + String.format("%02x", 5 - portNum);
194 * Get the ip address for the n'th port created on this network (starts at 1).
195 * @param portNum index of port created
196 * @return the mac address
198 public String ipFor(long portNum) {
199 return ipPfx + portNum;