blob: fe2a8638fd75e1dc8383ddc3000b03c285e76d1f [file] [log] [blame]
Jonathan Hartaa380972014-04-03 10:24:46 -07001package net.onrc.onos.core.intent.runtime;
Toshio Koidec87810e2014-02-11 13:03:21 -08002
Toshio Koide066506e2014-02-20 19:52:09 -08003import static org.easymock.EasyMock.*;
4
Pavlin Radoslavov74986ce2014-02-20 13:17:20 -08005import java.util.LinkedList;
Brian O'Connor12861f72014-02-19 20:40:32 -08006import java.util.List;
7import java.util.Set;
8
Toshio Koide27ffd412014-02-18 19:15:27 -08009import net.floodlightcontroller.core.module.FloodlightModuleContext;
10import net.floodlightcontroller.core.module.FloodlightModuleException;
Jonathan Hart6df90172014-04-03 10:13:11 -070011import net.onrc.onos.core.datagrid.IDatagridService;
12import net.onrc.onos.core.datagrid.IEventChannel;
13import net.onrc.onos.core.datagrid.IEventChannelListener;
Jonathan Hartaa380972014-04-03 10:24:46 -070014import net.onrc.onos.core.intent.ConstrainedShortestPathIntent;
15import net.onrc.onos.core.intent.FlowEntry;
16import net.onrc.onos.core.intent.Intent;
17import net.onrc.onos.core.intent.IntentOperationList;
18import net.onrc.onos.core.intent.MockNetworkGraph;
19import net.onrc.onos.core.intent.PathIntent;
20import net.onrc.onos.core.intent.PathIntentMap;
21import net.onrc.onos.core.intent.ShortestPathIntent;
22import net.onrc.onos.core.intent.Intent.IntentState;
23import net.onrc.onos.core.intent.IntentOperation.Operator;
24import net.onrc.onos.core.intent.runtime.IntentStateList;
25import net.onrc.onos.core.intent.runtime.PathCalcRuntimeModule;
26import net.onrc.onos.core.intent.runtime.PersistIntent;
27import net.onrc.onos.core.intent.runtime.PlanCalcRuntime;
Jonathan Hartdeda0ba2014-04-03 11:14:12 -070028import net.onrc.onos.core.registry.IControllerRegistryService;
Jonathan Hart472062d2014-04-03 10:56:48 -070029import net.onrc.onos.core.topology.DeviceEvent;
30import net.onrc.onos.core.topology.INetworkGraphListener;
31import net.onrc.onos.core.topology.INetworkGraphService;
32import net.onrc.onos.core.topology.LinkEvent;
33import net.onrc.onos.core.topology.NetworkGraph;
34import net.onrc.onos.core.topology.PortEvent;
35import net.onrc.onos.core.topology.SwitchEvent;
Toshio Koidec87810e2014-02-11 13:03:21 -080036
37import org.junit.After;
38import org.junit.Before;
39import org.junit.Test;
Nick Karanatsios8abe7172014-02-19 20:31:48 -080040import org.junit.runner.RunWith;
41import org.powermock.api.easymock.PowerMock;
42import org.powermock.core.classloader.annotations.PrepareForTest;
43import org.powermock.modules.junit4.PowerMockRunner;
Toshio Koidec87810e2014-02-11 13:03:21 -080044
45/**
46 * @author Toshio Koide (t-koide@onlab.us)
47 */
Nick Karanatsios8abe7172014-02-19 20:31:48 -080048@RunWith(PowerMockRunner.class)
49@PrepareForTest(PathCalcRuntimeModule.class)
Toshio Koidec87810e2014-02-11 13:03:21 -080050public class UseCaseTest {
Toshio Koide27ffd412014-02-18 19:15:27 -080051 private NetworkGraph g;
52 private FloodlightModuleContext modContext;
53 private IDatagridService datagridService;
54 private INetworkGraphService networkGraphService;
Toshio Koide798bc1b2014-02-20 14:02:40 -080055 private IControllerRegistryService controllerRegistryService;
56 private PersistIntent persistIntent;
Toshio Koide27ffd412014-02-18 19:15:27 -080057 @SuppressWarnings("rawtypes")
58 private IEventChannel eventChannel;
Toshio Koidec87810e2014-02-11 13:03:21 -080059
Toshio Koidefe1d5d92014-02-26 20:09:48 -080060 private static Long LOCAL_PORT = 0xFFFEL;
61
Toshio Koide27ffd412014-02-18 19:15:27 -080062 @SuppressWarnings("unchecked")
Toshio Koidec87810e2014-02-11 13:03:21 -080063 @Before
Nick Karanatsios8abe7172014-02-19 20:31:48 -080064 public void setUp() throws Exception {
Toshio Koideebdbb622014-02-12 20:28:38 -080065 MockNetworkGraph graph = new MockNetworkGraph();
Toshio Koidefe1d5d92014-02-26 20:09:48 -080066 graph.createSampleTopology1();
Toshio Koideebdbb622014-02-12 20:28:38 -080067 g = graph;
Toshio Koide27ffd412014-02-18 19:15:27 -080068
Toshio Koide066506e2014-02-20 19:52:09 -080069 datagridService = createMock(IDatagridService.class);
70 networkGraphService = createMock(INetworkGraphService.class);
71 controllerRegistryService = createMock(IControllerRegistryService.class);
72 modContext = createMock(FloodlightModuleContext.class);
73 eventChannel = createMock(IEventChannel.class);
Toshio Koide798bc1b2014-02-20 14:02:40 -080074 persistIntent = PowerMock.createMock(PersistIntent.class);
75
76 PowerMock.expectNew(PersistIntent.class,
Toshio Koide066506e2014-02-20 19:52:09 -080077 anyObject(IControllerRegistryService.class),
78 anyObject(INetworkGraphService.class)).andReturn(persistIntent);
Toshio Koide27ffd412014-02-18 19:15:27 -080079
Toshio Koide066506e2014-02-20 19:52:09 -080080 expect(modContext.getServiceImpl(IDatagridService.class))
Toshio Koide27ffd412014-02-18 19:15:27 -080081 .andReturn(datagridService).once();
Toshio Koide066506e2014-02-20 19:52:09 -080082 expect(modContext.getServiceImpl(INetworkGraphService.class))
Toshio Koide27ffd412014-02-18 19:15:27 -080083 .andReturn(networkGraphService).once();
Toshio Koide066506e2014-02-20 19:52:09 -080084 expect(modContext.getServiceImpl(IControllerRegistryService.class))
Toshio Koide798bc1b2014-02-20 14:02:40 -080085 .andReturn(controllerRegistryService).once();
Toshio Koide066506e2014-02-20 19:52:09 -080086 expect(persistIntent.getKey()).andReturn(1L).anyTimes();
87 expect(persistIntent.persistIfLeader(eq(1L),
88 anyObject(IntentOperationList.class))).andReturn(true).anyTimes();
Toshio Koide0c9106d2014-02-19 15:26:38 -080089
Toshio Koide066506e2014-02-20 19:52:09 -080090 expect(networkGraphService.getNetworkGraph()).andReturn(g).anyTimes();
91 networkGraphService.registerNetworkGraphListener(anyObject(INetworkGraphListener.class));
92 expectLastCall();
Toshio Koide0c9106d2014-02-19 15:26:38 -080093
Toshio Koide066506e2014-02-20 19:52:09 -080094 expect(datagridService.createChannel("onos.pathintent", Long.class, IntentOperationList.class))
Toshio Koide27ffd412014-02-18 19:15:27 -080095 .andReturn(eventChannel).once();
96
Toshio Koide066506e2014-02-20 19:52:09 -080097 expect(datagridService.addListener(
98 eq("onos.pathintent_state"),
99 anyObject(IEventChannelListener.class),
100 eq(Long.class),
101 eq(IntentStateList.class)))
102 .andReturn(eventChannel).once();
103
104 replay(datagridService);
105 replay(networkGraphService);
106 replay(modContext);
107 replay(controllerRegistryService);
Toshio Koide798bc1b2014-02-20 14:02:40 -0800108 PowerMock.replay(persistIntent, PersistIntent.class);
Toshio Koidec87810e2014-02-11 13:03:21 -0800109 }
110
111 @After
112 public void tearDown() {
Toshio Koide066506e2014-02-20 19:52:09 -0800113 verify(datagridService);
114 verify(networkGraphService);
115 verify(modContext);
116 verify(controllerRegistryService);
Toshio Koide798bc1b2014-02-20 14:02:40 -0800117 PowerMock.verify(persistIntent, PersistIntent.class);
Toshio Koidec87810e2014-02-11 13:03:21 -0800118 }
119
Toshio Koide4f308732014-02-18 15:19:48 -0800120 private void showResult(PathIntentMap intents) {
121 for (Intent intent: intents.getAllIntents()) {
122 PathIntent pathIntent = (PathIntent)intent;
Toshio Koidebf875662014-02-24 12:19:15 -0800123 System.out.println("Path intent:" + pathIntent);
Toshio Koidec87810e2014-02-11 13:03:21 -0800124 System.out.println("Parent intent: " + pathIntent.getParentIntent().toString());
Toshio Koidec87810e2014-02-11 13:03:21 -0800125 }
126 }
127
128 @Test
Toshio Koide0c9106d2014-02-19 15:26:38 -0800129 public void createShortestPaths() throws FloodlightModuleException {
Toshio Koidec87810e2014-02-11 13:03:21 -0800130 // create shortest path intents
Toshio Koide27ffd412014-02-18 19:15:27 -0800131 IntentOperationList opList = new IntentOperationList();
Toshio Koidefe1d5d92014-02-26 20:09:48 -0800132 opList.add(Operator.ADD, new ShortestPathIntent("1", 1L, 12L, LOCAL_PORT, 2L, 21L, LOCAL_PORT));
133 opList.add(Operator.ADD, new ShortestPathIntent("2", 1L, 14L, LOCAL_PORT, 4L, 41L, LOCAL_PORT));
134 opList.add(Operator.ADD, new ShortestPathIntent("3", 2L, 23L, LOCAL_PORT, 3L, 32L, LOCAL_PORT));
Toshio Koidec87810e2014-02-11 13:03:21 -0800135
Toshio Koide27ffd412014-02-18 19:15:27 -0800136 // compile high-level intent operations into low-level intent operations (calculate paths)
137 PathCalcRuntimeModule runtime1 = new PathCalcRuntimeModule();
138 runtime1.init(modContext);
139 runtime1.startUp(modContext);
140 IntentOperationList pathIntentOpList = runtime1.executeIntentOperations(opList);
141
Brian O'Connor7f8e3012014-02-15 23:59:29 -0800142 // compile low-level intents into flow entry installation plan
Brian O'Connor488e5ed2014-02-20 19:50:01 -0800143 PlanCalcRuntime runtime2 = new PlanCalcRuntime();
Brian O'Connor12861f72014-02-19 20:40:32 -0800144 List<Set<FlowEntry>> plan = runtime2.computePlan(pathIntentOpList);
Toshio Koidec87810e2014-02-11 13:03:21 -0800145
146 // show results
Toshio Koide27ffd412014-02-18 19:15:27 -0800147 showResult((PathIntentMap) runtime1.getPathIntents());
Brian O'Connor12861f72014-02-19 20:40:32 -0800148 System.out.println(plan);
Toshio Koidec87810e2014-02-11 13:03:21 -0800149 }
150
151 @Test
Toshio Koide0c9106d2014-02-19 15:26:38 -0800152 public void createConstrainedShortestPaths() throws FloodlightModuleException {
Toshio Koidec87810e2014-02-11 13:03:21 -0800153 // create constrained shortest path intents
Toshio Koide27ffd412014-02-18 19:15:27 -0800154 IntentOperationList opList = new IntentOperationList();
Toshio Koidefe1d5d92014-02-26 20:09:48 -0800155 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("1", 1L, 12L, LOCAL_PORT, 2L, 21L, LOCAL_PORT, 400.0));
156 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("2", 1L, 14L, LOCAL_PORT, 4L, 41L, LOCAL_PORT, 400.0));
157 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("3", 2L, 24L, LOCAL_PORT, 4L, 42L, LOCAL_PORT, 400.0));
158 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("4", 2L, 23L, LOCAL_PORT, 3L, 32L, LOCAL_PORT, 400.0));
159 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("5", 3L, 34L, LOCAL_PORT, 4L, 43L, LOCAL_PORT, 400.0));
Toshio Koidec87810e2014-02-11 13:03:21 -0800160
Toshio Koide27ffd412014-02-18 19:15:27 -0800161 // compile high-level intent operations into low-level intent operations (calculate paths)
162 PathCalcRuntimeModule runtime1 = new PathCalcRuntimeModule();
163 runtime1.init(modContext);
164 runtime1.startUp(modContext);
165 IntentOperationList pathIntentOpList = runtime1.executeIntentOperations(opList);
Toshio Koidec87810e2014-02-11 13:03:21 -0800166
Brian O'Connor7f8e3012014-02-15 23:59:29 -0800167 // compile low-level intents into flow entry installation plan
Brian O'Connor488e5ed2014-02-20 19:50:01 -0800168 PlanCalcRuntime runtime2 = new PlanCalcRuntime();
Brian O'Connor12861f72014-02-19 20:40:32 -0800169 List<Set<FlowEntry>> plan = runtime2.computePlan(pathIntentOpList);
Brian O'Connor7f8e3012014-02-15 23:59:29 -0800170
Toshio Koidec87810e2014-02-11 13:03:21 -0800171 // show results
Toshio Koide27ffd412014-02-18 19:15:27 -0800172 showResult((PathIntentMap) runtime1.getPathIntents());
Brian O'Connor12861f72014-02-19 20:40:32 -0800173 System.out.println(plan);
Toshio Koidec87810e2014-02-11 13:03:21 -0800174 }
175
176 @Test
Toshio Koide0c9106d2014-02-19 15:26:38 -0800177 public void createMixedShortestPaths() throws FloodlightModuleException {
178 // create constrained & best effort shortest path intents
Toshio Koide27ffd412014-02-18 19:15:27 -0800179 IntentOperationList opList = new IntentOperationList();
Toshio Koidefe1d5d92014-02-26 20:09:48 -0800180 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("1", 1L, 12L, LOCAL_PORT, 2L, 21L, LOCAL_PORT, 400.0));
181 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("2", 1L, 14L, LOCAL_PORT, 4L, 41L, LOCAL_PORT, 400.0));
182 opList.add(Operator.ADD, new ShortestPathIntent("3", 2L, 24L, LOCAL_PORT, 4L, 42L, LOCAL_PORT));
183 opList.add(Operator.ADD, new ShortestPathIntent("4", 2L, 23L, LOCAL_PORT, 3L, 32L, LOCAL_PORT));
184 opList.add(Operator.ADD, new ConstrainedShortestPathIntent("5", 3L, 34L, LOCAL_PORT, 4L, 43L, LOCAL_PORT, 400.0));
Toshio Koidec87810e2014-02-11 13:03:21 -0800185
Toshio Koide27ffd412014-02-18 19:15:27 -0800186 // compile high-level intent operations into low-level intent operations (calculate paths)
187 PathCalcRuntimeModule runtime1 = new PathCalcRuntimeModule();
188 runtime1.init(modContext);
189 runtime1.startUp(modContext);
190 IntentOperationList pathIntentOpList = runtime1.executeIntentOperations(opList);
Toshio Koidec87810e2014-02-11 13:03:21 -0800191
Brian O'Connor7f8e3012014-02-15 23:59:29 -0800192 // compile low-level intents into flow entry installation plan
Brian O'Connor488e5ed2014-02-20 19:50:01 -0800193 PlanCalcRuntime runtime2 = new PlanCalcRuntime();
Brian O'Connor12861f72014-02-19 20:40:32 -0800194 List<Set<FlowEntry>> plan = runtime2.computePlan(pathIntentOpList);
Brian O'Connor7f8e3012014-02-15 23:59:29 -0800195
Toshio Koidec87810e2014-02-11 13:03:21 -0800196 // show results
Toshio Koide27ffd412014-02-18 19:15:27 -0800197 showResult((PathIntentMap) runtime1.getPathIntents());
Brian O'Connor12861f72014-02-19 20:40:32 -0800198 System.out.println(plan);
Toshio Koidec87810e2014-02-11 13:03:21 -0800199 }
Toshio Koided9fa2a82014-02-19 17:35:18 -0800200
Toshio Koide0c9106d2014-02-19 15:26:38 -0800201 @Test
202 public void rerouteShortestPaths() throws FloodlightModuleException {
Pavlin Radoslavov74986ce2014-02-20 13:17:20 -0800203 List<SwitchEvent> addedSwitchEvents = new LinkedList<>();
204 List<SwitchEvent> removedSwitchEvents = new LinkedList<>();
205 List<PortEvent> addedPortEvents = new LinkedList<>();
206 List<PortEvent> removedPortEvents = new LinkedList<>();
207 List<LinkEvent> addedLinkEvents = new LinkedList<>();
208 List<LinkEvent> removedLinkEvents = new LinkedList<>();
209 List<DeviceEvent> addedDeviceEvents = new LinkedList<>();
210 List<DeviceEvent> removedDeviceEvents = new LinkedList<>();
211
Toshio Koide0c9106d2014-02-19 15:26:38 -0800212 // create shortest path intents
213 IntentOperationList opList = new IntentOperationList();
Toshio Koidefe1d5d92014-02-26 20:09:48 -0800214 opList.add(Operator.ADD, new ShortestPathIntent("1", 1L, 12L, LOCAL_PORT, 2L, 21L, LOCAL_PORT));
215 opList.add(Operator.ADD, new ShortestPathIntent("2", 1L, 14L, LOCAL_PORT, 4L, 41L, LOCAL_PORT));
216 opList.add(Operator.ADD, new ShortestPathIntent("3", 2L, 23L, LOCAL_PORT, 3L, 32L, LOCAL_PORT));
Toshio Koide0c9106d2014-02-19 15:26:38 -0800217
218 // compile high-level intent operations into low-level intent operations (calculate paths)
219 PathCalcRuntimeModule runtime1 = new PathCalcRuntimeModule();
220 runtime1.init(modContext);
221 runtime1.startUp(modContext);
222 IntentOperationList pathIntentOpList = runtime1.executeIntentOperations(opList);
223
224 // compile low-level intents into flow entry installation plan
Brian O'Connor488e5ed2014-02-20 19:50:01 -0800225 PlanCalcRuntime runtime2 = new PlanCalcRuntime();
Brian O'Connor12861f72014-02-19 20:40:32 -0800226 List<Set<FlowEntry>> plan = runtime2.computePlan(pathIntentOpList);
Toshio Koide0c9106d2014-02-19 15:26:38 -0800227
228 // show results step1
229 showResult((PathIntentMap) runtime1.getPathIntents());
Brian O'Connor12861f72014-02-19 20:40:32 -0800230 System.out.println(plan);
Toshio Koide0c9106d2014-02-19 15:26:38 -0800231
Toshio Koidea10c0372014-02-20 17:28:10 -0800232 // TODO this state changes should be triggered by notification of plan module
Toshio Koide066506e2014-02-20 19:52:09 -0800233 IntentStateList states = new IntentStateList();
Toshio Koidea10c0372014-02-20 17:28:10 -0800234 states.put("1", IntentState.INST_ACK);
235 states.put("2", IntentState.INST_ACK);
236 states.put("3", IntentState.INST_ACK);
237 runtime1.getHighLevelIntents().changeStates(states);
Toshio Koidebf875662014-02-24 12:19:15 -0800238 states.clear();
239 states.put("1___0", IntentState.INST_ACK);
240 states.put("2___0", IntentState.INST_ACK);
241 states.put("3___0", IntentState.INST_ACK);
242 runtime1.getPathIntents().changeStates(states);
Toshio Koidea10c0372014-02-20 17:28:10 -0800243
Toshio Koide0c9106d2014-02-19 15:26:38 -0800244 // link down
Toshio Koidefe1d5d92014-02-26 20:09:48 -0800245 ((MockNetworkGraph)g).removeLink(1L, 12L, 2L, 21L); // This link is used by the intent "1"
246 ((MockNetworkGraph)g).removeLink(2L, 21L, 1L, 12L);
247 LinkEvent linkEvent1 = new LinkEvent(1L, 12L, 2L, 21L);
248 LinkEvent linkEvent2 = new LinkEvent(2L, 21L, 1L, 12L);
Pavlin Radoslavov74986ce2014-02-20 13:17:20 -0800249 removedLinkEvents.clear();
Toshio Koidea10c0372014-02-20 17:28:10 -0800250 removedLinkEvents.add(linkEvent1);
251 removedLinkEvents.add(linkEvent2);
Toshio Koide798bc1b2014-02-20 14:02:40 -0800252 runtime1.networkGraphEvents(
253 addedSwitchEvents,
254 removedSwitchEvents,
255 addedPortEvents,
256 removedPortEvents,
257 addedLinkEvents,
258 removedLinkEvents,
259 addedDeviceEvents,
260 removedDeviceEvents);
Toshio Koide0c9106d2014-02-19 15:26:38 -0800261 System.out.println("Link goes down.");
262
263 // show results step2
264 showResult((PathIntentMap) runtime1.getPathIntents());
Brian O'Connor12861f72014-02-19 20:40:32 -0800265 // TODO: show results of plan computation
Toshio Koide0c9106d2014-02-19 15:26:38 -0800266 }
Toshio Koidefa735a12014-03-28 10:49:07 -0700267
268
269 @Test
270 public void createAndRemoveShortestPaths() throws FloodlightModuleException {
271 // create shortest path intents
272 IntentOperationList opList = new IntentOperationList();
273 opList.add(Operator.ADD, new ShortestPathIntent("1", 1L, 12L, LOCAL_PORT, 2L, 21L, LOCAL_PORT));
274 opList.add(Operator.ADD, new ShortestPathIntent("2", 1L, 14L, LOCAL_PORT, 4L, 41L, LOCAL_PORT));
275 opList.add(Operator.ADD, new ShortestPathIntent("3", 2L, 23L, LOCAL_PORT, 3L, 32L, LOCAL_PORT));
276
277 // compile high-level intent operations into low-level intent operations (calculate paths)
278 PathCalcRuntimeModule runtime1 = new PathCalcRuntimeModule();
279 runtime1.init(modContext);
280 runtime1.startUp(modContext);
281 IntentOperationList pathIntentOpList = runtime1.executeIntentOperations(opList);
282
283 // compile low-level intents into flow entry installation plan
284 PlanCalcRuntime runtime2 = new PlanCalcRuntime();
285 List<Set<FlowEntry>> plan = runtime2.computePlan(pathIntentOpList);
286
287 // show results
288 showResult((PathIntentMap) runtime1.getPathIntents());
289 System.out.println(plan);
290
291 // create remove operations
292 opList.clear();
293 opList.add(Operator.REMOVE, new Intent("1"));
294 opList.add(Operator.REMOVE, new Intent("2"));
295
296 // compile
297 runtime1.executeIntentOperations(opList);
298
299 // show results
300 showResult((PathIntentMap) runtime1.getPathIntents());
301 System.out.println(plan);
302 }
303
Toshio Koidec87810e2014-02-11 13:03:21 -0800304}