ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/CompletableFutureTest.java
(Generate patch)

Comparing jsr166/src/test/tck/CompletableFutureTest.java (file contents):
Revision 1.57 by jsr166, Mon Jun 2 22:48:50 2014 UTC vs.
Revision 1.61 by jsr166, Wed Jun 4 04:34:49 2014 UTC

# Line 320 | Line 320 | public class CompletableFutureTest exten
320          checkCompletedNormally(f, "test");
321      }
322  
323 <    // Choose non-commutative actions for better coverage
324 <
325 <    // A non-commutative function that handles and produces null values as well.
326 <    static Integer subtract(Integer x, Integer y) {
327 <        return (x == null && y == null) ? null :
328 <            ((x == null) ? 42 : x.intValue())
329 <            - ((y == null) ? 99 : y.intValue());
323 >    static final class IntegerSupplier implements Supplier<Integer> {
324 >        final ExecutionMode m;
325 >        int invocationCount = 0;
326 >        final Integer value;
327 >        IntegerSupplier(ExecutionMode m, Integer value) {
328 >            this.m = m;
329 >            this.value = value;
330 >        }
331 >        public Integer get() {
332 >            m.checkExecutionMode();
333 >            invocationCount++;
334 >            return value;
335 >        }
336      }
337  
338      // A function that handles and produces null values as well.
# Line 334 | Line 340 | public class CompletableFutureTest exten
340          return (x == null) ? null : x + 1;
341      }
342  
337    static final Supplier<Integer> supplyOne =
338        () -> Integer.valueOf(1);
339    static final Function<Integer, Integer> inc =
340        (Integer x) -> Integer.valueOf(x.intValue() + 1);
341    static final BiFunction<Integer, Integer, Integer> subtract =
342        (Integer x, Integer y) -> subtract(x, y);
343      static final class IncAction implements Consumer<Integer> {
344          int invocationCount = 0;
345          Integer value;
# Line 359 | Line 359 | public class CompletableFutureTest exten
359              return value = inc(x);
360          }
361      }
362 +
363 +    // Choose non-commutative actions for better coverage
364 +    // A non-commutative function that handles and produces null values as well.
365 +    static Integer subtract(Integer x, Integer y) {
366 +        return (x == null && y == null) ? null :
367 +            ((x == null) ? 42 : x.intValue())
368 +            - ((y == null) ? 99 : y.intValue());
369 +    }
370 +
371      static final class SubtractAction implements BiConsumer<Integer, Integer> {
372          final ExecutionMode m;
373          int invocationCount = 0;
# Line 383 | Line 392 | public class CompletableFutureTest exten
392              return value = subtract(x, y);
393          }
394      }
395 +
396      static final class Noop implements Runnable {
397          final ExecutionMode m;
398          int invocationCount = 0;
# Line 496 | Line 506 | public class CompletableFutureTest exten
506  
507      /**
508       * Permits the testing of parallel code for the 3 different
509 <     * execution modes without repeating all the testing code.
509 >     * execution modes without copy/pasting all the test methods.
510       */
511      enum ExecutionMode {
512          DEFAULT {
513              public void checkExecutionMode() {
514 +                assertFalse(ThreadExecutor.startedCurrentThread());
515                  assertNull(ForkJoinTask.getPool());
516              }
517              public CompletableFuture<Void> runAsync(Runnable a) {
518                  throw new UnsupportedOperationException();
519              }
520 +            public <U> CompletableFuture<U> supplyAsync(Supplier<U> a) {
521 +                throw new UnsupportedOperationException();
522 +            }
523              public <T> CompletableFuture<Void> thenRun
524                  (CompletableFuture<T> f, Runnable a) {
525                  return f.thenRun(a);
# Line 577 | Line 591 | public class CompletableFutureTest exten
591              public CompletableFuture<Void> runAsync(Runnable a) {
592                  return CompletableFuture.runAsync(a);
593              }
594 +            public <U> CompletableFuture<U> supplyAsync(Supplier<U> a) {
595 +                return CompletableFuture.supplyAsync(a);
596 +            }
597              public <T> CompletableFuture<Void> thenRun
598                  (CompletableFuture<T> f, Runnable a) {
599                  return f.thenRunAsync(a);
# Line 647 | Line 664 | public class CompletableFutureTest exten
664              public CompletableFuture<Void> runAsync(Runnable a) {
665                  return CompletableFuture.runAsync(a, new ThreadExecutor());
666              }
667 +            public <U> CompletableFuture<U> supplyAsync(Supplier<U> a) {
668 +                return CompletableFuture.supplyAsync(a, new ThreadExecutor());
669 +            }
670              public <T> CompletableFuture<Void> thenRun
671                  (CompletableFuture<T> f, Runnable a) {
672                  return f.thenRunAsync(a, new ThreadExecutor());
# Line 712 | Line 732 | public class CompletableFutureTest exten
732  
733          public abstract void checkExecutionMode();
734          public abstract CompletableFuture<Void> runAsync(Runnable a);
735 +        public abstract <U> CompletableFuture<U> supplyAsync(Supplier<U> a);
736          public abstract <T> CompletableFuture<Void> thenRun
737              (CompletableFuture<T> f, Runnable a);
738          public abstract <T> CompletableFuture<Void> thenAccept
# Line 998 | Line 1019 | public class CompletableFutureTest exten
1019      /**
1020       * supplyAsync completes with result of supplier
1021       */
1022 <    public void testSupplyAsync() {
1023 <        CompletableFuture<Integer> f;
1024 <        f = CompletableFuture.supplyAsync(supplyOne);
1025 <        assertEquals(f.join(), one);
1026 <        checkCompletedNormally(f, one);
1027 <    }
1028 <
1029 <    /**
1030 <     * supplyAsync with executor completes with result of supplier
1031 <     */
1032 <    public void testSupplyAsync2() {
1033 <        CompletableFuture<Integer> f;
1034 <        f = CompletableFuture.supplyAsync(supplyOne, new ThreadExecutor());
1035 <        assertEquals(f.join(), one);
1015 <        checkCompletedNormally(f, one);
1016 <    }
1022 >    public void testSupplyAsync_normalCompletion() {
1023 >        ExecutionMode[] executionModes = {
1024 >            ExecutionMode.ASYNC,
1025 >            ExecutionMode.EXECUTOR,
1026 >        };
1027 >        for (ExecutionMode m : executionModes)
1028 >        for (Integer v1 : new Integer[] { 1, null })
1029 >    {
1030 >        final IntegerSupplier r = new IntegerSupplier(m, v1);
1031 >        final CompletableFuture<Integer> f = m.supplyAsync(r);
1032 >        assertSame(v1, f.join());
1033 >        checkCompletedNormally(f, v1);
1034 >        assertEquals(1, r.invocationCount);
1035 >    }}
1036  
1037      /**
1038       * Failing supplyAsync completes exceptionally
1039       */
1040 <    public void testSupplyAsync3() {
1041 <        FailingSupplier r = new FailingSupplier(ExecutionMode.ASYNC);
1042 <        CompletableFuture<Integer> f = CompletableFuture.supplyAsync(r);
1040 >    public void testSupplyAsync_exceptionalCompletion() {
1041 >        ExecutionMode[] executionModes = {
1042 >            ExecutionMode.ASYNC,
1043 >            ExecutionMode.EXECUTOR,
1044 >        };
1045 >        for (ExecutionMode m : executionModes)
1046 >    {
1047 >        FailingSupplier r = new FailingSupplier(m);
1048 >        CompletableFuture<Integer> f = m.supplyAsync(r);
1049          checkCompletedWithWrappedCFException(f);
1050          assertEquals(1, r.invocationCount);
1051 <    }
1051 >    }}
1052  
1053      // seq completion methods
1054  
# Line 1250 | Line 1275 | public class CompletableFutureTest exten
1275      }}
1276  
1277      /**
1278 <     * thenAccept result completes exceptionally if action does
1278 >     * thenAccept result completes exceptionally if source cancelled
1279       */
1280 <    public void testThenAccept_actionFailed() {
1280 >    public void testThenAccept_sourceCancelled() {
1281          for (ExecutionMode m : ExecutionMode.values())
1282          for (boolean createIncomplete : new boolean[] { true, false })
1283 <        for (Integer v1 : new Integer[] { 1, null })
1283 >        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1284      {
1285          final CompletableFuture<Integer> f = new CompletableFuture<>();
1286 <        final FailingConsumer r = new FailingConsumer(m);
1287 <        if (!createIncomplete) f.complete(v1);
1286 >        final IncAction r = new IncAction();
1287 >        if (!createIncomplete) assertTrue(f.cancel(mayInterruptIfRunning));
1288          final CompletableFuture<Void> g = m.thenAccept(f, r);
1289          if (createIncomplete) {
1290              checkIncomplete(g);
1291 <            f.complete(v1);
1291 >            assertTrue(f.cancel(mayInterruptIfRunning));
1292          }
1293  
1294 <        checkCompletedWithWrappedCFException(g);
1295 <        checkCompletedNormally(f, v1);
1294 >        checkCompletedWithWrappedCancellationException(g);
1295 >        checkCancelled(f);
1296 >        assertEquals(0, r.invocationCount);
1297      }}
1298  
1299      /**
1300 <     * thenAccept result completes exceptionally if source cancelled
1300 >     * thenAccept result completes exceptionally if action does
1301       */
1302 <    public void testThenAccept_sourceCancelled() {
1302 >    public void testThenAccept_actionFailed() {
1303          for (ExecutionMode m : ExecutionMode.values())
1304          for (boolean createIncomplete : new boolean[] { true, false })
1305 <        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1305 >        for (Integer v1 : new Integer[] { 1, null })
1306      {
1307          final CompletableFuture<Integer> f = new CompletableFuture<>();
1308 <        final IncAction r = new IncAction();
1309 <        if (!createIncomplete) assertTrue(f.cancel(mayInterruptIfRunning));
1308 >        final FailingConsumer r = new FailingConsumer(m);
1309 >        if (!createIncomplete) f.complete(v1);
1310          final CompletableFuture<Void> g = m.thenAccept(f, r);
1311          if (createIncomplete) {
1312              checkIncomplete(g);
1313 <            assertTrue(f.cancel(mayInterruptIfRunning));
1313 >            f.complete(v1);
1314          }
1315  
1316 <        checkCompletedWithWrappedCancellationException(g);
1317 <        checkCancelled(f);
1292 <        assertEquals(0, r.invocationCount);
1316 >        checkCompletedWithWrappedCFException(g);
1317 >        checkCompletedNormally(f, v1);
1318      }}
1319  
1320      /**
# Line 1354 | Line 1379 | public class CompletableFutureTest exten
1379      }}
1380  
1381      /**
1357     * thenCombine result completes exceptionally if action does
1358     */
1359    public void testThenCombine_actionFailed() {
1360        for (ExecutionMode m : ExecutionMode.values())
1361        for (boolean fFirst : new boolean[] { true, false })
1362        for (Integer v1 : new Integer[] { 1, null })
1363        for (Integer v2 : new Integer[] { 2, null })
1364    {
1365        final CompletableFuture<Integer> f = new CompletableFuture<>();
1366        final CompletableFuture<Integer> g = new CompletableFuture<>();
1367        final FailingBiFunction r = new FailingBiFunction(m);
1368        final CompletableFuture<Integer> h = m.thenCombine(f, g, r);
1369
1370        if (fFirst) {
1371            f.complete(v1);
1372            g.complete(v2);
1373        } else {
1374            g.complete(v2);
1375            f.complete(v1);
1376        }
1377
1378        checkCompletedWithWrappedCFException(h);
1379        checkCompletedNormally(f, v1);
1380        checkCompletedNormally(g, v2);
1381    }}
1382
1383    /**
1382       * thenCombine result completes exceptionally if either source cancelled
1383       */
1384      public void testThenCombine_sourceCancelled() {
# Line 1410 | Line 1408 | public class CompletableFutureTest exten
1408      }}
1409  
1410      /**
1411 +     * thenCombine result completes exceptionally if action does
1412 +     */
1413 +    public void testThenCombine_actionFailed() {
1414 +        for (ExecutionMode m : ExecutionMode.values())
1415 +        for (boolean fFirst : new boolean[] { true, false })
1416 +        for (Integer v1 : new Integer[] { 1, null })
1417 +        for (Integer v2 : new Integer[] { 2, null })
1418 +    {
1419 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1420 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1421 +        final FailingBiFunction r = new FailingBiFunction(m);
1422 +        final CompletableFuture<Integer> h = m.thenCombine(f, g, r);
1423 +
1424 +        if (fFirst) {
1425 +            f.complete(v1);
1426 +            g.complete(v2);
1427 +        } else {
1428 +            g.complete(v2);
1429 +            f.complete(v1);
1430 +        }
1431 +
1432 +        checkCompletedWithWrappedCFException(h);
1433 +        checkCompletedNormally(f, v1);
1434 +        checkCompletedNormally(g, v2);
1435 +    }}
1436 +
1437 +    /**
1438       * thenAcceptBoth result completes normally after normal
1439       * completion of sources
1440       */
# Line 1471 | Line 1496 | public class CompletableFutureTest exten
1496      }}
1497  
1498      /**
1474     * thenAcceptBoth result completes exceptionally if action does
1475     */
1476    public void testThenAcceptBoth_actionFailed() {
1477        for (ExecutionMode m : ExecutionMode.values())
1478        for (boolean fFirst : new boolean[] { true, false })
1479        for (Integer v1 : new Integer[] { 1, null })
1480        for (Integer v2 : new Integer[] { 2, null })
1481    {
1482        final CompletableFuture<Integer> f = new CompletableFuture<>();
1483        final CompletableFuture<Integer> g = new CompletableFuture<>();
1484        final FailingBiConsumer r = new FailingBiConsumer(m);
1485        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1486
1487        if (fFirst) {
1488            f.complete(v1);
1489            g.complete(v2);
1490        } else {
1491            g.complete(v2);
1492            f.complete(v1);
1493        }
1494
1495        checkCompletedWithWrappedCFException(h);
1496        checkCompletedNormally(f, v1);
1497        checkCompletedNormally(g, v2);
1498    }}
1499
1500    /**
1499       * thenAcceptBoth result completes exceptionally if either source cancelled
1500       */
1501      public void testThenAcceptBoth_sourceCancelled() {
# Line 1527 | Line 1525 | public class CompletableFutureTest exten
1525      }}
1526  
1527      /**
1528 +     * thenAcceptBoth result completes exceptionally if action does
1529 +     */
1530 +    public void testThenAcceptBoth_actionFailed() {
1531 +        for (ExecutionMode m : ExecutionMode.values())
1532 +        for (boolean fFirst : new boolean[] { true, false })
1533 +        for (Integer v1 : new Integer[] { 1, null })
1534 +        for (Integer v2 : new Integer[] { 2, null })
1535 +    {
1536 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1537 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1538 +        final FailingBiConsumer r = new FailingBiConsumer(m);
1539 +        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1540 +
1541 +        if (fFirst) {
1542 +            f.complete(v1);
1543 +            g.complete(v2);
1544 +        } else {
1545 +            g.complete(v2);
1546 +            f.complete(v1);
1547 +        }
1548 +
1549 +        checkCompletedWithWrappedCFException(h);
1550 +        checkCompletedNormally(f, v1);
1551 +        checkCompletedNormally(g, v2);
1552 +    }}
1553 +
1554 +    /**
1555       * runAfterBoth result completes normally after normal
1556       * completion of sources
1557       */
# Line 1588 | Line 1613 | public class CompletableFutureTest exten
1613      }}
1614  
1615      /**
1591     * runAfterBoth result completes exceptionally if action does
1592     */
1593    public void testRunAfterBoth_actionFailed() {
1594        for (ExecutionMode m : ExecutionMode.values())
1595        for (boolean fFirst : new boolean[] { true, false })
1596        for (Integer v1 : new Integer[] { 1, null })
1597        for (Integer v2 : new Integer[] { 2, null })
1598    {
1599        final CompletableFuture<Integer> f = new CompletableFuture<>();
1600        final CompletableFuture<Integer> g = new CompletableFuture<>();
1601        final FailingRunnable r = new FailingRunnable(m);
1602
1603        CompletableFuture<Void> h1 = m.runAfterBoth(f, g, r);
1604        if (fFirst) {
1605            f.complete(v1);
1606            g.complete(v2);
1607        } else {
1608            g.complete(v2);
1609            f.complete(v1);
1610        }
1611        CompletableFuture<Void> h2 = m.runAfterBoth(f, g, r);
1612
1613        checkCompletedWithWrappedCFException(h1);
1614        checkCompletedWithWrappedCFException(h2);
1615        checkCompletedNormally(f, v1);
1616        checkCompletedNormally(g, v2);
1617    }}
1618
1619    /**
1616       * runAfterBoth result completes exceptionally if either source cancelled
1617       */
1618      public void testRunAfterBoth_sourceCancelled() {
# Line 1647 | Line 1643 | public class CompletableFutureTest exten
1643      }}
1644  
1645      /**
1646 +     * runAfterBoth result completes exceptionally if action does
1647 +     */
1648 +    public void testRunAfterBoth_actionFailed() {
1649 +        for (ExecutionMode m : ExecutionMode.values())
1650 +        for (boolean fFirst : new boolean[] { true, false })
1651 +        for (Integer v1 : new Integer[] { 1, null })
1652 +        for (Integer v2 : new Integer[] { 2, null })
1653 +    {
1654 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1655 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1656 +        final FailingRunnable r = new FailingRunnable(m);
1657 +
1658 +        CompletableFuture<Void> h1 = m.runAfterBoth(f, g, r);
1659 +        if (fFirst) {
1660 +            f.complete(v1);
1661 +            g.complete(v2);
1662 +        } else {
1663 +            g.complete(v2);
1664 +            f.complete(v1);
1665 +        }
1666 +        CompletableFuture<Void> h2 = m.runAfterBoth(f, g, r);
1667 +
1668 +        checkCompletedWithWrappedCFException(h1);
1669 +        checkCompletedWithWrappedCFException(h2);
1670 +        checkCompletedNormally(f, v1);
1671 +        checkCompletedNormally(g, v2);
1672 +    }}
1673 +
1674 +    /**
1675       * applyToEither result completes normally after normal completion
1676       * of either source
1677       */
# Line 2591 | Line 2616 | public class CompletableFutureTest exten
2616       */
2617      public void testAllOf_normal() throws Exception {
2618          for (int k = 1; k < 20; ++k) {
2619 <            CompletableFuture<Integer>[] fs = (CompletableFuture<Integer>[]) new CompletableFuture[k];
2619 >            CompletableFuture<Integer>[] fs
2620 >                = (CompletableFuture<Integer>[]) new CompletableFuture[k];
2621              for (int i = 0; i < k; ++i)
2622                  fs[i] = new CompletableFuture<>();
2623              CompletableFuture<Void> f = CompletableFuture.allOf(fs);
# Line 2605 | Line 2631 | public class CompletableFutureTest exten
2631          }
2632      }
2633  
2634 +    public void testAllOf_backwards() throws Exception {
2635 +        for (int k = 1; k < 20; ++k) {
2636 +            CompletableFuture<Integer>[] fs
2637 +                = (CompletableFuture<Integer>[]) new CompletableFuture[k];
2638 +            for (int i = 0; i < k; ++i)
2639 +                fs[i] = new CompletableFuture<>();
2640 +            CompletableFuture<Void> f = CompletableFuture.allOf(fs);
2641 +            for (int i = k - 1; i >= 0; i--) {
2642 +                checkIncomplete(f);
2643 +                checkIncomplete(CompletableFuture.allOf(fs));
2644 +                fs[i].complete(one);
2645 +            }
2646 +            checkCompletedNormally(f, null);
2647 +            checkCompletedNormally(CompletableFuture.allOf(fs), null);
2648 +        }
2649 +    }
2650 +
2651      /**
2652       * anyOf(no component futures) returns an incomplete future
2653       */
# Line 2663 | Line 2706 | public class CompletableFutureTest exten
2706          Runnable[] throwingActions = {
2707              () -> CompletableFuture.supplyAsync(null),
2708              () -> CompletableFuture.supplyAsync(null, exec),
2709 <            () -> CompletableFuture.supplyAsync(supplyOne, null),
2709 >            () -> CompletableFuture.supplyAsync(new IntegerSupplier(ExecutionMode.DEFAULT, 42), null),
2710  
2711              () -> CompletableFuture.runAsync(null),
2712              () -> CompletableFuture.runAsync(null, exec),

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines