blob: 5268527fc914b6f09ffbc3f079c4614c99e91f04 [file] [log] [blame]
Pier Luigif094c612017-10-14 12:15:02 +02001/*
2 * Copyright 2017-present Open Networking Foundation
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
Thomas Vachuska52f2cd12018-11-08 21:20:04 -080017package org.onosproject.store.meter.impl;
Pier Luigif094c612017-10-14 12:15:02 +020018
Charles Chan593acf92017-11-22 13:55:41 -080019import com.google.common.collect.Lists;
Pier Luigif094c612017-10-14 12:15:02 +020020import org.junit.After;
21import org.junit.Before;
22import org.junit.Test;
23import org.onlab.junit.TestUtils;
Charles Chan593acf92017-11-22 13:55:41 -080024import org.onlab.util.KryoNamespace;
25import org.onosproject.TestApplicationId;
Pier Luigif094c612017-10-14 12:15:02 +020026import org.onosproject.net.DeviceId;
27import org.onosproject.net.behaviour.MeterQuery;
28import org.onosproject.net.driver.Behaviour;
29import org.onosproject.net.driver.Driver;
30import org.onosproject.net.driver.DriverData;
31import org.onosproject.net.driver.DriverHandler;
32import org.onosproject.net.driver.DriverServiceAdapter;
33import org.onosproject.net.meter.Band;
34import org.onosproject.net.meter.DefaultBand;
35import org.onosproject.net.meter.DefaultMeter;
36import org.onosproject.net.meter.DefaultMeterFeatures;
37import org.onosproject.net.meter.Meter;
pierventre3b39bd82021-08-18 09:40:14 +020038import org.onosproject.net.meter.MeterCellId;
Pier Luigif094c612017-10-14 12:15:02 +020039import org.onosproject.net.meter.MeterFeatures;
40import org.onosproject.net.meter.MeterFeaturesKey;
41import org.onosproject.net.meter.MeterId;
42import org.onosproject.net.meter.MeterKey;
pierventre3b39bd82021-08-18 09:40:14 +020043import org.onosproject.net.meter.MeterScope;
Pier Luigif094c612017-10-14 12:15:02 +020044import org.onosproject.net.meter.MeterState;
pierventre3b39bd82021-08-18 09:40:14 +020045import org.onosproject.net.meter.MeterTableKey;
46import org.onosproject.net.pi.model.PiMeterId;
47import org.onosproject.net.pi.runtime.PiMeterCellId;
Charles Chan593acf92017-11-22 13:55:41 -080048import org.onosproject.store.service.Serializer;
Pier Luigif094c612017-10-14 12:15:02 +020049import org.onosproject.store.service.TestStorageService;
50
pierventre44220052020-09-22 12:51:06 +020051import java.util.Collection;
Pier Luigif094c612017-10-14 12:15:02 +020052import java.util.Collections;
53import java.util.HashSet;
Pier Luigif094c612017-10-14 12:15:02 +020054import java.util.concurrent.CompletableFuture;
55import java.util.concurrent.ExecutionException;
56
57import static org.hamcrest.Matchers.is;
58import static org.junit.Assert.*;
59import static org.onosproject.net.NetTestTools.APP_ID;
Daniele Moro43ac2892021-07-15 17:02:59 +020060import static org.onosproject.net.NetTestTools.APP_ID_2;
Pier Luigif094c612017-10-14 12:15:02 +020061import static org.onosproject.net.NetTestTools.did;
62
63/**
64 * Meter store tests.
65 */
66public class DistributedMeterStoreTest {
Pier Luigif094c612017-10-14 12:15:02 +020067 // Store under testing
68 private DistributedMeterStore meterStore;
69
70 // Device ids used during the tests
71 private DeviceId did1 = did("1");
72 private DeviceId did2 = did("2");
73 private DeviceId did3 = did("3");
74 private DeviceId did4 = did("4");
75
76 // Meter ids used during the tests
77 private MeterId mid1 = MeterId.meterId(1);
78 private MeterId mid2 = MeterId.meterId(2);
Daniele Moro43ac2892021-07-15 17:02:59 +020079 private MeterId mid3 = MeterId.meterId(3);
Pier Luigibdcd9672017-10-13 13:54:48 +020080 private MeterId mid10 = MeterId.meterId(10);
pierventre3b39bd82021-08-18 09:40:14 +020081 private MeterCellId cid4 = PiMeterCellId.ofIndirect(
82 PiMeterId.of("foo"), 4);
83 private MeterCellId invalidCid = PiMeterCellId.ofIndirect(
84 PiMeterId.of("foo"), 11);
Pier Luigif094c612017-10-14 12:15:02 +020085
86 // Bands used during the tests
87 private Band b1 = DefaultBand.builder()
88 .ofType(Band.Type.DROP)
89 .withRate(500)
90 .build();
91
92 // Meters used during the tests
93 private Meter m1 = DefaultMeter.builder()
94 .forDevice(did1)
95 .fromApp(APP_ID)
96 .withId(mid1)
97 .withUnit(Meter.Unit.KB_PER_SEC)
98 .withBands(Collections.singletonList(b1))
99 .build();
100
Daniele Moro43ac2892021-07-15 17:02:59 +0200101 private Meter m2 = DefaultMeter.builder()
102 .forDevice(did1)
103 .fromApp(APP_ID_2)
104 .withCellId(mid2)
105 .withUnit(Meter.Unit.KB_PER_SEC)
106 .withBands(Collections.singletonList(b1))
107 .build();
108
109 private Meter m3 = DefaultMeter.builder()
110 .forDevice(did2)
111 .fromApp(APP_ID_2)
112 .withCellId(mid3)
113 .withUnit(Meter.Unit.KB_PER_SEC)
114 .withBands(Collections.singletonList(b1))
115 .build();
116
pierventre3b39bd82021-08-18 09:40:14 +0200117 private Meter m4 = DefaultMeter.builder()
118 .forDevice(did3)
119 .fromApp(APP_ID)
120 .withCellId(cid4)
121 .withUnit(Meter.Unit.KB_PER_SEC)
122 .withBands(Collections.singletonList(b1))
123 .build();
124
Pier Luigif094c612017-10-14 12:15:02 +0200125 // Meter features used during the tests
126 private MeterFeatures mef1 = DefaultMeterFeatures.builder().forDevice(did1)
127 .withMaxMeters(3L)
128 .withBandTypes(new HashSet<>())
129 .withUnits(new HashSet<>())
130 .hasStats(false)
131 .hasBurst(false)
132 .withMaxBands((byte) 0)
133 .withMaxColors((byte) 0)
134 .build();
135 private MeterFeatures mef2 = DefaultMeterFeatures.builder().forDevice(did2)
136 .withMaxMeters(10L)
137 .withBandTypes(new HashSet<>())
138 .withUnits(new HashSet<>())
139 .hasStats(false)
140 .hasBurst(false)
141 .withMaxBands((byte) 0)
142 .withMaxColors((byte) 0)
143 .build();
pierventre3b39bd82021-08-18 09:40:14 +0200144 private MeterFeatures mef3 = DefaultMeterFeatures.builder().forDevice(did3)
145 .withStartIndex(0L)
146 .withEndIndex(10L)
147 .withScope(MeterScope.of("foo"))
148 .withBandTypes(new HashSet<>())
149 .withUnits(new HashSet<>())
150 .hasStats(false)
151 .hasBurst(false)
152 .withMaxBands((byte) 0)
153 .withMaxColors((byte) 0)
154 .build();
Pier Luigif094c612017-10-14 12:15:02 +0200155
156 @Before
157 public void setup() {
158 // Init step
159 meterStore = new DistributedMeterStore();
160 // Let's initialize some internal services
161 TestUtils.setField(meterStore, "storageService", new TestStorageService());
Pier Luigif094c612017-10-14 12:15:02 +0200162 TestUtils.setField(meterStore, "driverService", new TestDriverService());
Charles Chan593acf92017-11-22 13:55:41 -0800163
164 // Inject TestApplicationId into the DistributedMeterStore serializer
165 KryoNamespace.Builder testKryoBuilder = TestUtils.getField(meterStore, "APP_KRYO_BUILDER");
166 testKryoBuilder.register(TestApplicationId.class);
167 Serializer testSerializer = Serializer.using(Lists.newArrayList(testKryoBuilder.build()));
168 TestUtils.setField(meterStore, "serializer", testSerializer);
169
Pier Luigif094c612017-10-14 12:15:02 +0200170 // Activate the store
171 meterStore.activate();
172 }
173
174 @After
175 public void tearDown() {
176 // Deactivate the store
177 meterStore.deactivate();
178 }
179
pierventre3b39bd82021-08-18 09:40:14 +0200180 private void initMeterStore(boolean enableUserDefinedIndex) {
181 meterStore.userDefinedIndexMode(enableUserDefinedIndex);
Pier Luigif094c612017-10-14 12:15:02 +0200182 // Let's store feature for device 1
183 meterStore.storeMeterFeatures(mef1);
184 // Let's store feature for device 2
185 meterStore.storeMeterFeatures(mef2);
pierventre3b39bd82021-08-18 09:40:14 +0200186 meterStore.storeMeterFeatures(mef3);
Pier Luigif094c612017-10-14 12:15:02 +0200187 }
188
189 /**
190 * Test proper store of meter features.
191 */
192 @Test
193 public void testStoreMeterFeatures() {
194 // Let's store feature for device 1
195 meterStore.storeMeterFeatures(mef1);
196 // Verify store meter features
197 assertThat(meterStore.getMaxMeters(MeterFeaturesKey.key(did1)), is(3L));
198 // Let's store feature for device 1
199 meterStore.storeMeterFeatures(mef2);
200 // Verify store meter features
201 assertThat(meterStore.getMaxMeters(MeterFeaturesKey.key(did2)), is(10L));
202 }
203
204 /**
205 * Test proper delete of meter features.
206 */
207 @Test
208 public void testDeleteMeterFeatures() {
209 // Let's store feature for device 1
210 meterStore.storeMeterFeatures(mef1);
211 // Verify store meter features
212 assertThat(meterStore.getMaxMeters(MeterFeaturesKey.key(did1)), is(3L));
213 // Let's delete the features
214 meterStore.deleteMeterFeatures(did1);
215 // Verify delete meter features
216 assertThat(meterStore.getMaxMeters(MeterFeaturesKey.key(did1)), is(0L));
217 }
218
219 /**
220 * Test proper allocation of meter ids.
221 */
222 @Test
223 public void testAllocateId() {
224 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200225 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200226 // Allocate a meter id and verify is equal to mid1
227 assertThat(mid1, is(meterStore.allocateMeterId(did1)));
228 // Allocate a meter id and verify is equal to mid2
229 assertThat(mid2, is(meterStore.allocateMeterId(did1)));
230 }
231
232 /**
233 * Test proper free of meter ids.
234 */
235 @Test
236 public void testFreeId() {
237 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200238 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200239 // Allocate a meter id and verify is equal to mid1
240 assertThat(mid1, is(meterStore.allocateMeterId(did1)));
241 // Free the above id
242 meterStore.freeMeterId(did1, mid1);
243 // Allocate a meter id and verify is equal to mid1
244 assertThat(mid1, is(meterStore.allocateMeterId(did1)));
Pier Luigibdcd9672017-10-13 13:54:48 +0200245 // Free an id not allocated
246 meterStore.freeMeterId(did1, mid10);
247 // Allocate a meter id and verify is equal to mid2
248 assertThat(mid2, is(meterStore.allocateMeterId(did1)));
Pier Luigif094c612017-10-14 12:15:02 +0200249 }
250
251 /**
252 * Test proper reuse of meter ids.
253 */
254 @Test
255 public void testReuseId() {
256 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200257 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200258 // Reserve id 1
259 MeterId meterIdOne = meterStore.allocateMeterId(did2);
260 // Free the above id
261 meterStore.freeMeterId(did2, meterIdOne);
262 // Start an async reservation
263 CompletableFuture<MeterId> future = CompletableFuture.supplyAsync(
264 () -> meterStore.allocateMeterId(did2)
265 );
266 // Start another reservation
267 MeterId meterIdTwo = meterStore.allocateMeterId(did2);
268 try {
269 meterIdOne = future.get();
270 } catch (InterruptedException | ExecutionException e) {
271 e.printStackTrace();
272 }
273 // Ids should be different, otherwise we had clash in the store
274 assertNotEquals("Ids should be different", meterIdOne, meterIdTwo);
275
276 // Free the above id
277 meterStore.freeMeterId(did1, meterIdOne);
278 // Free the above id
279 meterStore.freeMeterId(did1, meterIdTwo);
280 // Reserve id 1
281 meterIdOne = meterStore.allocateMeterId(did2);
282 // Reserve id 2
283 meterStore.allocateMeterId(did2);
284 // Reserve id 3
285 MeterId meterIdThree = meterStore.allocateMeterId(did2);
286 // Reserve id 4
287 MeterId meterIdFour = meterStore.allocateMeterId(did2);
288 // Free the above id
289 meterStore.freeMeterId(did1, meterIdOne);
290 // Free the above id
291 meterStore.freeMeterId(did1, meterIdThree);
292 // Free the above id
293 meterStore.freeMeterId(did1, meterIdFour);
294 // Start an async reservation
295 future = CompletableFuture.supplyAsync(
296 () -> meterStore.allocateMeterId(did2)
297 );
298 // Start another reservation
299 MeterId meterAnotherId = meterStore.allocateMeterId(did2);
300 try {
301 meterAnotherId = future.get();
302 } catch (InterruptedException | ExecutionException e) {
303 e.printStackTrace();
304 }
305 // Ids should be different, otherwise we had clash in the store
306 assertNotEquals("Ids should be different", meterAnotherId, meterIdOne);
307 }
308
309 /**
310 * Test query meters mechanism.
311 */
312 @Test
313 public void testQueryMeters() {
314 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200315 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200316 // Let's test queryMeters
317 assertThat(mid1, is(meterStore.allocateMeterId(did3)));
318 // Let's test queryMeters error
319 assertNull(meterStore.allocateMeterId(did4));
320 }
321
322 /**
323 * Test max meter error.
324 */
325 @Test
326 public void testMaxMeterError() {
327 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200328 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200329 // Reserve id 1
330 assertThat(mid1, is(meterStore.allocateMeterId(did1)));
331 // Reserve id 2
332 assertThat(mid2, is(meterStore.allocateMeterId(did1)));
Wailok Shum90b988a2021-09-13 17:23:20 +0800333 // Reserve id 3
334 assertThat(mid3, is(meterStore.allocateMeterId(did1)));
Pier Luigif094c612017-10-14 12:15:02 +0200335 // Max meter error
336 assertNull(meterStore.allocateMeterId(did1));
337 }
338
339 /**
340 * Test store meter.
341 */
342 @Test
343 public void testStoreMeter() {
344 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200345 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200346 // Simulate the allocation of an id
347 MeterId idOne = meterStore.allocateMeterId(did1);
348 // Verify the allocation
349 assertThat(mid1, is(idOne));
350 // Let's create a meter
351 Meter meterOne = DefaultMeter.builder()
352 .forDevice(did1)
353 .fromApp(APP_ID)
354 .withId(mid1)
355 .withUnit(Meter.Unit.KB_PER_SEC)
356 .withBands(Collections.singletonList(b1))
357 .build();
358 // Set the state
359 ((DefaultMeter) meterOne).setState(MeterState.PENDING_ADD);
360 // Store the meter
361 meterStore.storeMeter(meterOne);
362 // Let's create meter key
363 MeterKey meterKey = MeterKey.key(did1, mid1);
364 // Verify the store
365 assertThat(1, is(meterStore.getAllMeters().size()));
366 assertThat(1, is(meterStore.getAllMeters(did1).size()));
367 assertThat(m1, is(meterStore.getMeter(meterKey)));
368 }
369
370 /**
371 * Test delete meter.
372 */
373 @Test
374 public void testDeleteMeter() {
375 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200376 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200377 // Simulate the allocation of an id
378 MeterId idOne = meterStore.allocateMeterId(did1);
379 // Verify the allocation
380 assertThat(mid1, is(idOne));
381 // Let's create a meter
382 Meter meterOne = DefaultMeter.builder()
383 .forDevice(did1)
384 .fromApp(APP_ID)
385 .withId(mid1)
386 .withUnit(Meter.Unit.KB_PER_SEC)
387 .withBands(Collections.singletonList(b1))
388 .build();
389 // Set the state
390 ((DefaultMeter) meterOne).setState(MeterState.PENDING_ADD);
391 // Store the meter
392 meterStore.storeMeter(meterOne);
393 // Set the state
394 ((DefaultMeter) meterOne).setState(MeterState.PENDING_REMOVE);
395 // Let's create meter key
396 MeterKey meterKey = MeterKey.key(did1, mid1);
397 // Delete meter
398 meterStore.deleteMeter(meterOne);
399 // Start an async delete, simulating the operation of the provider
400 CompletableFuture<Void> future = CompletableFuture.runAsync(
401 () -> meterStore.deleteMeterNow(meterOne)
402 );
403 // Let's wait
404 try {
405 future.get();
406 } catch (InterruptedException | ExecutionException e) {
407 e.printStackTrace();
408 }
409 // Verify delete
410 assertThat(0, is(meterStore.getAllMeters().size()));
411 assertThat(0, is(meterStore.getAllMeters(did1).size()));
412 assertNull(meterStore.getMeter(meterKey));
413 assertThat(mid1, is(meterStore.allocateMeterId(did1)));
414 }
415
416 /**
417 * Test no delete meter.
418 */
419 @Test
420 public void testNoDeleteMeter() {
421 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200422 initMeterStore(false);
Pier Luigif094c612017-10-14 12:15:02 +0200423 // Simulate the allocation of an id
424 MeterId idOne = meterStore.allocateMeterId(did1);
425 // Create the key
426 MeterKey keyOne = MeterKey.key(did1, idOne);
427 // Let's create a meter
428 Meter meterOne = DefaultMeter.builder()
429 .forDevice(did1)
430 .fromApp(APP_ID)
431 .withId(mid1)
432 .withUnit(Meter.Unit.KB_PER_SEC)
433 .withBands(Collections.singletonList(b1))
434 .build();
435 // Set the state
436 ((DefaultMeter) meterOne).setState(MeterState.PENDING_REMOVE);
437 // Delete meter
438 meterStore.deleteMeter(meterOne);
439 // Verify No delete
440 assertThat(0, is(meterStore.getAllMeters().size()));
441 assertThat(0, is(meterStore.getAllMeters(did1).size()));
442 assertNull(meterStore.getMeter(keyOne));
443 }
444
pierventre1b8afbc2020-07-13 14:07:05 +0200445 /**
446 * Test purge meter.
447 */
448 @Test
449 public void testPurgeMeter() {
450 // add the meter
451 testStoreMeter();
452 meterStore.purgeMeter(did1);
453 // Verify delete
454 MeterKey keyOne = MeterKey.key(did1, mid1);
455 assertThat(0, is(meterStore.getAllMeters().size()));
456 assertThat(0, is(meterStore.getAllMeters(did1).size()));
457 assertNull(meterStore.getMeter(keyOne));
Pier Luigif094c612017-10-14 12:15:02 +0200458 }
459
pierventre44220052020-09-22 12:51:06 +0200460 /**
Daniele Moro43ac2892021-07-15 17:02:59 +0200461 * Test purge meter given device and application.
462 */
463 @Test
464 public void testPurgeMeterDeviceAndApp() {
465 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200466 initMeterStore(false);
Daniele Moro43ac2892021-07-15 17:02:59 +0200467 // add the meters
468 ((DefaultMeter) m1).setState(MeterState.PENDING_ADD);
469 ((DefaultMeter) m2).setState(MeterState.PENDING_ADD);
470 ((DefaultMeter) m3).setState(MeterState.PENDING_ADD);
471 meterStore.storeMeter(m1);
472 meterStore.storeMeter(m2);
473 meterStore.storeMeter(m3);
474 assertThat(3, is(meterStore.getAllMeters().size()));
475
476 meterStore.purgeMeters(did1, APP_ID_2);
477 // Verify delete
478 MeterKey keyTwo = MeterKey.key(did1, mid2);
479 assertThat(2, is(meterStore.getAllMeters().size()));
480 assertThat(1, is(meterStore.getAllMeters(did1).size()));
481 assertThat(1, is(meterStore.getAllMeters(did2).size()));
482 assertNull(meterStore.getMeter(keyTwo));
483 }
484
485 /**
pierventre44220052020-09-22 12:51:06 +0200486 * Test getMeters API immutability.
487 */
488 @Test
489 public void testGetMetersImmutability() {
490 // Init the store
pierventre3b39bd82021-08-18 09:40:14 +0200491 initMeterStore(false);
pierventre44220052020-09-22 12:51:06 +0200492
493 // Simulate the allocation of an id
494 MeterId idOne = meterStore.allocateMeterId(did1);
495 // Verify the allocation
496 assertThat(mid1, is(idOne));
497 // Let's create a meter
498 Meter meterOne = DefaultMeter.builder()
499 .forDevice(did1)
500 .fromApp(APP_ID)
501 .withId(mid1)
502 .withUnit(Meter.Unit.KB_PER_SEC)
503 .withBands(Collections.singletonList(b1))
504 .build();
505 // Set the state
506 ((DefaultMeter) meterOne).setState(MeterState.PENDING_ADD);
507 // Store the meter
508 meterStore.storeMeter(meterOne);
509
510 // Verify the immutability
511 Collection<Meter> meters = meterStore.getAllMeters();
512 Collection<Meter> metersDevice = meterStore.getAllMeters(did1);
513 assertThat(1, is(meters.size()));
514 assertThat(1, is(metersDevice.size()));
515
516 MeterId idTwo = meterStore.allocateMeterId(did1);
517 // Verify the allocation
518 assertThat(mid2, is(idTwo));
519 // Let's create a meter
520 Meter meterTwo = DefaultMeter.builder()
521 .forDevice(did1)
522 .fromApp(APP_ID)
523 .withId(mid2)
524 .withUnit(Meter.Unit.KB_PER_SEC)
525 .withBands(Collections.singletonList(b1))
526 .build();
527 // Set the state
528 ((DefaultMeter) meterTwo).setState(MeterState.PENDING_ADD);
529 // Store the meter
530 meterStore.storeMeter(meterTwo);
531
532 assertThat(1, is(meters.size()));
533 assertThat(1, is(metersDevice.size()));
534
535 meters = meterStore.getAllMeters();
536 metersDevice = meterStore.getAllMeters(did1);
537 assertThat(2, is(meters.size()));
538 assertThat(2, is(metersDevice.size()));
pierventre3b39bd82021-08-18 09:40:14 +0200539 }
pierventre44220052020-09-22 12:51:06 +0200540
pierventre3b39bd82021-08-18 09:40:14 +0200541 /**
542 * Test invalid allocation of a cell id.
543 */
544 @Test(expected = IllegalArgumentException.class)
545 public void testInvalidCellId() {
546 initMeterStore(true);
547 // MF defines an end index equals to 10
548 Meter meterBad = DefaultMeter.builder()
549 .forDevice(did3)
550 .fromApp(APP_ID)
551 .withCellId(invalidCid)
552 .withUnit(Meter.Unit.KB_PER_SEC)
553 .withBands(Collections.singletonList(b1))
554 .build();
555 ((DefaultMeter) meterBad).setState(MeterState.PENDING_ADD);
556 meterStore.storeMeter(meterBad);
557 }
pierventre44220052020-09-22 12:51:06 +0200558
pierventre3b39bd82021-08-18 09:40:14 +0200559 /**
560 * Test enabling user defined index mode.
561 */
562 @Test
563 public void testEnableUserDefinedIndex() {
564 initMeterStore(false);
565 assertTrue(meterStore.userDefinedIndexMode(true));
566 }
567
568 /**
569 * Test invalid enabling user defined index mode.
570 */
571 @Test
572 public void testInvalidEnableUserDefinedIndex() {
573 testStoreMeter();
574 assertFalse(meterStore.userDefinedIndexMode(true));
575 }
576
577 /**
578 * Test disabling user defined index mode.
579 */
580 @Test
581 public void testDisableUserDefinedIndex() {
582 initMeterStore(true);
583 assertFalse(meterStore.userDefinedIndexMode(false));
584 }
585
586 /**
587 * Test store meter in user defined index mode.
588 */
589 @Test
590 public void testStoreMeterInUserDefinedIndexMode() {
591 initMeterStore(true);
592 // Let's create a meter
593 Meter meterOne = DefaultMeter.builder()
594 .forDevice(did3)
595 .fromApp(APP_ID)
596 .withCellId(cid4)
597 .withUnit(Meter.Unit.KB_PER_SEC)
598 .withBands(Collections.singletonList(b1))
599 .build();
600 // Set the state
601 ((DefaultMeter) meterOne).setState(MeterState.PENDING_ADD);
602 // Store the meter
603 meterStore.storeMeter(meterOne);
604 // Let's create meter key
605 MeterKey meterKey = MeterKey.key(did3, cid4);
606 // Verify the store
607 assertThat(1, is(meterStore.getAllMeters().size()));
608 assertThat(1, is(meterStore.getAllMeters(did3).size()));
609 assertThat(m4, is(meterStore.getMeter(meterKey)));
610 }
611
612 /**
613 * Test invalid disabling user defined index mode.
614 */
615 @Test
616 public void testInvalidDisableUserDefinedIndex() {
617 testStoreMeterInUserDefinedIndexMode();
618 assertTrue(meterStore.userDefinedIndexMode(false));
619 }
620
621 /**
622 * Test allocation of meter ids in user defined index mode.
623 */
624 @Test
625 public void testAllocateIdInUserDefinedIndexMode() {
626 initMeterStore(true);
627 assertNull(meterStore.allocateMeterId(did1));
628 }
629
630 /**
631 * Test free of meter ids in user defined index mode.
632 */
633 @Test
634 public void testFreeIdInUserMode() {
635 initMeterStore(true);
636 // Free the id and expect not being available
637 meterStore.freeMeterId(did1, mid1);
638 MeterTableKey globalKey = MeterTableKey.key(did1, MeterScope.globalScope());
639 assertNotNull(meterStore.availableMeterIds.get(globalKey));
640 assertTrue(meterStore.availableMeterIds.get(globalKey).isEmpty());
641 }
642
643 /**
644 * Test delete meter in user defined index mode.
645 */
646 @Test
647 public void testDeleteMeterInUserDefinedIndexMode() {
648 initMeterStore(true);
649 Meter meterOne = DefaultMeter.builder()
650 .forDevice(did3)
651 .fromApp(APP_ID)
652 .withCellId(cid4)
653 .withUnit(Meter.Unit.KB_PER_SEC)
654 .withBands(Collections.singletonList(b1))
655 .build();
656 ((DefaultMeter) meterOne).setState(MeterState.PENDING_ADD);
657 meterStore.storeMeter(meterOne);
658
659 ((DefaultMeter) meterOne).setState(MeterState.PENDING_REMOVE);
660 MeterKey meterKey = MeterKey.key(did3, cid4);
661 meterStore.deleteMeter(meterOne);
662 CompletableFuture<Void> future = CompletableFuture.runAsync(
663 () -> meterStore.purgeMeter(meterOne)
664 );
665
666 try {
667 future.get();
668 } catch (InterruptedException | ExecutionException e) {
669 e.printStackTrace();
670 }
671 assertThat(0, is(meterStore.getAllMeters().size()));
672 assertThat(0, is(meterStore.getAllMeters(did3).size()));
673 assertNull(meterStore.getMeter(meterKey));
674 MeterTableKey globalKey = MeterTableKey.key(did1, MeterScope.globalScope());
675 assertNotNull(meterStore.availableMeterIds.get(globalKey));
676 assertTrue(meterStore.availableMeterIds.get(globalKey).isEmpty());
pierventre44220052020-09-22 12:51:06 +0200677 }
678
Pier Luigif094c612017-10-14 12:15:02 +0200679 // Test class for driver service.
680 private class TestDriverService extends DriverServiceAdapter {
681 @Override
682 public DriverHandler createHandler(DeviceId deviceId, String... credentials) {
683 return deviceId.equals(did3) ? new TestDriverHandler() : null;
684 }
685 }
686
687 // Test class for driver handler.
688 private class TestDriverHandler implements DriverHandler {
689
690 @Override
691 public Driver driver() {
692 return null;
693 }
694
695 @Override
696 public DriverData data() {
697 return null;
698 }
699
700 @Override
701 @SuppressWarnings("unchecked")
702 public <T extends Behaviour> T behaviour(Class<T> behaviourClass) {
703 return (T) new TestMeterQuery();
704 }
705
706 @Override
707 public <T> T get(Class<T> serviceClass) {
708 return null;
709 }
710
711 @Override
712 public boolean hasBehaviour(Class<? extends Behaviour> behaviourClass) {
713 return true;
714 }
715 }
716
717 // Test meter query
718 private class TestMeterQuery implements MeterQuery {
719
720 @Override
721 public DriverData data() {
722 return null;
723 }
724
725 @Override
726 public void setData(DriverData data) {
727
728 }
729 @Override
730 public DriverHandler handler() {
731 return null;
732 }
733
734 @Override
735 public void setHandler(DriverHandler handler) {
736
737 }
738
739 @Override
740 public long getMaxMeters() {
741 return 100;
742 }
743 }
744
745}