1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 package org.apache.commons.io.function;
19
20 import static org.junit.jupiter.api.Assertions.assertArrayEquals;
21 import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
22 import static org.junit.jupiter.api.Assertions.assertEquals;
23 import static org.junit.jupiter.api.Assertions.assertFalse;
24 import static org.junit.jupiter.api.Assertions.assertNotNull;
25 import static org.junit.jupiter.api.Assertions.assertNull;
26 import static org.junit.jupiter.api.Assertions.assertThrows;
27 import static org.junit.jupiter.api.Assertions.assertTrue;
28
29 import java.io.IOException;
30 import java.util.Arrays;
31 import java.util.Collections;
32 import java.util.NoSuchElementException;
33 import java.util.concurrent.atomic.AtomicInteger;
34 import java.util.concurrent.atomic.AtomicReference;
35 import java.util.stream.Collectors;
36 import java.util.stream.DoubleStream;
37 import java.util.stream.IntStream;
38 import java.util.stream.LongStream;
39 import java.util.stream.Stream;
40
41 import org.apache.commons.lang3.JavaVersion;
42 import org.apache.commons.lang3.SystemUtils;
43 import org.junit.jupiter.api.Test;
44
45
46
47
48 public class IOStreamTest {
49
50 private static final boolean AT_LEAST_JAVA_11 = SystemUtils.isJavaVersionAtLeast(JavaVersion.JAVA_11);
51 private static final boolean AT_LEAST_JAVA_17 = SystemUtils.isJavaVersionAtLeast(JavaVersion.JAVA_17);
52
53 private void compareAndSetIO(final AtomicReference<String> ref, final String expected, final String update) throws IOException {
54 TestUtils.compareAndSetThrowsIO(ref, expected, update);
55 }
56
57 private void compareAndSetRE(final AtomicReference<String> ref, final String expected, final String update) {
58 TestUtils.compareAndSetThrowsRE(ref, expected, update);
59 }
60
61 private void ioExceptionOnNull(final Object test) throws IOException {
62 if (test == null) {
63 throw new IOException("Unexpected");
64 }
65 }
66
67 @SuppressWarnings("resource")
68 @Test
69 public void testAdapt() {
70 assertEquals(0, IOStream.adapt((Stream<?>) null).count());
71 assertEquals(0, IOStream.adapt(Stream.empty()).count());
72 assertEquals(1, IOStream.adapt(Stream.of("A")).count());
73 }
74
75 @SuppressWarnings("resource")
76 @Test
77 public void testAllMatch() throws IOException {
78 assertThrows(IOException.class, () -> IOStream.of("A", "B").allMatch(TestConstants.THROWING_IO_PREDICATE));
79 assertTrue(IOStream.of("A", "B").allMatch(IOPredicate.alwaysTrue()));
80 assertFalse(IOStream.of("A", "B").allMatch(IOPredicate.alwaysFalse()));
81 }
82
83 @SuppressWarnings("resource")
84 @Test
85 public void testAnyMatch() throws IOException {
86 assertThrows(IOException.class, () -> IOStream.of("A", "B").anyMatch(TestConstants.THROWING_IO_PREDICATE));
87 assertTrue(IOStream.of("A", "B").anyMatch(IOPredicate.alwaysTrue()));
88 assertFalse(IOStream.of("A", "B").anyMatch(IOPredicate.alwaysFalse()));
89 }
90
91 @Test
92 public void testClose() {
93 IOStream.of("A", "B").close();
94 }
95
96 @SuppressWarnings("resource")
97 @Test
98 public void testCollectCollectorOfQsuperTAR() {
99
100 IOStream.of("A", "B").collect(Collectors.toList());
101 }
102
103 @SuppressWarnings("resource")
104 @Test
105 public void testCollectSupplierOfRBiConsumerOfRQsuperTBiConsumerOfRR() throws IOException {
106
107 IOStream.of("A", "B").collect(() -> "A", (t, u) -> {
108 }, (t, u) -> {
109 });
110 assertEquals("AB", Stream.of("A", "B").collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString());
111 assertEquals("AB", IOStream.of("A", "B").collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString());
112
113 assertThrows(IOException.class, () -> IOStream.of("A", "B").collect(TestUtils.throwingIOSupplier(), (t, u) -> {
114 }, (t, u) -> {
115 }));
116 assertThrows(IOException.class, () -> IOStream.of("A", "B").collect(() -> "A", TestUtils.throwingIOBiConsumer(), (t, u) -> {
117 }));
118 }
119
120 @SuppressWarnings("resource")
121 @Test
122 public void testCount() {
123 assertEquals(0, IOStream.of().count());
124 assertEquals(1, IOStream.of("A").count());
125 assertEquals(2, IOStream.of("A", "B").count());
126 assertEquals(3, IOStream.of("A", "B", "C").count());
127 assertEquals(3, IOStream.of("A", "A", "A").count());
128 }
129
130 @SuppressWarnings("resource")
131 @Test
132 public void testDistinct() {
133 assertEquals(0, IOStream.of().distinct().count());
134 assertEquals(1, IOStream.of("A").distinct().count());
135 assertEquals(2, IOStream.of("A", "B").distinct().count());
136 assertEquals(3, IOStream.of("A", "B", "C").distinct().count());
137 assertEquals(1, IOStream.of("A", "A", "A").distinct().count());
138 }
139
140 @SuppressWarnings("resource")
141 @Test
142 public void testEmpty() throws IOException {
143 assertEquals(0, Stream.empty().count());
144 assertEquals(0, IOStream.empty().count());
145 IOStream.empty().forEach(TestUtils.throwingIOConsumer());
146 }
147
148 @SuppressWarnings("resource")
149 @Test
150 public void testFilter() throws IOException {
151 IOStream.of("A").filter(TestConstants.THROWING_IO_PREDICATE);
152
153 assertThrows(IOException.class, () -> IOStream.of("A").filter(TestConstants.THROWING_IO_PREDICATE).count());
154
155 assertThrows(IOException.class, () -> IOStream.of("A").filter(e -> {
156 throw new IOException("Failure");
157 }).count());
158 }
159
160 @SuppressWarnings("resource")
161 @Test
162 public void testFindAny() throws IOException {
163
164 assertThrows(IOException.class, () -> IOStream.of("A").filter(TestConstants.THROWING_IO_PREDICATE).findAny());
165
166 assertThrows(IOException.class, () -> IOStream.of("A").filter(e -> {
167 throw new IOException("Failure");
168 }).findAny());
169
170 assertTrue(IOStream.of("A", "B").filter(IOPredicate.alwaysTrue()).findAny().isPresent());
171 assertFalse(IOStream.of("A", "B").filter(IOPredicate.alwaysFalse()).findAny().isPresent());
172 }
173
174 @SuppressWarnings("resource")
175 @Test
176 public void testFindFirst() throws IOException {
177
178 assertThrows(IOException.class, () -> IOStream.of("A").filter(TestConstants.THROWING_IO_PREDICATE).findFirst());
179
180 assertThrows(IOException.class, () -> IOStream.of("A").filter(e -> {
181 throw new IOException("Failure");
182 }).findAny());
183
184 assertTrue(IOStream.of("A", "B").filter(IOPredicate.alwaysTrue()).findFirst().isPresent());
185 assertFalse(IOStream.of("A", "B").filter(IOPredicate.alwaysFalse()).findFirst().isPresent());
186 }
187
188 @SuppressWarnings("resource")
189 @Test
190 public void testFlatMap() throws IOException {
191 assertEquals(Arrays.asList("A", "B", "C", "D"),
192 IOStream.of(IOStream.of("A", "B"), IOStream.of("C", "D")).flatMap(IOFunction.identity()).collect(Collectors.toList()));
193 }
194
195 @SuppressWarnings("resource")
196 @Test
197 public void testFlatMapToDouble() throws IOException {
198 assertEquals('A' + 'B', IOStream.of("A", "B").flatMapToDouble(e -> DoubleStream.of(e.charAt(0))).sum());
199 }
200
201 @SuppressWarnings("resource")
202 @Test
203 public void testFlatMapToInt() throws IOException {
204 assertEquals('A' + 'B', IOStream.of("A", "B").flatMapToInt(e -> IntStream.of(e.charAt(0))).sum());
205 }
206
207 @SuppressWarnings("resource")
208 @Test
209 public void testFlatMapToLong() throws IOException {
210 assertEquals('A' + 'B', IOStream.of("A", "B").flatMapToLong(e -> LongStream.of(e.charAt(0))).sum());
211 }
212
213 @SuppressWarnings("resource")
214 @Test
215 public void testForaAllIOConsumer() throws IOException {
216
217 assertThrows(IOException.class, () -> IOStream.of("A").forAll(TestUtils.throwingIOConsumer()));
218
219 assertThrows(IOException.class, () -> IOStream.of("A").forAll(e -> {
220 throw new IOException("Failure");
221 }));
222 assertThrows(IOException.class, () -> IOStream.of("A", "B").forAll(TestUtils.throwingIOConsumer()));
223 final StringBuilder sb = new StringBuilder();
224 IOStream.of("A", "B").forAll(sb::append);
225 assertEquals("AB", sb.toString());
226 }
227
228 @SuppressWarnings("resource")
229 @Test
230 public void testForaAllIOConsumerBiFunction() throws IOException {
231
232 assertThrows(IOException.class, () -> IOStream.of("A").forAll(TestUtils.throwingIOConsumer(), (i, e) -> e));
233
234 assertThrows(IOException.class, () -> IOStream.of("A").forAll(e -> {
235 throw new IOException("Failure");
236 }, (i, e) -> e));
237 assertThrows(IOException.class, () -> IOStream.of("A", "B").forAll(TestUtils.throwingIOConsumer(), (i, e) -> e));
238 final StringBuilder sb = new StringBuilder();
239 IOStream.of("A", "B").forAll(sb::append, (i, e) -> e);
240 assertEquals("AB", sb.toString());
241 }
242
243 @SuppressWarnings("resource")
244 @Test
245 public void testForaAllIOConsumerBiFunctionNull() throws IOException {
246
247 assertDoesNotThrow(() -> IOStream.of("A").forAll(TestUtils.throwingIOConsumer(), null));
248
249 assertDoesNotThrow(() -> IOStream.of("A").forAll(e -> {
250 throw new IOException("Failure");
251 }, null));
252 assertDoesNotThrow(() -> IOStream.of("A", "B").forAll(TestUtils.throwingIOConsumer(), null));
253 final StringBuilder sb = new StringBuilder();
254 IOStream.of("A", "B").forAll(sb::append, null);
255 assertEquals("AB", sb.toString());
256 }
257
258 @SuppressWarnings("resource")
259 @Test
260 public void testForEachIOConsumerOfQsuperT() throws IOException {
261
262 assertThrows(IOException.class, () -> IOStream.of("A").forEach(TestUtils.throwingIOConsumer()));
263
264 assertThrows(IOException.class, () -> IOStream.of("A").forEach(e -> {
265 throw new IOException("Failure");
266 }));
267 assertThrows(IOException.class, () -> IOStream.of("A", "B").forEach(TestUtils.throwingIOConsumer()));
268 final StringBuilder sb = new StringBuilder();
269 IOStream.of("A", "B").forEachOrdered(sb::append);
270 assertEquals("AB", sb.toString());
271 }
272
273 @SuppressWarnings("resource")
274 @Test
275 public void testForEachOrdered() throws IOException {
276
277 assertThrows(IOException.class, () -> IOStream.of("A").forEach(TestUtils.throwingIOConsumer()));
278
279 assertThrows(IOException.class, () -> IOStream.of("A").forEach(e -> {
280 throw new IOException("Failure");
281 }));
282 assertThrows(IOException.class, () -> IOStream.of("A", "B").forEach(TestUtils.throwingIOConsumer()));
283 final StringBuilder sb = new StringBuilder();
284 IOStream.of("A", "B").forEachOrdered(sb::append);
285 assertEquals("AB", sb.toString());
286 }
287
288 @SuppressWarnings("resource")
289 @Test
290 public void testIsParallel() {
291 assertFalse(IOStream.of("A", "B").isParallel());
292 }
293
294 @SuppressWarnings("resource")
295 @Test
296 public void testIterateException() throws IOException {
297 final IOStream<Long> stream = IOStream.iterate(1L, TestUtils.throwingIOUnaryOperator());
298 final IOIterator<Long> iterator = stream.iterator();
299 assertEquals(1L, iterator.next());
300 assertThrows(NoSuchElementException.class, () -> iterator.next());
301 }
302
303 @SuppressWarnings("resource")
304 @Test
305 public void testIterateLong() throws IOException {
306 final IOStream<Long> stream = IOStream.iterate(1L, i -> i + 1);
307 final IOIterator<Long> iterator = stream.iterator();
308 assertEquals(1L, iterator.next());
309 assertEquals(2L, iterator.next());
310 }
311
312 @SuppressWarnings("resource")
313 @Test
314 public void testIterator() throws IOException {
315 final AtomicInteger ref = new AtomicInteger();
316 IOStream.of("A", "B").iterator().forEachRemaining(e -> ref.incrementAndGet());
317 assertEquals(2, ref.get());
318 }
319
320 @SuppressWarnings("resource")
321 @Test
322 public void testLimit() {
323 assertEquals(1, IOStream.of("A", "B").limit(1).count());
324 }
325
326 @SuppressWarnings("resource")
327 @Test
328 public void testMap() throws IOException {
329 assertEquals(Arrays.asList("AC", "BC"), IOStream.of("A", "B").map(e -> e + "C").collect(Collectors.toList()));
330 }
331
332 @SuppressWarnings("resource")
333 @Test
334 public void testMapToDouble() {
335 assertArrayEquals(new double[] { Double.parseDouble("1"), Double.parseDouble("2") }, IOStream.of("1", "2").mapToDouble(Double::parseDouble).toArray());
336 }
337
338 @SuppressWarnings("resource")
339 @Test
340 public void testMapToInt() {
341 assertArrayEquals(new int[] { 1, 2 }, IOStream.of("1", "2").mapToInt(Integer::parseInt).toArray());
342 }
343
344 @SuppressWarnings("resource")
345 @Test
346 public void testMapToLong() {
347 assertArrayEquals(new long[] { 1L, 2L }, IOStream.of("1", "2").mapToLong(Long::parseLong).toArray());
348 }
349
350 @SuppressWarnings("resource")
351 @Test
352 public void testMax() throws IOException {
353 assertEquals("B", IOStream.of("A", "B").max(String::compareTo).get());
354 }
355
356 @SuppressWarnings("resource")
357 @Test
358 public void testMin() throws IOException {
359 assertEquals("A", IOStream.of("A", "B").min(String::compareTo).get());
360 }
361
362 @SuppressWarnings("resource")
363 @Test
364 public void testNoneMatch() throws IOException {
365 assertThrows(IOException.class, () -> IOStream.of("A", "B").noneMatch(TestConstants.THROWING_IO_PREDICATE));
366 assertFalse(IOStream.of("A", "B").noneMatch(IOPredicate.alwaysTrue()));
367 assertTrue(IOStream.of("A", "B").noneMatch(IOPredicate.alwaysFalse()));
368 }
369
370 @SuppressWarnings("resource")
371 @Test
372 public void testOfArray() {
373 assertEquals(0, IOStream.of((String[]) null).count());
374 assertEquals(0, IOStream.of().count());
375 assertEquals(2, IOStream.of("A", "B").count());
376 }
377
378 @SuppressWarnings("resource")
379 @Test
380 public void testOfIterable() {
381 assertEquals(0, IOStream.of((Iterable<?>) null).count());
382 assertEquals(0, IOStream.of(Collections.emptyList()).count());
383 assertEquals(0, IOStream.of(Collections.emptySet()).count());
384 assertEquals(0, IOStream.of(Collections.emptySortedSet()).count());
385 assertEquals(1, IOStream.of(Arrays.asList("a")).count());
386 assertEquals(2, IOStream.of(Arrays.asList("a", "b")).count());
387 }
388
389 @SuppressWarnings("resource")
390 @Test
391 public void testOfOne() {
392 assertEquals(1, IOStream.of("A").count());
393 }
394
395 @SuppressWarnings("resource")
396 @Test
397 public void testOnClose() throws IOException {
398 assertThrows(IOException.class, () -> IOStream.of("A").onClose(TestConstants.THROWING_IO_RUNNABLE).close());
399 final AtomicReference<String> ref = new AtomicReference<>();
400 IOStream.of("A").onClose(() -> compareAndSetIO(ref, null, "new1")).close();
401 assertEquals("new1", ref.get());
402 }
403
404 @SuppressWarnings("resource")
405 @Test
406 public void testOnCloseMultipleHandlers() {
407
408 final AtomicReference<String> ref = new AtomicReference<>();
409
410 ref.set(null);
411 final RuntimeException thrownRE = assertThrows(RuntimeException.class, () -> {
412
413 final Stream<String> stream = Stream.of("A")
414 .onClose(() -> compareAndSetRE(ref, null, "new1"))
415 .onClose(() -> TestConstants.throwRuntimeException("Failure 2"));
416
417 stream.close();
418 });
419 assertEquals("new1", ref.get());
420 assertEquals("Failure 2", thrownRE.getMessage());
421 assertEquals(0, thrownRE.getSuppressed().length);
422
423 ref.set(null);
424 final IOException thrownIO = assertThrows(IOException.class, () -> {
425
426 final IOStream<String> stream = IOStream.of("A")
427 .onClose(() -> compareAndSetIO(ref, null, "new1"))
428 .onClose(() -> TestConstants.throwIOException("Failure 2"));
429
430 stream.close();
431 });
432 assertEquals("new1", ref.get());
433 assertEquals("Failure 2", thrownIO.getMessage());
434 assertEquals(0, thrownIO.getSuppressed().length);
435
436 final IOException thrownB = assertThrows(IOException.class, () -> {
437
438 final IOStream<String> stream = IOStream.of("A")
439 .onClose(TestConstants.throwIOException("Failure 1"))
440 .onClose(TestConstants.throwIOException("Failure 2"));
441
442 stream.close();
443 });
444 assertEquals("Failure 1", thrownB.getMessage());
445 assertEquals(0, thrownB.getSuppressed().length);
446 }
447
448 @SuppressWarnings("resource")
449 @Test
450 public void testParallel() {
451 assertEquals(2, IOStream.of("A", "B").parallel().count());
452 }
453
454 @SuppressWarnings("resource")
455 @Test
456 public void testPeek() throws IOException {
457 final AtomicReference<String> ref = new AtomicReference<>();
458
459 assertEquals(1, Stream.of("A").peek(e -> compareAndSetRE(ref, null, e)).count());
460
461 assertEquals(AT_LEAST_JAVA_11 ? null : "A", ref.get());
462 if (AT_LEAST_JAVA_11) {
463 assertEquals(1, IOStream.of("B").peek(e -> compareAndSetRE(ref, null, e)).count());
464 assertEquals(1, IOStream.of("B").peek(e -> compareAndSetIO(ref, null, e)).count());
465 assertNull(ref.get());
466 } else {
467
468 assertThrows(RuntimeException.class, () -> IOStream.of("B").peek(e -> compareAndSetRE(ref, null, e)).count());
469 assertThrows(IOException.class, () -> IOStream.of("B").peek(e -> compareAndSetIO(ref, null, e)).count());
470 assertEquals("A", ref.get());
471 }
472 }
473
474 @SuppressWarnings("resource")
475 @Test
476 public void testReduceBinaryOperatorOfT() throws IOException {
477 assertEquals("AB", IOStream.of("A", "B").reduce((t, u) -> t + u).get());
478 assertEquals(TestConstants.ABS_PATH_A.toRealPath(),
479 IOStream.of(TestConstants.ABS_PATH_A, TestConstants.ABS_PATH_B).reduce((t, u) -> t.toRealPath()).get());
480 }
481
482 @SuppressWarnings("resource")
483 @Test
484 public void testReduceTBinaryOperatorOfT() throws IOException {
485 assertEquals("_AB", IOStream.of("A", "B").reduce("_", (t, u) -> t + u));
486 assertEquals(TestConstants.ABS_PATH_A.toRealPath(),
487 IOStream.of(TestConstants.ABS_PATH_A, TestConstants.ABS_PATH_B).reduce(TestConstants.ABS_PATH_A, (t, u) -> t.toRealPath()));
488 }
489
490 @SuppressWarnings("resource")
491 @Test
492 public void testReduceUBiFunctionOfUQsuperTUBinaryOperatorOfU() throws IOException {
493 assertEquals("_AB", IOStream.of("A", "B").reduce("_", (t, u) -> t + u, (t, u) -> t + u));
494 assertEquals(TestConstants.ABS_PATH_A.toRealPath(), IOStream.of(TestConstants.ABS_PATH_A, TestConstants.ABS_PATH_B).reduce(TestConstants.ABS_PATH_A,
495 (t, u) -> t.toRealPath(), (t, u) -> u.toRealPath()));
496 }
497
498 @SuppressWarnings("resource")
499 @Test
500 public void testSequential() {
501 assertEquals(2, IOStream.of("A", "B").sequential().count());
502 }
503
504 @SuppressWarnings("resource")
505 @Test
506 public void testSkip() throws IOException {
507 final AtomicReference<String> ref = new AtomicReference<>();
508 assertEquals(1, Stream.of("A", "B").skip(1).peek(e -> compareAndSetRE(ref, null, e)).count());
509
510 assertEquals(AT_LEAST_JAVA_17 ? null : "B", ref.get());
511 if (AT_LEAST_JAVA_17) {
512 assertEquals(1, IOStream.of("C", "D").skip(1).peek(e -> compareAndSetRE(ref, null, e)).count());
513 assertEquals(1, IOStream.of("C", "D").skip(1).peek(e -> compareAndSetIO(ref, null, e)).count());
514 assertNull(ref.get());
515 } else {
516 if (AT_LEAST_JAVA_11) {
517 assertThrows(RuntimeException.class, () -> IOStream.of("C", "D").skip(1).peek(e -> compareAndSetRE(ref, null, e)).count());
518 assertThrows(IOException.class, () -> IOStream.of("C", "D").skip(1).peek(e -> compareAndSetIO(ref, null, e)).count());
519 } else {
520 assertThrows(RuntimeException.class, () -> IOStream.of("C", "D").skip(1).peek(e -> compareAndSetRE(ref, null, e)).count());
521 assertThrows(IOException.class, () -> IOStream.of("C", "D").skip(1).peek(e -> compareAndSetIO(ref, null, e)).count());
522 }
523 assertEquals("B", ref.get());
524 }
525 }
526
527 @SuppressWarnings("resource")
528 @Test
529 public void testSorted() throws IOException {
530 assertEquals(Arrays.asList("A", "B", "C", "D"), IOStream.of("D", "A", "B", "C").sorted().collect(Collectors.toList()));
531 assertEquals(Arrays.asList("A", "B", "C", "D"), IOStream.of("D", "A", "B", "C").sorted().peek(this::ioExceptionOnNull).collect(Collectors.toList()));
532 }
533
534 @SuppressWarnings("resource")
535 @Test
536 public void testSortedComparatorOfQsuperT() throws IOException {
537 assertEquals(Arrays.asList("A", "B", "C", "D"), IOStream.of("D", "A", "B", "C").sorted(String::compareTo).collect(Collectors.toList()));
538 assertEquals(Arrays.asList("A", "B", "C", "D"),
539 IOStream.of("D", "A", "B", "C").sorted(String::compareTo).peek(this::ioExceptionOnNull).collect(Collectors.toList()));
540 }
541
542 @SuppressWarnings("resource")
543 @Test
544 public void testSpliterator() {
545 final AtomicInteger ref = new AtomicInteger();
546 IOStream.of("A", "B").spliterator().forEachRemaining(e -> ref.incrementAndGet());
547 assertEquals(2, ref.get());
548 }
549
550 @SuppressWarnings("resource")
551 @Test
552 public void testToArray() {
553 assertArrayEquals(new String[] { "A", "B" }, IOStream.of("A", "B").toArray());
554 }
555
556 @SuppressWarnings("resource")
557 @Test
558 public void testToArrayIntFunctionOfA() {
559 assertArrayEquals(new String[] { "A", "B" }, IOStream.of("A", "B").toArray(String[]::new));
560 }
561
562 @SuppressWarnings("resource")
563 @Test
564 public void testUnordered() {
565
566 assertArrayEquals(new String[] { "A", "B" }, Stream.of("A", "B").unordered().toArray());
567
568 assertArrayEquals(new String[] { "A", "B" }, IOStream.of("A", "B").unordered().toArray());
569 }
570
571 @SuppressWarnings("resource")
572 @Test
573 public void testUnwrap() {
574 final Stream<String> unwrap = IOStream.of("A", "B").unwrap();
575 assertNotNull(unwrap);
576 assertEquals(2, unwrap.count());
577 }
578
579 }