Jonathan Hart
Committed by Gerrit Code Review

Unit tests for InterfaceManager

Change-Id: I01ed7a562255a2b46c26f36bc24bec937ec89a70
/*
* Copyright 2015 Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.onosproject.incubator.net.intf.impl;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import org.junit.Before;
import org.junit.Test;
import org.onlab.packet.Ip4Address;
import org.onlab.packet.IpAddress;
import org.onlab.packet.MacAddress;
import org.onlab.packet.VlanId;
import org.onosproject.incubator.net.config.basics.ConfigException;
import org.onosproject.incubator.net.config.basics.InterfaceConfig;
import org.onosproject.incubator.net.intf.Interface;
import org.onosproject.net.ConnectPoint;
import org.onosproject.net.config.Config;
import org.onosproject.net.config.NetworkConfigEvent;
import org.onosproject.net.config.NetworkConfigListener;
import org.onosproject.net.config.NetworkConfigServiceAdapter;
import org.onosproject.net.host.InterfaceIpAddress;
import java.util.Collections;
import java.util.Map;
import java.util.Set;
import static junit.framework.TestCase.assertEquals;
import static org.junit.Assert.assertNull;
/**
* Unit tests for InterfaceManager.
*/
public class InterfaceManagerTest {
private static final Class<InterfaceConfig> CONFIG_CLASS = InterfaceConfig.class;
private static final int NUM_INTERFACES = 4;
private Set<ConnectPoint> subjects = Sets.newHashSet();
private Map<ConnectPoint, InterfaceConfig> configs = Maps.newHashMap();
private Set<Interface> interfaces = Sets.newHashSet();
private NetworkConfigListener listener;
private InterfaceManager interfaceManager;
@Before
public void setUp() throws Exception {
for (int i = 0; i < NUM_INTERFACES; i++) {
ConnectPoint cp = createConnectPoint(i);
subjects.add(cp);
Interface intf = createInterface(i);
interfaces.add(intf);
InterfaceConfig ic = new TestInterfaceConfig(cp, Sets.newHashSet(intf));
configs.put(cp, ic);
}
TestNetworkConfigService configService =
new TestNetworkConfigService(subjects, configs);
interfaceManager = new InterfaceManager();
interfaceManager.configService = configService;
interfaceManager.activate();
}
private Interface createInterface(int i) {
ConnectPoint cp = createConnectPoint(i);
InterfaceIpAddress ia = InterfaceIpAddress.valueOf("192.168." + i + ".1/24");
Interface intf = new Interface(cp,
Sets.newHashSet(ia),
MacAddress.valueOf(i),
VlanId.vlanId((short) i));
return intf;
}
private ConnectPoint createConnectPoint(int i) {
return ConnectPoint.deviceConnectPoint("of:000000000000000" + i + "/1");
}
@Test
public void testGetInterfaces() throws Exception {
assertEquals(interfaces, interfaceManager.getInterfaces());
}
@Test
public void testGetInterfacesByPort() throws Exception {
ConnectPoint cp = ConnectPoint.deviceConnectPoint("of:0000000000000001/1");
Set<Interface> byPort = Collections.singleton(createInterface(1));
assertEquals(byPort, interfaceManager.getInterfacesByPort(cp));
}
@Test
public void testGetInterfacesByIp() throws Exception {
IpAddress ip = Ip4Address.valueOf("192.168.2.1");
Set<Interface> byIp = Collections.singleton(createInterface(2));
assertEquals(byIp, interfaceManager.getInterfacesByIp(ip));
}
@Test
public void testGetMatchingInterface() throws Exception {
IpAddress ip = Ip4Address.valueOf("192.168.1.100");
Interface matchingIntf = createInterface(1);
assertEquals(matchingIntf, interfaceManager.getMatchingInterface(ip));
// Searching for an IP with no match should return null
ip = Ip4Address.valueOf("1.1.1.1");
assertNull(interfaceManager.getMatchingInterface(ip));
}
@Test
public void testGetInterfacesByVlan() throws Exception {
VlanId vlanId = VlanId.vlanId((short) 1);
Set<Interface> byVlan = Collections.singleton(createInterface(1));
assertEquals(byVlan, interfaceManager.getInterfacesByVlan(vlanId));
}
@Test
public void testAddInterface() throws Exception {
// Create a new InterfaceConfig which will get added
VlanId vlanId = VlanId.vlanId((short) 1);
ConnectPoint cp = ConnectPoint.deviceConnectPoint("of:0000000000000001/2");
Interface newIntf = new Interface(cp,
Collections.emptySet(),
MacAddress.valueOf(100),
vlanId);
InterfaceConfig ic = new TestInterfaceConfig(cp, Collections.singleton(newIntf));
subjects.add(cp);
configs.put(cp, ic);
interfaces.add(newIntf);
NetworkConfigEvent event = new NetworkConfigEvent(
NetworkConfigEvent.Type.CONFIG_ADDED, cp, CONFIG_CLASS);
assertEquals(NUM_INTERFACES, interfaceManager.getInterfaces().size());
// Send in a config event containing a new interface config
listener.event(event);
// Check the new interface exists in the InterfaceManager's inventory
assertEquals(interfaces, interfaceManager.getInterfaces());
assertEquals(NUM_INTERFACES + 1, interfaceManager.getInterfaces().size());
// There are now two interfaces with vlan ID 1
Set<Interface> byVlan = Sets.newHashSet(createInterface(1), newIntf);
assertEquals(byVlan, interfaceManager.getInterfacesByVlan(vlanId));
}
@Test
public void testUpdateInterface() throws Exception {
ConnectPoint cp = createConnectPoint(1);
// Create an interface that is the same as the existing one, but adds a
// new IP address
Interface intf = createInterface(1);
Set<InterfaceIpAddress> addresses = Sets.newHashSet(intf.ipAddresses());
addresses.add(InterfaceIpAddress.valueOf("192.168.100.1/24"));
intf = new Interface(intf.connectPoint(), addresses, intf.mac(), intf.vlan());
// Create a new interface on the same connect point as the existing one
InterfaceIpAddress newAddr = InterfaceIpAddress.valueOf("192.168.101.1/24");
Interface newIntf = new Interface(cp,
Collections.singleton(newAddr),
MacAddress.valueOf(101),
VlanId.vlanId((short) 101));
Set<Interface> interfaces = Sets.newHashSet(intf, newIntf);
// New interface config updates the existing interface and adds a new
// interface to the same connect point
InterfaceConfig ic = new TestInterfaceConfig(cp, interfaces);
configs.put(cp, ic);
NetworkConfigEvent event = new NetworkConfigEvent(
NetworkConfigEvent.Type.CONFIG_UPDATED, cp, CONFIG_CLASS);
// Send in the event signalling the interfaces for this connect point
// have been updated
listener.event(event);
assertEquals(NUM_INTERFACES + 1, interfaceManager.getInterfaces().size());
assertEquals(interfaces, interfaceManager.getInterfacesByPort(cp));
}
@Test
public void testRemoveInterface() throws Exception {
ConnectPoint cp = createConnectPoint(1);
NetworkConfigEvent event = new NetworkConfigEvent(
NetworkConfigEvent.Type.CONFIG_REMOVED, cp, CONFIG_CLASS);
assertEquals(NUM_INTERFACES, interfaceManager.getInterfaces().size());
// Send in a config event removing an interface config
listener.event(event);
assertEquals(NUM_INTERFACES - 1, interfaceManager.getInterfaces().size());
}
/**
* Test version of NetworkConfigService which allows us to pass in subjects
* and InterfaceConfigs directly.
*/
private class TestNetworkConfigService extends NetworkConfigServiceAdapter {
private final Set<ConnectPoint> subjects;
private final Map<ConnectPoint, InterfaceConfig> configs;
public TestNetworkConfigService(Set<ConnectPoint> subjects,
Map<ConnectPoint, InterfaceConfig> configs) {
this.subjects = subjects;
this.configs = configs;
}
@Override
public <S, C extends Config<S>> Set<S> getSubjects(Class<S> subjectClass,
Class<C> configClass) {
return (Set<S>) subjects;
}
@Override
public <S, C extends Config<S>> C getConfig(S subject, Class<C> configClass) {
return (C) configs.get(subject);
}
@Override
public void addListener(NetworkConfigListener listener) {
InterfaceManagerTest.this.listener = listener;
}
}
/**
* Test version of InterfaceConfig where we can inject interfaces directly,
* rather than parsing them from JSON.
*/
private class TestInterfaceConfig extends InterfaceConfig {
private final ConnectPoint subject;
private final Set<Interface> interfaces;
@Override
public ConnectPoint subject() {
return subject;
}
public TestInterfaceConfig(ConnectPoint subject, Set<Interface> interfaces) {
this.subject = subject;
this.interfaces = interfaces;
}
@Override
public Set<Interface> getInterfaces() throws ConfigException {
return interfaces;
}
}
}