12cb05445c175060e2abababfc55f63d28ffaa19
[openflowplugin.git] / applications / forwardingrules-sync / src / test / java / org / opendaylight / openflowplugin / applications / frsync / impl / strategy / SyncPlanPushStrategyIncrementalImplTest.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
9 package org.opendaylight.openflowplugin.applications.frsync.impl.strategy;
10
11 import com.google.common.collect.Lists;
12 import com.google.common.util.concurrent.ListenableFuture;
13 import java.util.Collections;
14 import java.util.HashMap;
15 import java.util.LinkedHashMap;
16 import java.util.List;
17 import java.util.Map;
18 import java.util.concurrent.Future;
19 import org.junit.Assert;
20 import org.junit.Before;
21 import org.junit.Test;
22 import org.junit.runner.RunWith;
23 import org.mockito.ArgumentCaptor;
24 import org.mockito.ArgumentMatchers;
25 import org.mockito.Captor;
26 import org.mockito.InOrder;
27 import org.mockito.Mock;
28 import org.mockito.Mockito;
29 import org.mockito.runners.MockitoJUnitRunner;
30 import org.mockito.stubbing.Answer;
31 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
32 import org.opendaylight.openflowplugin.applications.frsync.impl.DSInputFactory;
33 import org.opendaylight.openflowplugin.applications.frsync.util.ItemSyncBox;
34 import org.opendaylight.openflowplugin.applications.frsync.util.SyncCrudCounters;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNode;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.FlowCapableNodeBuilder;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.meters.Meter;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.TableBuilder;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.TableKey;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.inventory.rev130819.tables.table.Flow;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.AddFlowOutputBuilder;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.RemoveFlowOutputBuilder;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.UpdateFlowOutputBuilder;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.transaction.rev150304.FlowCapableTransactionService;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.transaction.rev150304.SendBarrierInput;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.transaction.rev150304.SendBarrierOutput;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.AddGroupOutputBuilder;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.RemoveGroupOutputBuilder;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.UpdateGroupOutputBuilder;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.groups.Group;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.NodeId;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.Nodes;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.Node;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.inventory.rev130819.nodes.NodeKey;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.AddMeterOutputBuilder;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.RemoveMeterOutputBuilder;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.meter.service.rev130918.UpdateMeterOutputBuilder;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.service.rev131026.UpdateTableOutputBuilder;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.table.features.TableFeatures;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.table.types.rev131026.table.features.TableFeaturesBuilder;
61 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
62 import org.opendaylight.yangtools.yang.common.RpcResult;
63 import org.opendaylight.yangtools.yang.common.RpcResultBuilder;
64
65 /**
66  * Test for {@link SyncPlanPushStrategyIncrementalImpl}.
67  */
68 @RunWith(MockitoJUnitRunner.class)
69 public class SyncPlanPushStrategyIncrementalImplTest {
70
71     private static final NodeId NODE_ID = new NodeId("unit-nodeId");
72     private static final InstanceIdentifier<FlowCapableNode> NODE_IDENT = InstanceIdentifier.create(Nodes.class)
73             .child(Node.class, new NodeKey(NODE_ID)).augmentation(FlowCapableNode.class);
74
75     private SyncPlanPushStrategyIncrementalImpl syncPlanPushStrategy;
76
77     @Mock
78     private DataBroker db;
79     @Mock
80     private GroupForwarder groupCommitter;
81     @Mock
82     private FlowForwarder flowCommitter;
83     @Mock
84     private MeterForwarder meterCommitter;
85     @Mock
86     private TableForwarder tableCommitter;
87     @Mock
88     private FlowCapableTransactionService flowCapableTxService;
89
90     @Captor
91     private ArgumentCaptor<Group> groupCaptor;
92     @Captor
93     private ArgumentCaptor<Group> groupUpdateCaptor;
94     @Captor
95     private ArgumentCaptor<Flow> flowCaptor;
96     @Captor
97     private ArgumentCaptor<Flow> flowUpdateCaptor;
98     @Captor
99     private ArgumentCaptor<Meter> meterCaptor;
100     @Captor
101     private ArgumentCaptor<Meter> meterUpdateCaptor;
102     @Captor
103     private ArgumentCaptor<TableFeatures> tableFeaturesCaptor;
104
105     private SyncCrudCounters counters;
106
107     private final List<ItemSyncBox<Group>> groupsToAddOrUpdate;
108     private final List<ItemSyncBox<Group>> groupsToRemove;
109     private final ItemSyncBox<Meter> metersToAddOrUpdate;
110     private final ItemSyncBox<Meter> metersToRemove;
111     private final Map<TableKey, ItemSyncBox<Flow>> flowsToAddOrUpdate;
112     private final Map<TableKey, ItemSyncBox<Flow>> flowsToRemove;
113
114     public SyncPlanPushStrategyIncrementalImplTest() {
115         groupsToAddOrUpdate = Lists.newArrayList(DiffInputFactory.createGroupSyncBox(1, 2, 3),
116                 DiffInputFactory.createGroupSyncBoxWithUpdates(4, 5, 6));
117         groupsToRemove = Lists.newArrayList(DiffInputFactory.createGroupSyncBox(1, 2, 3),
118                 DiffInputFactory.createGroupSyncBox(4, 5, 6));
119
120         metersToAddOrUpdate = DiffInputFactory.createMeterSyncBoxWithUpdates(1, 2, 3);
121         metersToRemove = DiffInputFactory.createMeterSyncBox(1, 2, 3);
122
123         flowsToAddOrUpdate = new HashMap<>();
124         flowsToAddOrUpdate.put(new TableKey((short) 0), DiffInputFactory.createFlowSyncBox("1", "2", "3"));
125         flowsToAddOrUpdate.put(new TableKey((short) 1), DiffInputFactory.createFlowSyncBoxWithUpdates("4", "5", "6"));
126         flowsToRemove = new HashMap<>();
127         flowsToRemove.put(new TableKey((short) 0), DiffInputFactory.createFlowSyncBox("1", "2", "3"));
128         flowsToRemove.put(new TableKey((short) 1), DiffInputFactory.createFlowSyncBox("4", "5", "6"));
129     }
130
131     @Test
132     public void testExecuteSyncStrategy() throws Exception {
133         final SynchronizationDiffInput diffInput = new SynchronizationDiffInput(NODE_IDENT,
134                 groupsToAddOrUpdate, metersToAddOrUpdate, flowsToAddOrUpdate, flowsToRemove,
135                 metersToRemove, groupsToRemove);
136
137         final SyncCrudCounters syncCounters = new SyncCrudCounters();
138         final ListenableFuture<RpcResult<Void>> rpcResult = syncPlanPushStrategy.executeSyncStrategy(
139                 RpcResultBuilder.<Void>success().buildFuture(), diffInput, syncCounters);
140
141         Mockito.verify(groupCommitter, Mockito.times(6)).add(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
142                 ArgumentMatchers.<Group>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
143         Mockito.verify(groupCommitter, Mockito.times(3)).update(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
144                 ArgumentMatchers.<Group>any(), ArgumentMatchers.<Group>any(),
145                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
146         Mockito.verify(groupCommitter, Mockito.times(6)).remove(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
147                 ArgumentMatchers.<Group>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
148         Mockito.verify(flowCommitter, Mockito.times(6)).add(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
149                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
150         Mockito.verify(flowCommitter, Mockito.times(3)).update(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
151                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.<Flow>any(),
152                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
153         Mockito.verify(flowCommitter, Mockito.times(6)).remove(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
154                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
155         Mockito.verify(meterCommitter, Mockito.times(3)).add(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
156                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
157         Mockito.verify(meterCommitter, Mockito.times(3)).update(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
158                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.<Meter>any(),
159                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
160         Mockito.verify(meterCommitter, Mockito.times(3)).remove(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
161                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
162
163         Assert.assertTrue(rpcResult.isDone());
164         Assert.assertTrue(rpcResult.get().isSuccessful());
165
166         Assert.assertEquals(6, syncCounters.getFlowCrudCounts().getAdded());
167         Assert.assertEquals(3, syncCounters.getFlowCrudCounts().getUpdated());
168         Assert.assertEquals(6, syncCounters.getFlowCrudCounts().getRemoved());
169
170         Assert.assertEquals(6, syncCounters.getGroupCrudCounts().getAdded());
171         Assert.assertEquals(3, syncCounters.getGroupCrudCounts().getUpdated());
172         Assert.assertEquals(6, syncCounters.getGroupCrudCounts().getRemoved());
173
174         Assert.assertEquals(3, syncCounters.getMeterCrudCounts().getAdded());
175         Assert.assertEquals(3, syncCounters.getMeterCrudCounts().getUpdated());
176         Assert.assertEquals(3, syncCounters.getMeterCrudCounts().getRemoved());
177     }
178
179     @Before
180     public void setUp() throws Exception {
181         Mockito.when(flowCapableTxService.sendBarrier(ArgumentMatchers.<SendBarrierInput>any()))
182                 .thenReturn(RpcResultBuilder.success((SendBarrierOutput) null).buildFuture());
183
184         Mockito.doAnswer(createSalServiceFutureAnswer()).when(groupCommitter).add(
185                 ArgumentMatchers.<InstanceIdentifier<Group>>any(), ArgumentMatchers.<Group>any(),
186                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
187         Mockito.doAnswer(createSalServiceFutureAnswer()).when(groupCommitter).update(
188                 ArgumentMatchers.<InstanceIdentifier<Group>>any(), ArgumentMatchers.<Group>any(),
189                 ArgumentMatchers.<Group>any(),
190                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
191         Mockito.doAnswer(createSalServiceFutureAnswer()).when(groupCommitter).remove(
192                 ArgumentMatchers.<InstanceIdentifier<Group>>any(), ArgumentMatchers.<Group>any(),
193                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
194
195         Mockito.doAnswer(createSalServiceFutureAnswer()).when(flowCommitter).add(
196                 ArgumentMatchers.<InstanceIdentifier<Flow>>any(), ArgumentMatchers.<Flow>any(),
197                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
198         Mockito.doAnswer(createSalServiceFutureAnswer()).when(flowCommitter).update(
199                 ArgumentMatchers.<InstanceIdentifier<Flow>>any(), ArgumentMatchers.<Flow>any(),
200                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
201         Mockito.doAnswer(createSalServiceFutureAnswer()).when(flowCommitter).remove(
202                 ArgumentMatchers.<InstanceIdentifier<Flow>>any(), ArgumentMatchers.<Flow>any(),
203                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
204
205         Mockito.doAnswer(createSalServiceFutureAnswer()).when(meterCommitter).add(
206                 ArgumentMatchers.<InstanceIdentifier<Meter>>any(), ArgumentMatchers.<Meter>any(),
207                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
208         Mockito.doAnswer(createSalServiceFutureAnswer()).when(meterCommitter).update(
209                 ArgumentMatchers.<InstanceIdentifier<Meter>>any(), ArgumentMatchers.<Meter>any(),
210                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
211         Mockito.doAnswer(createSalServiceFutureAnswer()).when(meterCommitter).remove(
212                 ArgumentMatchers.<InstanceIdentifier<Meter>>any(), ArgumentMatchers.<Meter>any(),
213                 ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
214
215         Mockito.doAnswer(createSalServiceFutureAnswer()).when(tableCommitter).update(
216                 ArgumentMatchers.<InstanceIdentifier<TableFeatures>>any(), ArgumentMatchers.<TableFeatures>any(),
217                 ArgumentMatchers.<TableFeatures>any(), ArgumentMatchers.<InstanceIdentifier<FlowCapableNode>>any());
218
219         syncPlanPushStrategy = new SyncPlanPushStrategyIncrementalImpl()
220                 .setMeterForwarder(meterCommitter)
221                 .setTableForwarder(tableCommitter)
222                 .setGroupForwarder(groupCommitter)
223                 .setFlowForwarder(flowCommitter)
224                 .setTransactionService(flowCapableTxService);
225
226         counters = new SyncCrudCounters();
227     }
228
229     private <O> Answer<Future<RpcResult<O>>> createSalServiceFutureAnswer() {
230         return invocation -> RpcResultBuilder.<O>success().buildFuture();
231     }
232
233     @Test
234     public void testAddMissingFlows() throws Exception {
235         Mockito.when(flowCommitter.add(ArgumentMatchers.<InstanceIdentifier<Flow>>any(), flowCaptor.capture(),
236                 ArgumentMatchers.same(NODE_IDENT)))
237                 .thenReturn(RpcResultBuilder.success(new AddFlowOutputBuilder().build()).buildFuture());
238
239         final ItemSyncBox<Flow> flowBox = new ItemSyncBox<>();
240         flowBox.getItemsToPush().add(DSInputFactory.createFlow("f3", 3));
241         flowBox.getItemsToPush().add(DSInputFactory.createFlow("f4", 4));
242
243         final Map<TableKey, ItemSyncBox<Flow>> flowBoxMap = new LinkedHashMap<>();
244         flowBoxMap.put(new TableKey((short) 0), flowBox);
245
246         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.addMissingFlows(
247                 NODE_ID, NODE_IDENT, flowBoxMap, counters);
248
249         Assert.assertTrue(result.isDone());
250         Assert.assertTrue(result.get().isSuccessful());
251
252         final List<Flow> flowCaptorAllValues = flowCaptor.getAllValues();
253         Assert.assertEquals(2, flowCaptorAllValues.size());
254         Assert.assertEquals("f3", flowCaptorAllValues.get(0).getId().getValue());
255         Assert.assertEquals("f4", flowCaptorAllValues.get(1).getId().getValue());
256
257         final InOrder inOrderFlow = Mockito.inOrder(flowCapableTxService, flowCommitter);
258         inOrderFlow.verify(flowCommitter, Mockito.times(2)).add(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
259                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.eq(NODE_IDENT));
260         //TODO: uncomment when enabled in impl
261 //        inOrderFlow.verify(flowCapableTxService).sendBarrier(Matchers.<SendBarrierInput>any());
262         inOrderFlow.verifyNoMoreInteractions();
263     }
264
265     @Test
266     public void testRemoveRedundantFlows() throws Exception {
267         Mockito.when(flowCommitter.remove(ArgumentMatchers.<InstanceIdentifier<Flow>>any(), flowCaptor.capture(),
268                 ArgumentMatchers.same(NODE_IDENT)))
269                 .thenReturn(RpcResultBuilder.success(new RemoveFlowOutputBuilder().build()).buildFuture());
270
271         final ItemSyncBox<Flow> flowBox = new ItemSyncBox<>();
272         flowBox.getItemsToPush().add(DSInputFactory.createFlow("f3", 3));
273         flowBox.getItemsToPush().add(DSInputFactory.createFlow("f4", 4));
274
275         final Map<TableKey, ItemSyncBox<Flow>> flowBoxMap = new LinkedHashMap<>();
276         flowBoxMap.put(new TableKey((short) 0), flowBox);
277
278         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.removeRedundantFlows(
279                 NODE_ID, NODE_IDENT, flowBoxMap, counters);
280
281         Assert.assertTrue(result.isDone());
282         Assert.assertTrue(result.get().isSuccessful());
283
284         final List<Flow> flowCaptorAllValues = flowCaptor.getAllValues();
285         Assert.assertEquals(2, flowCaptorAllValues.size());
286         Assert.assertEquals("f3", flowCaptorAllValues.get(0).getId().getValue());
287         Assert.assertEquals("f4", flowCaptorAllValues.get(1).getId().getValue());
288
289         final InOrder inOrderFlow = Mockito.inOrder(flowCapableTxService, flowCommitter);
290         inOrderFlow.verify(flowCommitter, Mockito.times(2)).remove(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
291                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.eq(NODE_IDENT));
292         inOrderFlow.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
293         inOrderFlow.verifyNoMoreInteractions();
294     }
295
296
297     @Test
298     public void testAddMissingFlows_withUpdate() throws Exception {
299         Mockito.when(flowCommitter.add(ArgumentMatchers.<InstanceIdentifier<Flow>>any(), flowCaptor.capture(),
300                 ArgumentMatchers.same(NODE_IDENT)))
301                 .thenReturn(RpcResultBuilder.success(new AddFlowOutputBuilder().build()).buildFuture());
302
303         Mockito.when(flowCommitter.update(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
304                 flowUpdateCaptor.capture(), flowUpdateCaptor.capture(),
305                 ArgumentMatchers.same(NODE_IDENT)))
306                 .thenReturn(RpcResultBuilder.success(new UpdateFlowOutputBuilder().build()).buildFuture());
307
308         final ItemSyncBox<Flow> flowBox = new ItemSyncBox<>();
309         flowBox.getItemsToPush().add(DSInputFactory.createFlow("f3", 3));
310         flowBox.getItemsToPush().add(DSInputFactory.createFlow("f4", 4));
311         flowBox.getItemsToUpdate().add(new ItemSyncBox.ItemUpdateTuple<>(
312                 DSInputFactory.createFlow("f1", 1), DSInputFactory.createFlowWithInstruction("f1", 1)));
313
314         final Map<TableKey, ItemSyncBox<Flow>> flowBoxMap = new LinkedHashMap<>();
315         flowBoxMap.put(new TableKey((short) 0), flowBox);
316
317
318         //TODO: replace null
319         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.addMissingFlows(
320                 NODE_ID, NODE_IDENT, flowBoxMap, counters);
321
322         Assert.assertTrue(result.isDone());
323         Assert.assertTrue(result.get().isSuccessful());
324
325         final List<Flow> flowCaptorAllValues = flowCaptor.getAllValues();
326         Assert.assertEquals(2, flowCaptorAllValues.size());
327         Assert.assertEquals("f3", flowCaptorAllValues.get(0).getId().getValue());
328         Assert.assertEquals("f4", flowCaptorAllValues.get(1).getId().getValue());
329
330         final List<Flow> flowUpdateCaptorAllValues = flowUpdateCaptor.getAllValues();
331         Assert.assertEquals(2, flowUpdateCaptorAllValues.size());
332         Assert.assertEquals("f1", flowUpdateCaptorAllValues.get(0).getId().getValue());
333         Assert.assertEquals("f1", flowUpdateCaptorAllValues.get(1).getId().getValue());
334
335         final InOrder inOrderFlow = Mockito.inOrder(flowCapableTxService, flowCommitter);
336         // add f3, f4
337         inOrderFlow.verify(flowCommitter, Mockito.times(2)).add(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
338                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.eq(NODE_IDENT));
339         // update f1
340         inOrderFlow.verify(flowCommitter).update(ArgumentMatchers.<InstanceIdentifier<Flow>>any(),
341                 ArgumentMatchers.<Flow>any(), ArgumentMatchers.<Flow>any(), ArgumentMatchers.eq(NODE_IDENT));
342         //TODO: uncomment when enabled in impl
343 //        inOrderFlow.verify(flowCapableTxService).sendBarrier(Matchers.<SendBarrierInput>any());
344
345         inOrderFlow.verifyNoMoreInteractions();
346     }
347
348     @Test
349     public void testAddMissingMeters() throws Exception {
350         Mockito.when(meterCommitter.add(ArgumentMatchers.<InstanceIdentifier<Meter>>any(), meterCaptor.capture(),
351                 ArgumentMatchers.same(NODE_IDENT)))
352                 .thenReturn(RpcResultBuilder.success(new AddMeterOutputBuilder().build()).buildFuture());
353
354         final ItemSyncBox<Meter> meterSyncBox = new ItemSyncBox<>();
355         meterSyncBox.getItemsToPush().add(DSInputFactory.createMeter(2L));
356         meterSyncBox.getItemsToPush().add(DSInputFactory.createMeter(4L));
357
358         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.addMissingMeters(
359                 NODE_ID, NODE_IDENT, meterSyncBox, counters);
360
361         Assert.assertTrue(result.isDone());
362         Assert.assertTrue(result.get().isSuccessful());
363
364         final List<Meter> metercaptorAllValues = meterCaptor.getAllValues();
365         Assert.assertEquals(2, metercaptorAllValues.size());
366         Assert.assertEquals(2L, metercaptorAllValues.get(0).getMeterId().getValue().longValue());
367         Assert.assertEquals(4L, metercaptorAllValues.get(1).getMeterId().getValue().longValue());
368
369         final InOrder inOrderMeter = Mockito.inOrder(flowCapableTxService, meterCommitter);
370         inOrderMeter.verify(meterCommitter, Mockito.times(2)).add(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
371                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.eq(NODE_IDENT));
372         //TODO: uncomment when enabled in impl
373 //        inOrderMeter.verify(flowCapableTxService).sendBarrier(Matchers.<SendBarrierInput>any());
374         inOrderMeter.verifyNoMoreInteractions();
375     }
376
377     @Test
378     public void testAddMissingMeters_withUpdate() throws Exception {
379         Mockito.when(meterCommitter.add(ArgumentMatchers.<InstanceIdentifier<Meter>>any(), meterCaptor.capture(),
380                 ArgumentMatchers.same(NODE_IDENT)))
381                 .thenReturn(RpcResultBuilder.success(new AddMeterOutputBuilder().build()).buildFuture());
382
383         Mockito.when(meterCommitter.update(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
384                 meterUpdateCaptor.capture(), meterUpdateCaptor.capture(), ArgumentMatchers.same(NODE_IDENT)))
385                 .thenReturn(RpcResultBuilder.success(new UpdateMeterOutputBuilder().build()).buildFuture());
386
387         final ItemSyncBox<Meter> meterSyncBox = new ItemSyncBox<>();
388         meterSyncBox.getItemsToPush().add(DSInputFactory.createMeter(2L));
389         meterSyncBox.getItemsToPush().add(DSInputFactory.createMeter(4L));
390         meterSyncBox.getItemsToUpdate().add(new ItemSyncBox.ItemUpdateTuple<>(
391                 DSInputFactory.createMeter(1L), DSInputFactory.createMeterWithBody(1L)));
392
393         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.addMissingMeters(
394                 NODE_ID, NODE_IDENT, meterSyncBox, counters);
395
396         Assert.assertTrue(result.isDone());
397         Assert.assertTrue(result.get().isSuccessful());
398
399         final List<Meter> meterCaptorAllValues = meterCaptor.getAllValues();
400         Assert.assertEquals(2, meterCaptorAllValues.size());
401         Assert.assertEquals(2L, meterCaptorAllValues.get(0).getMeterId().getValue().longValue());
402         Assert.assertEquals(4L, meterCaptorAllValues.get(1).getMeterId().getValue().longValue());
403
404
405         final List<Meter> meterUpdateCaptorAllValues = meterUpdateCaptor.getAllValues();
406         Assert.assertEquals(2, meterUpdateCaptorAllValues.size());
407         Assert.assertEquals(1L, meterUpdateCaptorAllValues.get(0).getMeterId().getValue().longValue());
408         Assert.assertEquals(1L, meterUpdateCaptorAllValues.get(1).getMeterId().getValue().longValue());
409
410         final InOrder inOrderMeters = Mockito.inOrder(flowCapableTxService, meterCommitter);
411         inOrderMeters.verify(meterCommitter, Mockito.times(2)).add(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
412                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.eq(NODE_IDENT));
413         inOrderMeters.verify(meterCommitter).update(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
414                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.<Meter>any(), ArgumentMatchers.eq(NODE_IDENT));
415         //TODO: uncomment when enabled in impl
416 //        inOrderMeters.verify(flowCapableTxService).sendBarrier(Matchers.<SendBarrierInput>any());
417
418         inOrderMeters.verifyNoMoreInteractions();
419     }
420
421     @Test
422     public void testRemoveRedundantMeters() throws Exception {
423         Mockito.when(meterCommitter.remove(ArgumentMatchers.<InstanceIdentifier<Meter>>any(), meterCaptor.capture(),
424                 ArgumentMatchers.same(NODE_IDENT)))
425                 .thenReturn(RpcResultBuilder.success(new RemoveMeterOutputBuilder().build()).buildFuture());
426
427         final ItemSyncBox<Meter> meterSyncBox = new ItemSyncBox<>();
428         meterSyncBox.getItemsToPush().add(DSInputFactory.createMeter(2L));
429         meterSyncBox.getItemsToPush().add(DSInputFactory.createMeter(4L));
430         meterSyncBox.getItemsToUpdate().add(new ItemSyncBox.ItemUpdateTuple<>(
431                 DSInputFactory.createMeter(1L), DSInputFactory.createMeterWithBody(1L)));
432
433         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.removeRedundantMeters(
434                 NODE_ID, NODE_IDENT, meterSyncBox, counters);
435
436         Assert.assertTrue(result.isDone());
437         Assert.assertTrue(result.get().isSuccessful());
438
439         final List<Meter> metercaptorAllValues = meterCaptor.getAllValues();
440         Assert.assertEquals(2, metercaptorAllValues.size());
441         Assert.assertEquals(2L, metercaptorAllValues.get(0).getMeterId().getValue().longValue());
442         Assert.assertEquals(4L, metercaptorAllValues.get(1).getMeterId().getValue().longValue());
443
444         final InOrder inOrderMeter = Mockito.inOrder(flowCapableTxService, meterCommitter);
445         inOrderMeter.verify(meterCommitter, Mockito.times(2)).remove(ArgumentMatchers.<InstanceIdentifier<Meter>>any(),
446                 ArgumentMatchers.<Meter>any(), ArgumentMatchers.eq(NODE_IDENT));
447         //TODO: uncomment when enabled in impl
448 //        inOrderMeter.verify(flowCapableTxService).sendBarrier(Matchers.<SendBarrierInput>any());
449         inOrderMeter.verifyNoMoreInteractions();
450     }
451
452     @Test
453     public void testAddMissingGroups() throws Exception {
454         Mockito.when(groupCommitter.add(ArgumentMatchers.<InstanceIdentifier<Group>>any(), groupCaptor.capture(),
455                 ArgumentMatchers.same(NODE_IDENT)))
456                 .thenReturn(RpcResultBuilder.success(new AddGroupOutputBuilder().build()).buildFuture());
457
458         ItemSyncBox<Group> groupBox1 = new ItemSyncBox<>();
459         groupBox1.getItemsToPush().add(DSInputFactory.createGroup(2L));
460
461         ItemSyncBox<Group> groupBox2 = new ItemSyncBox<>();
462         groupBox2.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(3L, 2L));
463         groupBox2.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(4L, 2L));
464
465         ItemSyncBox<Group> groupBox3 = new ItemSyncBox<>();
466         groupBox3.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(5L, 3L, 4L));
467
468         final List<ItemSyncBox<Group>> groupBoxLot = Lists.newArrayList(groupBox1, groupBox2, groupBox3);
469
470         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.addMissingGroups(
471                 NODE_ID, NODE_IDENT, groupBoxLot, counters);
472
473         Assert.assertTrue(result.isDone());
474         Assert.assertTrue(result.get().isSuccessful());
475
476         final List<Group> groupCaptorAllValues = groupCaptor.getAllValues();
477         Assert.assertEquals(4, groupCaptorAllValues.size());
478         Assert.assertEquals(2L, groupCaptorAllValues.get(0).getGroupId().getValue().longValue());
479         Assert.assertEquals(3L, groupCaptorAllValues.get(1).getGroupId().getValue().longValue());
480         Assert.assertEquals(4L, groupCaptorAllValues.get(2).getGroupId().getValue().longValue());
481         Assert.assertEquals(5L, groupCaptorAllValues.get(3).getGroupId().getValue().longValue());
482
483         final InOrder inOrderGroups = Mockito.inOrder(flowCapableTxService, groupCommitter);
484         // add 2
485         inOrderGroups.verify(groupCommitter).add(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
486                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
487         inOrderGroups.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
488         // add 3, 4
489         inOrderGroups.verify(groupCommitter, Mockito.times(2)).add(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
490                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
491         inOrderGroups.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
492         // add 5
493         inOrderGroups.verify(groupCommitter).add(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
494                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
495         inOrderGroups.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
496
497         inOrderGroups.verifyNoMoreInteractions();
498     }
499
500     @Test
501     public void testAddMissingGroups_withUpdate() throws Exception {
502         Mockito.when(groupCommitter.add(ArgumentMatchers.<InstanceIdentifier<Group>>any(), groupCaptor.capture(),
503                 ArgumentMatchers.same(NODE_IDENT)))
504                 .thenReturn(RpcResultBuilder.success(new AddGroupOutputBuilder().build()).buildFuture());
505
506         Mockito.when(groupCommitter.update(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
507                 groupUpdateCaptor.capture(), groupUpdateCaptor.capture(),
508                 ArgumentMatchers.same(NODE_IDENT)))
509                 .thenReturn(RpcResultBuilder.success(new UpdateGroupOutputBuilder().build()).buildFuture());
510
511         ItemSyncBox<Group> groupBox1 = new ItemSyncBox<>();
512         groupBox1.getItemsToPush().add(DSInputFactory.createGroup(2L));
513         groupBox1.getItemsToUpdate().add(new ItemSyncBox.ItemUpdateTuple<>(
514                 DSInputFactory.createGroup(1L), DSInputFactory.createGroupWithAction(1L)));
515
516         ItemSyncBox<Group> groupBox2 = new ItemSyncBox<>();
517         groupBox2.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(3L, 2L));
518         groupBox2.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(4L, 2L));
519
520         ItemSyncBox<Group> groupBox3 = new ItemSyncBox<>();
521         groupBox3.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(5L, 3L, 4L));
522
523         final List<ItemSyncBox<Group>> groupBoxLot = Lists.newArrayList(groupBox1, groupBox2, groupBox3);
524         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.addMissingGroups(
525                 NODE_ID, NODE_IDENT, groupBoxLot, counters);
526
527         Assert.assertTrue(result.isDone());
528         Assert.assertTrue(result.get().isSuccessful());
529
530         final List<Group> groupCaptorAllValues = groupCaptor.getAllValues();
531         Assert.assertEquals(4, groupCaptorAllValues.size());
532         Assert.assertEquals(2L, groupCaptorAllValues.get(0).getGroupId().getValue().longValue());
533         Assert.assertEquals(3L, groupCaptorAllValues.get(1).getGroupId().getValue().longValue());
534         Assert.assertEquals(4L, groupCaptorAllValues.get(2).getGroupId().getValue().longValue());
535         Assert.assertEquals(5L, groupCaptorAllValues.get(3).getGroupId().getValue().longValue());
536
537         final List<Group> groupUpdateCaptorAllValues = groupUpdateCaptor.getAllValues();
538         Assert.assertEquals(2, groupUpdateCaptorAllValues.size());
539         Assert.assertEquals(1L, groupUpdateCaptorAllValues.get(0).getGroupId().getValue().longValue());
540         Assert.assertEquals(1L, groupUpdateCaptorAllValues.get(1).getGroupId().getValue().longValue());
541
542         final InOrder inOrderGroups = Mockito.inOrder(flowCapableTxService, groupCommitter);
543
544         // add 2, update 1
545         inOrderGroups.verify(groupCommitter).add(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
546                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
547         inOrderGroups.verify(groupCommitter).update(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
548                 ArgumentMatchers.<Group>any(), ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
549         inOrderGroups.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
550
551         // add 3, 4
552         inOrderGroups.verify(groupCommitter, Mockito.times(2)).add(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
553                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
554         inOrderGroups.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
555         // add 5
556         inOrderGroups.verify(groupCommitter).add(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
557                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
558         inOrderGroups.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
559
560         inOrderGroups.verifyNoMoreInteractions();
561     }
562
563     @Test
564     public void testRemoveRedundantGroups() throws Exception {
565         Mockito.when(groupCommitter.remove(ArgumentMatchers.<InstanceIdentifier<Group>>any(), groupCaptor.capture(),
566                 ArgumentMatchers.same(NODE_IDENT)))
567                 .thenReturn(RpcResultBuilder.success(new RemoveGroupOutputBuilder().build()).buildFuture());
568
569         ItemSyncBox<Group> groupBox1 = new ItemSyncBox<>();
570         groupBox1.getItemsToPush().add(DSInputFactory.createGroup(2L));
571         groupBox1.getItemsToUpdate().add(new ItemSyncBox.ItemUpdateTuple<>(
572                 DSInputFactory.createGroup(1L), DSInputFactory.createGroupWithAction(1L)));
573
574         ItemSyncBox<Group> groupBox2 = new ItemSyncBox<>();
575         groupBox2.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(3L, 2L));
576         groupBox2.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(4L, 2L));
577
578         ItemSyncBox<Group> groupBox3 = new ItemSyncBox<>();
579         groupBox3.getItemsToPush().add(DSInputFactory.createGroupWithPreconditions(5L, 3L, 4L));
580
581         final List<ItemSyncBox<Group>> groupBoxLot = Lists.newArrayList(groupBox1, groupBox2, groupBox3);
582         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.removeRedundantGroups(
583                 NODE_ID, NODE_IDENT, groupBoxLot, counters);
584
585         Assert.assertTrue(result.isDone());
586         Assert.assertTrue(result.get().isSuccessful());
587
588         final List<Group> groupCaptorAllValues = groupCaptor.getAllValues();
589         Assert.assertEquals(4, groupCaptorAllValues.size());
590         Assert.assertEquals(5L, groupCaptorAllValues.get(0).getGroupId().getValue().longValue());
591         Assert.assertEquals(3L, groupCaptorAllValues.get(1).getGroupId().getValue().longValue());
592         Assert.assertEquals(4L, groupCaptorAllValues.get(2).getGroupId().getValue().longValue());
593         Assert.assertEquals(2L, groupCaptorAllValues.get(3).getGroupId().getValue().longValue());
594
595         final InOrder inOrderGroup = Mockito.inOrder(flowCapableTxService, groupCommitter);
596         // remove 5
597         inOrderGroup.verify(groupCommitter).remove(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
598                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
599         inOrderGroup.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
600         // remove 3, 4
601         inOrderGroup.verify(groupCommitter, Mockito.times(2)).remove(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
602                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
603         inOrderGroup.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
604         // remove 2
605         inOrderGroup.verify(groupCommitter).remove(ArgumentMatchers.<InstanceIdentifier<Group>>any(),
606                 ArgumentMatchers.<Group>any(), ArgumentMatchers.eq(NODE_IDENT));
607         inOrderGroup.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
608
609         inOrderGroup.verifyNoMoreInteractions();
610     }
611
612     @Test
613     public void testUpdateTableFeatures() throws Exception {
614         Mockito.lenient().when(tableCommitter.update(ArgumentMatchers.<InstanceIdentifier<TableFeatures>>any(),
615                 ArgumentMatchers.isNull(TableFeatures.class), tableFeaturesCaptor.capture(),
616                 ArgumentMatchers.same(NODE_IDENT)))
617                 .thenReturn(RpcResultBuilder.success(new UpdateTableOutputBuilder().build()).buildFuture());
618
619         final FlowCapableNode operational = new FlowCapableNodeBuilder()
620                 .setTable(Collections.singletonList(new TableBuilder()
621                         .setId((short) 1)
622                         .build()))
623                 .setTableFeatures(Collections.singletonList(new TableFeaturesBuilder()
624                         .setName("test table features")
625                         .setTableId((short) 1)
626                         .build()))
627                 .build();
628
629         final ListenableFuture<RpcResult<Void>> result = syncPlanPushStrategy.updateTableFeatures(
630                 NODE_IDENT, operational);
631
632         Assert.assertTrue(result.isDone());
633         Assert.assertTrue(result.get().isSuccessful());
634
635         final List<TableFeatures> groupCaptorAllValues = tableFeaturesCaptor.getAllValues();
636         //TODO: uncomment when enabled in impl
637 //        Assert.assertEquals(1, groupCaptorAllValues.size());
638 //        Assert.assertEquals("test table features", groupCaptorAllValues.get(0).getName());
639 //        Assert.assertEquals(1, groupCaptorAllValues.get(0).getTableId().intValue());
640
641         Mockito.verify(flowCapableTxService).sendBarrier(ArgumentMatchers.<SendBarrierInput>any());
642     }
643 }