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.22 by jsr166, Mon Apr 8 20:46:59 2013 UTC vs.
Revision 1.35 by jsr166, Sun Jun 1 22:22:49 2014 UTC

# Line 16 | Line 16 | import java.util.concurrent.ExecutionExc
16   import java.util.concurrent.Future;
17   import java.util.concurrent.CompletableFuture;
18   import java.util.concurrent.CompletionException;
19 + import java.util.concurrent.CompletionStage;
20   import java.util.concurrent.TimeoutException;
21   import java.util.concurrent.atomic.AtomicInteger;
22   import static java.util.concurrent.TimeUnit.MILLISECONDS;
# Line 68 | Line 69 | public class CompletableFutureTest exten
69          } catch (Throwable fail) { threadUnexpectedException(fail); }
70          assertTrue(f.isDone());
71          assertFalse(f.isCancelled());
72 +        assertFalse(f.isCompletedExceptionally());
73          assertTrue(f.toString().contains("[Completed normally]"));
74      }
75  
# Line 101 | Line 103 | public class CompletableFutureTest exten
103          assertTrue(f.toString().contains("[Completed exceptionally]"));
104      }
105  
106 +    void checkCompletedWithWrappedCFException(CompletableFuture<?> f,
107 +                                              CFException ex) {
108 +        try {
109 +            f.get(LONG_DELAY_MS, MILLISECONDS);
110 +            shouldThrow();
111 +        } catch (ExecutionException success) {
112 +            assertSame(ex, success.getCause());
113 +        } catch (Throwable fail) { threadUnexpectedException(fail); }
114 +        try {
115 +            f.join();
116 +            shouldThrow();
117 +        } catch (CompletionException success) {
118 +            assertSame(ex, success.getCause());
119 +        }
120 +        try {
121 +            f.getNow(null);
122 +            shouldThrow();
123 +        } catch (CompletionException success) {
124 +            assertSame(ex, success.getCause());
125 +        }
126 +        try {
127 +            f.get();
128 +            shouldThrow();
129 +        } catch (ExecutionException success) {
130 +            assertSame(ex, success.getCause());
131 +        } catch (Throwable fail) { threadUnexpectedException(fail); }
132 +        assertTrue(f.isDone());
133 +        assertFalse(f.isCancelled());
134 +        assertTrue(f.toString().contains("[Completed exceptionally]"));
135 +    }
136 +
137      void checkCancelled(CompletableFuture<?> f) {
138          try {
139              f.get(LONG_DELAY_MS, MILLISECONDS);
# Line 121 | Line 154 | public class CompletableFutureTest exten
154          } catch (CancellationException success) {
155          } catch (Throwable fail) { threadUnexpectedException(fail); }
156          assertTrue(f.isDone());
157 +        assertTrue(f.isCompletedExceptionally());
158          assertTrue(f.isCancelled());
159          assertTrue(f.toString().contains("[Completed exceptionally]"));
160      }
# Line 152 | Line 186 | public class CompletableFutureTest exten
186          } catch (Throwable fail) { threadUnexpectedException(fail); }
187          assertTrue(f.isDone());
188          assertFalse(f.isCancelled());
189 +        assertTrue(f.isCompletedExceptionally());
190          assertTrue(f.toString().contains("[Completed exceptionally]"));
191      }
192  
# Line 256 | Line 291 | public class CompletableFutureTest exten
291          assertEquals(g.getNumberOfDependents(), 0);
292      }
293  
259
294      /**
295       * toString indicates current completion state
296       */
# Line 295 | Line 329 | public class CompletableFutureTest exten
329          public void accept(Integer x) { value = x.intValue() + 1; }
330      }
331      static final class SubtractAction implements BiConsumer<Integer, Integer> {
332 +        // Handle null values as well
333 +        public int subtract(Integer x, Integer y) {
334 +            return ((x == null) ? 42 : x.intValue())
335 +                - ((y == null) ? 99 : y.intValue());
336 +        }
337          int value;
338 +        public boolean ran() { return value != 0; }
339          public void accept(Integer x, Integer y) {
340 <            value = x.intValue() - y.intValue();
340 >            value = subtract(x, y);
341          }
342      }
343      static final class Noop implements Runnable {
# Line 371 | Line 411 | public class CompletableFutureTest exten
411          }
412      }
413  
414 +    /**
415 +     * Permits the testing of parallel code for the 3 different
416 +     * execution modes without repeating all the testing code.
417 +     */
418 +    enum ExecutionMode {
419 +        DEFAULT {
420 +            public <T,U> CompletableFuture<Void> runAfterBoth
421 +                (CompletableFuture<T> f, CompletableFuture<U> g, Runnable a) {
422 +                return f.runAfterBoth(g, a);
423 +            }
424 +            public <T,U> CompletableFuture<Void> thenAcceptBoth
425 +                (CompletableFuture<T> f,
426 +                 CompletionStage<? extends U> g,
427 +                 BiConsumer<? super T,? super U> a) {
428 +                return f.thenAcceptBoth(g, a);
429 +            }
430 +        },
431 +
432 + //             /** Experimental way to do more testing */
433 + //         REVERSE_DEFAULT {
434 + //             public <T,U> CompletableFuture<Void> runAfterBoth
435 + //                 (CompletableFuture<T> f, CompletableFuture<U> g, Runnable a) {
436 + //                 return g.runAfterBoth(f, a);
437 + //             }
438 + //             public <T,U> CompletableFuture<Void> thenAcceptBoth
439 + //                 (CompletableFuture<T> f,
440 + //                  CompletionStage<? extends U> g,
441 + //                  BiConsumer<? super T,? super U> a) {
442 + //                 return DEFAULT.thenAcceptBoth(f, g, a);
443 + //             }
444 + //         },
445 +
446 +        DEFAULT_ASYNC {
447 +            public <T,U> CompletableFuture<Void> runAfterBoth
448 +                (CompletableFuture<T> f, CompletableFuture<U> g, Runnable a) {
449 +                return f.runAfterBothAsync(g, a);
450 +            }
451 +            public <T,U> CompletableFuture<Void> thenAcceptBoth
452 +                (CompletableFuture<T> f,
453 +                 CompletionStage<? extends U> g,
454 +                 BiConsumer<? super T,? super U> a) {
455 +                return f.thenAcceptBothAsync(g, a);
456 +            }
457 +        },
458 +
459 + //         REVERSE_DEFAULT_ASYNC {
460 + //             public <T,U> CompletableFuture<Void> runAfterBoth
461 + //                 (CompletableFuture<T> f, CompletableFuture<U> g, Runnable a) {
462 + //                 return f.runAfterBothAsync(g, a);
463 + //             }
464 + //             public <T,U> CompletableFuture<Void> thenAcceptBoth
465 + //                 (CompletableFuture<T> f,
466 + //                  CompletionStage<? extends U> g,
467 + //                  BiConsumer<? super T,? super U> a) {
468 + //                 return DEFAULT_ASYNC.thenAcceptBoth(f, g, a);
469 + //             }
470 + //         },
471 +
472 +        EXECUTOR {
473 +            public <T,U> CompletableFuture<Void> runAfterBoth
474 +                (CompletableFuture<T> f, CompletableFuture<U> g, Runnable a) {
475 +                return f.runAfterBothAsync(g, a, new ThreadExecutor());
476 +            }
477 +            public <T,U> CompletableFuture<Void> thenAcceptBoth
478 +                (CompletableFuture<T> f,
479 +                 CompletionStage<? extends U> g,
480 +                 BiConsumer<? super T,? super U> a) {
481 +                return f.thenAcceptBothAsync(g, a, new ThreadExecutor());
482 +            }
483 +        };
484 +
485 +        public abstract <T,U> CompletableFuture<Void> runAfterBoth
486 +            (CompletableFuture<T> f, CompletableFuture<U> g, Runnable a);
487 +        public abstract <T,U> CompletableFuture<Void> thenAcceptBoth
488 +            (CompletableFuture<T> f,
489 +             CompletionStage<? extends U> g,
490 +             BiConsumer<? super T,? super U> a);
491 +    }
492  
493      /**
494       * exceptionally action completes with function value on source
495 <     * exception;  otherwise with source value
495 >     * exception; otherwise with source value
496       */
497      public void testExceptionally() {
498          CompletableFuture<Integer> f = new CompletableFuture<>();
# Line 495 | Line 613 | public class CompletableFutureTest exten
613       * thenRun result completes normally after normal completion of source
614       */
615      public void testThenRun() {
616 <        CompletableFuture<Integer> f = new CompletableFuture<>();
617 <        Noop r = new Noop();
618 <        CompletableFuture<Void> g = f.thenRun(r);
616 >        CompletableFuture<Integer> f;
617 >        CompletableFuture<Void> g;
618 >        Noop r;
619 >
620 >        f = new CompletableFuture<>();
621 >        g = f.thenRun(r = new Noop());
622          f.complete(null);
623          checkCompletedNormally(g, null);
624 <        // reordered version
624 >        assertTrue(r.ran);
625 >
626          f = new CompletableFuture<>();
627          f.complete(null);
628 <        r = new Noop();
507 <        g = f.thenRun(r);
628 >        g = f.thenRun(r = new Noop());
629          checkCompletedNormally(g, null);
630 +        assertTrue(r.ran);
631      }
632  
633      /**
# Line 513 | Line 635 | public class CompletableFutureTest exten
635       * completion of source
636       */
637      public void testThenRun2() {
638 <        CompletableFuture<Integer> f = new CompletableFuture<>();
639 <        Noop r = new Noop();
640 <        CompletableFuture<Void> g = f.thenRun(r);
638 >        CompletableFuture<Integer> f;
639 >        CompletableFuture<Void> g;
640 >        Noop r;
641 >
642 >        f = new CompletableFuture<>();
643 >        g = f.thenRun(r = new Noop());
644          f.completeExceptionally(new CFException());
645          checkCompletedWithWrappedCFException(g);
646 +        assertFalse(r.ran);
647 +
648 +        f = new CompletableFuture<>();
649 +        f.completeExceptionally(new CFException());
650 +        g = f.thenRun(r = new Noop());
651 +        checkCompletedWithWrappedCFException(g);
652 +        assertFalse(r.ran);
653      }
654  
655      /**
656       * thenRun result completes exceptionally if action does
657       */
658      public void testThenRun3() {
659 <        CompletableFuture<Integer> f = new CompletableFuture<>();
660 <        FailingNoop r = new FailingNoop();
661 <        CompletableFuture<Void> g = f.thenRun(r);
659 >        CompletableFuture<Integer> f;
660 >        CompletableFuture<Void> g;
661 >        FailingNoop r;
662 >
663 >        f = new CompletableFuture<>();
664 >        g = f.thenRun(r = new FailingNoop());
665 >        f.complete(null);
666 >        checkCompletedWithWrappedCFException(g);
667 >
668 >        f = new CompletableFuture<>();
669          f.complete(null);
670 +        g = f.thenRun(r = new FailingNoop());
671          checkCompletedWithWrappedCFException(g);
672      }
673  
# Line 535 | Line 675 | public class CompletableFutureTest exten
675       * thenRun result completes exceptionally if source cancelled
676       */
677      public void testThenRun4() {
678 <        CompletableFuture<Integer> f = new CompletableFuture<>();
679 <        Noop r = new Noop();
680 <        CompletableFuture<Void> g = f.thenRun(r);
678 >        CompletableFuture<Integer> f;
679 >        CompletableFuture<Void> g;
680 >        Noop r;
681 >
682 >        f = new CompletableFuture<>();
683 >        g = f.thenRun(r = new Noop());
684          assertTrue(f.cancel(true));
685          checkCompletedWithWrappedCancellationException(g);
686 +
687 +        f = new CompletableFuture<>();
688 +        assertTrue(f.cancel(true));
689 +        g = f.thenRun(r = new Noop());
690 +        checkCompletedWithWrappedCancellationException(g);
691      }
692  
693      /**
# Line 630 | Line 778 | public class CompletableFutureTest exten
778          checkCompletedWithWrappedCancellationException(g);
779      }
780  
633
781      /**
782       * thenCombine result completes normally after normal completion
783       * of sources
# Line 750 | Line 897 | public class CompletableFutureTest exten
897       * thenAcceptBoth result completes normally after normal
898       * completion of sources
899       */
900 <    public void testThenAcceptBoth() {
901 <        CompletableFuture<Integer> f, g;
902 <        CompletableFuture<Void> h;
903 <        SubtractAction r;
900 >    public void testThenAcceptBoth_normalCompletion1() {
901 >        for (ExecutionMode m : ExecutionMode.values())
902 >        for (Integer v1 : new Integer[] { 1, null })
903 >        for (Integer v2 : new Integer[] { 2, null }) {
904 >
905 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
906 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
907 >        final SubtractAction r = new SubtractAction();
908 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
909  
910 <        f = new CompletableFuture<>();
759 <        g = new CompletableFuture<>();
760 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
761 <        f.complete(3);
910 >        f.complete(v1);
911          checkIncomplete(h);
912 <        g.complete(1);
912 >        assertEquals(r.value, 0);
913 >        g.complete(v2);
914 >
915          checkCompletedNormally(h, null);
916 <        assertEquals(r.value, 2);
916 >        assertEquals(r.value, r.subtract(v1, v2));
917 >        checkCompletedNormally(f, v1);
918 >        checkCompletedNormally(g, v2);
919 >        }
920 >    }
921  
922 <        f = new CompletableFuture<>();
923 <        g = new CompletableFuture<>();
924 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
925 <        g.complete(1);
922 >    public void testThenAcceptBoth_normalCompletion2() {
923 >        for (ExecutionMode m : ExecutionMode.values())
924 >        for (Integer v1 : new Integer[] { 1, null })
925 >        for (Integer v2 : new Integer[] { 2, null }) {
926 >
927 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
928 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
929 >        final SubtractAction r = new SubtractAction();
930 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
931 >
932 >        g.complete(v2);
933          checkIncomplete(h);
934 <        f.complete(3);
934 >        assertEquals(r.value, 0);
935 >        f.complete(v1);
936 >
937          checkCompletedNormally(h, null);
938 <        assertEquals(r.value, 2);
938 >        assertEquals(r.value, r.subtract(v1, v2));
939 >        checkCompletedNormally(f, v1);
940 >        checkCompletedNormally(g, v2);
941 >        }
942 >    }
943 >
944 >    public void testThenAcceptBoth_normalCompletion3() {
945 >        for (ExecutionMode m : ExecutionMode.values())
946 >        for (Integer v1 : new Integer[] { 1, null })
947 >        for (Integer v2 : new Integer[] { 2, null }) {
948 >
949 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
950 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
951 >        final SubtractAction r = new SubtractAction();
952 >
953 >        g.complete(v2);
954 >        f.complete(v1);
955 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
956  
776        f = new CompletableFuture<>();
777        g = new CompletableFuture<>();
778        g.complete(1);
779        f.complete(3);
780        h = f.thenAcceptBoth(g, r = new SubtractAction());
957          checkCompletedNormally(h, null);
958 <        assertEquals(r.value, 2);
958 >        assertEquals(r.value, r.subtract(v1, v2));
959 >        checkCompletedNormally(f, v1);
960 >        checkCompletedNormally(g, v2);
961 >        }
962 >    }
963 >
964 >    public void testThenAcceptBoth_normalCompletion4() {
965 >        for (ExecutionMode m : ExecutionMode.values())
966 >        for (Integer v1 : new Integer[] { 1, null })
967 >        for (Integer v2 : new Integer[] { 2, null }) {
968 >
969 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
970 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
971 >        final SubtractAction r = new SubtractAction();
972 >
973 >        f.complete(v1);
974 >        g.complete(v2);
975 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
976 >
977 >        checkCompletedNormally(h, null);
978 >        assertEquals(r.value, r.subtract(v1, v2));
979 >        checkCompletedNormally(f, v1);
980 >        checkCompletedNormally(g, v2);
981 >        }
982      }
983  
984      /**
985       * thenAcceptBoth result completes exceptionally after exceptional
986       * completion of either source
987       */
988 <    public void testThenAcceptBoth2() {
989 <        CompletableFuture<Integer> f, g;
990 <        CompletableFuture<Void> h;
991 <        SubtractAction r;
992 <
993 <        f = new CompletableFuture<>();
994 <        g = new CompletableFuture<>();
995 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
996 <        f.completeExceptionally(new CFException());
997 <        checkIncomplete(h);
998 <        g.complete(1);
999 <        checkCompletedWithWrappedCFException(h);
988 >    public void testThenAcceptBoth_exceptionalCompletion1() {
989 >        for (ExecutionMode m : ExecutionMode.values())
990 >        for (Integer v1 : new Integer[] { 1, null }) {
991 >
992 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
993 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
994 >        final SubtractAction r = new SubtractAction();
995 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
996 >        final CFException ex = new CFException();
997 >
998 >        f.completeExceptionally(ex);
999 >        checkIncomplete(h);
1000 >        g.complete(v1);
1001 >
1002 >        checkCompletedWithWrappedCFException(h, ex);
1003 >        checkCompletedWithWrappedCFException(f, ex);
1004 >        assertFalse(r.ran());
1005 >        checkCompletedNormally(g, v1);
1006 >        }
1007 >    }
1008  
1009 <        f = new CompletableFuture<>();
1010 <        g = new CompletableFuture<>();
1011 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
1012 <        g.completeExceptionally(new CFException());
1013 <        checkIncomplete(h);
1014 <        f.complete(3);
1015 <        checkCompletedWithWrappedCFException(h);
1009 >    public void testThenAcceptBoth_exceptionalCompletion2() {
1010 >        for (ExecutionMode m : ExecutionMode.values())
1011 >        for (Integer v1 : new Integer[] { 1, null }) {
1012 >
1013 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1014 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1015 >        final SubtractAction r = new SubtractAction();
1016 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1017 >        final CFException ex = new CFException();
1018 >
1019 >        g.completeExceptionally(ex);
1020 >        checkIncomplete(h);
1021 >        f.complete(v1);
1022 >
1023 >        checkCompletedWithWrappedCFException(h, ex);
1024 >        checkCompletedWithWrappedCFException(g, ex);
1025 >        assertFalse(r.ran());
1026 >        checkCompletedNormally(f, v1);
1027 >        }
1028 >    }
1029  
1030 <        f = new CompletableFuture<>();
1031 <        g = new CompletableFuture<>();
1032 <        f.complete(3);
1033 <        g.completeExceptionally(new CFException());
1034 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
1035 <        checkCompletedWithWrappedCFException(h);
1030 >    public void testThenAcceptBoth_exceptionalCompletion3() {
1031 >        for (ExecutionMode m : ExecutionMode.values())
1032 >        for (Integer v1 : new Integer[] { 1, null }) {
1033 >
1034 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1035 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1036 >        final SubtractAction r = new SubtractAction();
1037 >        final CFException ex = new CFException();
1038 >
1039 >        g.completeExceptionally(ex);
1040 >        f.complete(v1);
1041 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1042 >
1043 >        checkCompletedWithWrappedCFException(h, ex);
1044 >        checkCompletedWithWrappedCFException(g, ex);
1045 >        assertFalse(r.ran());
1046 >        checkCompletedNormally(f, v1);
1047 >        }
1048 >    }
1049  
1050 <        f = new CompletableFuture<>();
1051 <        g = new CompletableFuture<>();
1052 <        f.completeExceptionally(new CFException());
1053 <        g.complete(3);
1054 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
1055 <        checkCompletedWithWrappedCFException(h);
1050 >    public void testThenAcceptBoth_exceptionalCompletion4() {
1051 >        for (ExecutionMode m : ExecutionMode.values())
1052 >        for (Integer v1 : new Integer[] { 1, null }) {
1053 >
1054 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1055 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1056 >        final SubtractAction r = new SubtractAction();
1057 >        final CFException ex = new CFException();
1058 >
1059 >        f.completeExceptionally(ex);
1060 >        g.complete(v1);
1061 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1062 >
1063 >        checkCompletedWithWrappedCFException(h, ex);
1064 >        checkCompletedWithWrappedCFException(f, ex);
1065 >        assertFalse(r.ran());
1066 >        checkCompletedNormally(g, v1);
1067 >        }
1068      }
1069  
1070      /**
1071       * thenAcceptBoth result completes exceptionally if action does
1072       */
1073 <    public void testThenAcceptBoth3() {
1074 <        CompletableFuture<Integer> f, g;
1075 <        CompletableFuture<Void> h;
1076 <        FailingBiConsumer r;
1073 >    public void testThenAcceptBoth_actionFailed1() {
1074 >        for (ExecutionMode m : ExecutionMode.values())
1075 >        for (Integer v1 : new Integer[] { 1, null })
1076 >        for (Integer v2 : new Integer[] { 2, null }) {
1077  
1078 <        f = new CompletableFuture<>();
1079 <        g = new CompletableFuture<>();
1080 <        h = f.thenAcceptBoth(g, r = new FailingBiConsumer());
1081 <        f.complete(3);
1078 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1079 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1080 >        final FailingBiConsumer r = new FailingBiConsumer();
1081 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1082 >
1083 >        f.complete(v1);
1084          checkIncomplete(h);
1085 <        g.complete(1);
1085 >        g.complete(v2);
1086 >
1087          checkCompletedWithWrappedCFException(h);
1088 +        checkCompletedNormally(f, v1);
1089 +        checkCompletedNormally(g, v2);
1090 +        }
1091 +    }
1092 +
1093 +    public void testThenAcceptBoth_actionFailed2() {
1094 +        for (ExecutionMode m : ExecutionMode.values())
1095 +        for (Integer v1 : new Integer[] { 1, null })
1096 +        for (Integer v2 : new Integer[] { 2, null }) {
1097 +
1098 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1099 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1100 +        final FailingBiConsumer r = new FailingBiConsumer();
1101 +        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1102 +
1103 +        g.complete(v2);
1104 +        checkIncomplete(h);
1105 +        f.complete(v1);
1106  
841        f = new CompletableFuture<>();
842        g = new CompletableFuture<>();
843        f.complete(3);
844        g.complete(1);
845        h = f.thenAcceptBoth(g, r = new FailingBiConsumer());
1107          checkCompletedWithWrappedCFException(h);
1108 +        checkCompletedNormally(f, v1);
1109 +        checkCompletedNormally(g, v2);
1110 +        }
1111      }
1112  
1113      /**
1114       * thenAcceptBoth result completes exceptionally if either source cancelled
1115       */
1116 <    public void testThenAcceptBoth4() {
1117 <        CompletableFuture<Integer> f, g;
1118 <        CompletableFuture<Void> h;
1119 <        SubtractAction r;
1116 >    public void testThenAcceptBoth_sourceCancelled1() {
1117 >        for (ExecutionMode m : ExecutionMode.values())
1118 >        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1119 >        for (Integer v1 : new Integer[] { 1, null }) {
1120 >
1121 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1122 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1123 >        final SubtractAction r = new SubtractAction();
1124 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1125  
1126 <        f = new CompletableFuture<>();
858 <        g = new CompletableFuture<>();
859 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
860 <        assertTrue(f.cancel(true));
1126 >        assertTrue(f.cancel(mayInterruptIfRunning));
1127          checkIncomplete(h);
1128 <        g.complete(1);
1128 >        g.complete(v1);
1129 >
1130          checkCompletedWithWrappedCancellationException(h);
1131 +        checkCancelled(f);
1132 +        assertFalse(r.ran());
1133 +        checkCompletedNormally(g, v1);
1134 +        }
1135 +    }
1136  
1137 <        f = new CompletableFuture<>();
1138 <        g = new CompletableFuture<>();
1139 <        h = f.thenAcceptBoth(g, r = new SubtractAction());
1140 <        assertTrue(g.cancel(true));
1137 >    public void testThenAcceptBoth_sourceCancelled2() {
1138 >        for (ExecutionMode m : ExecutionMode.values())
1139 >        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1140 >        for (Integer v1 : new Integer[] { 1, null }) {
1141 >
1142 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1143 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1144 >        final SubtractAction r = new SubtractAction();
1145 >        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1146 >
1147 >        assertTrue(g.cancel(mayInterruptIfRunning));
1148          checkIncomplete(h);
1149 <        f.complete(3);
871 <        checkCompletedWithWrappedCancellationException(h);
1149 >        f.complete(v1);
1150  
873        f = new CompletableFuture<>();
874        g = new CompletableFuture<>();
875        f.complete(3);
876        assertTrue(g.cancel(true));
877        h = f.thenAcceptBoth(g, r = new SubtractAction());
1151          checkCompletedWithWrappedCancellationException(h);
1152 +        checkCancelled(g);
1153 +        assertFalse(r.ran());
1154 +        checkCompletedNormally(f, v1);
1155 +        }
1156 +    }
1157 +
1158 +    public void testThenAcceptBoth_sourceCancelled3() {
1159 +        for (ExecutionMode m : ExecutionMode.values())
1160 +        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1161 +        for (Integer v1 : new Integer[] { 1, null }) {
1162 +
1163 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1164 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1165 +        final SubtractAction r = new SubtractAction();
1166 +
1167 +        assertTrue(g.cancel(mayInterruptIfRunning));
1168 +        f.complete(v1);
1169 +        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1170 +
1171 +        checkCompletedWithWrappedCancellationException(h);
1172 +        checkCancelled(g);
1173 +        assertFalse(r.ran());
1174 +        checkCompletedNormally(f, v1);
1175 +        }
1176 +    }
1177 +
1178 +    public void testThenAcceptBoth_sourceCancelled4() {
1179 +        for (ExecutionMode m : ExecutionMode.values())
1180 +        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1181 +        for (Integer v1 : new Integer[] { 1, null }) {
1182 +
1183 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1184 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1185 +        final SubtractAction r = new SubtractAction();
1186 +
1187 +        assertTrue(f.cancel(mayInterruptIfRunning));
1188 +        g.complete(v1);
1189 +        final CompletableFuture<Void> h = m.thenAcceptBoth(f, g, r);
1190  
880        f = new CompletableFuture<>();
881        g = new CompletableFuture<>();
882        assertTrue(f.cancel(true));
883        g.complete(3);
884        h = f.thenAcceptBoth(g, r = new SubtractAction());
1191          checkCompletedWithWrappedCancellationException(h);
1192 +        checkCancelled(f);
1193 +        assertFalse(r.ran());
1194 +        checkCompletedNormally(g, v1);
1195 +        }
1196      }
1197  
1198      /**
1199       * runAfterBoth result completes normally after normal
1200       * completion of sources
1201       */
1202 <    public void testRunAfterBoth() {
1203 <        CompletableFuture<Integer> f, g;
1204 <        CompletableFuture<Void> h;
1205 <        Noop r;
1202 >    public void testRunAfterBoth_normalCompletion1() {
1203 >        for (ExecutionMode m : ExecutionMode.values())
1204 >        for (Integer v1 : new Integer[] { 1, null })
1205 >        for (Integer v2 : new Integer[] { 2, null }) {
1206 >
1207 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1208 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1209 >        final Noop r = new Noop();
1210 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1211  
1212 <        f = new CompletableFuture<>();
898 <        g = new CompletableFuture<>();
899 <        h = f.runAfterBoth(g, r = new Noop());
900 <        f.complete(3);
1212 >        f.complete(v1);
1213          checkIncomplete(h);
1214 <        g.complete(1);
1214 >        assertFalse(r.ran);
1215 >        g.complete(v2);
1216 >
1217          checkCompletedNormally(h, null);
1218          assertTrue(r.ran);
1219 +        checkCompletedNormally(f, v1);
1220 +        checkCompletedNormally(g, v2);
1221 +        }
1222 +    }
1223  
1224 <        f = new CompletableFuture<>();
1225 <        g = new CompletableFuture<>();
1226 <        h = f.runAfterBoth(g, r = new Noop());
1227 <        g.complete(1);
1224 >    public void testRunAfterBoth_normalCompletion2() {
1225 >        for (ExecutionMode m : ExecutionMode.values())
1226 >        for (Integer v1 : new Integer[] { 1, null })
1227 >        for (Integer v2 : new Integer[] { 2, null }) {
1228 >
1229 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1230 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1231 >        final Noop r = new Noop();
1232 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1233 >
1234 >        g.complete(v2);
1235          checkIncomplete(h);
1236 <        f.complete(3);
1236 >        assertFalse(r.ran);
1237 >        f.complete(v1);
1238 >
1239          checkCompletedNormally(h, null);
1240          assertTrue(r.ran);
1241 +        checkCompletedNormally(f, v1);
1242 +        checkCompletedNormally(g, v2);
1243 +        }
1244 +    }
1245 +
1246 +    public void testRunAfterBoth_normalCompletion3() {
1247 +        for (ExecutionMode m : ExecutionMode.values())
1248 +        for (Integer v1 : new Integer[] { 1, null })
1249 +        for (Integer v2 : new Integer[] { 2, null }) {
1250 +
1251 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1252 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1253 +        final Noop r = new Noop();
1254 +
1255 +        g.complete(v2);
1256 +        f.complete(v1);
1257 +        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1258 +
1259 +        checkCompletedNormally(h, null);
1260 +        assertTrue(r.ran);
1261 +        checkCompletedNormally(f, v1);
1262 +        checkCompletedNormally(g, v2);
1263 +        }
1264 +    }
1265 +
1266 +    public void testRunAfterBoth_normalCompletion4() {
1267 +        for (ExecutionMode m : ExecutionMode.values())
1268 +        for (Integer v1 : new Integer[] { 1, null })
1269 +        for (Integer v2 : new Integer[] { 2, null }) {
1270 +
1271 +        final CompletableFuture<Integer> f = new CompletableFuture<>();
1272 +        final CompletableFuture<Integer> g = new CompletableFuture<>();
1273 +        final Noop r = new Noop();
1274 +
1275 +        f.complete(v1);
1276 +        g.complete(v2);
1277 +        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1278  
915        f = new CompletableFuture<>();
916        g = new CompletableFuture<>();
917        g.complete(1);
918        f.complete(3);
919        h = f.runAfterBoth(g, r = new Noop());
1279          checkCompletedNormally(h, null);
1280          assertTrue(r.ran);
1281 +        checkCompletedNormally(f, v1);
1282 +        checkCompletedNormally(g, v2);
1283 +        }
1284      }
1285  
1286      /**
1287       * runAfterBoth result completes exceptionally after exceptional
1288       * completion of either source
1289       */
1290 <    public void testRunAfterBoth2() {
1291 <        CompletableFuture<Integer> f, g;
1292 <        CompletableFuture<Void> h;
1293 <        Noop r;
1290 >    public void testRunAfterBoth_exceptionalCompletion1() {
1291 >        for (ExecutionMode m : ExecutionMode.values())
1292 >        for (Integer v1 : new Integer[] { 1, null }) {
1293 >
1294 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1295 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1296 >        final Noop r = new Noop();
1297 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1298 >        final CFException ex = new CFException();
1299  
1300 <        f = new CompletableFuture<>();
934 <        g = new CompletableFuture<>();
935 <        h = f.runAfterBoth(g, r = new Noop());
936 <        f.completeExceptionally(new CFException());
1300 >        f.completeExceptionally(ex);
1301          checkIncomplete(h);
1302 <        g.complete(1);
1303 <        checkCompletedWithWrappedCFException(h);
1302 >        g.complete(v1);
1303 >
1304 >        checkCompletedWithWrappedCFException(h, ex);
1305 >        checkCompletedWithWrappedCFException(f, ex);
1306          assertFalse(r.ran);
1307 +        checkCompletedNormally(g, v1);
1308 +        }
1309 +    }
1310  
1311 <        f = new CompletableFuture<>();
1312 <        g = new CompletableFuture<>();
1313 <        h = f.runAfterBoth(g, r = new Noop());
1314 <        g.completeExceptionally(new CFException());
1311 >    public void testRunAfterBoth_exceptionalCompletion2() {
1312 >        for (ExecutionMode m : ExecutionMode.values())
1313 >        for (Integer v1 : new Integer[] { 1, null }) {
1314 >
1315 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1316 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1317 >        final Noop r = new Noop();
1318 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1319 >        final CFException ex = new CFException();
1320 >
1321 >        g.completeExceptionally(ex);
1322          checkIncomplete(h);
1323 <        f.complete(3);
1324 <        checkCompletedWithWrappedCFException(h);
1323 >        f.complete(v1);
1324 >
1325 >        checkCompletedWithWrappedCFException(h, ex);
1326 >        checkCompletedWithWrappedCFException(g, ex);
1327          assertFalse(r.ran);
1328 +        checkCompletedNormally(f, v1);
1329 +        }
1330 +    }
1331  
1332 <        f = new CompletableFuture<>();
1333 <        g = new CompletableFuture<>();
1334 <        g.completeExceptionally(new CFException());
1335 <        f.complete(3);
1336 <        h = f.runAfterBoth(g, r = new Noop());
1337 <        checkCompletedWithWrappedCFException(h);
1332 >    public void testRunAfterBoth_exceptionalCompletion3() {
1333 >        for (ExecutionMode m : ExecutionMode.values())
1334 >        for (Integer v1 : new Integer[] { 1, null }) {
1335 >
1336 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1337 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1338 >        final Noop r = new Noop();
1339 >        final CFException ex = new CFException();
1340 >
1341 >        g.completeExceptionally(ex);
1342 >        f.complete(v1);
1343 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1344 >
1345 >        checkCompletedWithWrappedCFException(h, ex);
1346 >        checkCompletedWithWrappedCFException(g, ex);
1347          assertFalse(r.ran);
1348 +        checkCompletedNormally(f, v1);
1349 +        }
1350 +    }
1351  
1352 <        f = new CompletableFuture<>();
1353 <        g = new CompletableFuture<>();
1354 <        f.completeExceptionally(new CFException());
1355 <        g.complete(1);
1356 <        h = f.runAfterBoth(g, r = new Noop());
1357 <        checkCompletedWithWrappedCFException(h);
1352 >    public void testRunAfterBoth_exceptionalCompletion4() {
1353 >        for (ExecutionMode m : ExecutionMode.values())
1354 >        for (Integer v1 : new Integer[] { 1, null }) {
1355 >
1356 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1357 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1358 >        final Noop r = new Noop();
1359 >        final CFException ex = new CFException();
1360 >
1361 >        f.completeExceptionally(ex);
1362 >        g.complete(v1);
1363 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1364 >
1365 >        checkCompletedWithWrappedCFException(h, ex);
1366 >        checkCompletedWithWrappedCFException(f, ex);
1367          assertFalse(r.ran);
1368 +        checkCompletedNormally(g, v1);
1369 +        }
1370      }
1371  
1372      /**
1373       * runAfterBoth result completes exceptionally if action does
1374       */
1375 <    public void testRunAfterBoth3() {
1376 <        CompletableFuture<Integer> f = new CompletableFuture<>();
1377 <        CompletableFuture<Integer> f2 = new CompletableFuture<>();
1378 <        FailingNoop r = new FailingNoop();
1379 <        CompletableFuture<Void> g = f.runAfterBoth(f2, r);
1380 <        f.complete(one);
1381 <        checkIncomplete(g);
1382 <        f2.complete(two);
1383 <        checkCompletedWithWrappedCFException(g);
1375 >    public void testRunAfterBoth_actionFailed1() {
1376 >        for (ExecutionMode m : ExecutionMode.values())
1377 >        for (Integer v1 : new Integer[] { 1, null })
1378 >        for (Integer v2 : new Integer[] { 2, null }) {
1379 >
1380 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1381 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1382 >        final FailingNoop r = new FailingNoop();
1383 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1384 >
1385 >        f.complete(v1);
1386 >        checkIncomplete(h);
1387 >        g.complete(v2);
1388 >
1389 >        checkCompletedWithWrappedCFException(h);
1390 >        checkCompletedNormally(f, v1);
1391 >        checkCompletedNormally(g, v2);
1392 >        }
1393 >    }
1394 >
1395 >    public void testRunAfterBoth_actionFailed2() {
1396 >        for (ExecutionMode m : ExecutionMode.values())
1397 >        for (Integer v1 : new Integer[] { 1, null })
1398 >        for (Integer v2 : new Integer[] { 2, null }) {
1399 >
1400 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1401 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1402 >        final FailingNoop r = new FailingNoop();
1403 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1404 >
1405 >        g.complete(v2);
1406 >        checkIncomplete(h);
1407 >        f.complete(v1);
1408 >
1409 >        checkCompletedWithWrappedCFException(h);
1410 >        checkCompletedNormally(f, v1);
1411 >        checkCompletedNormally(g, v2);
1412 >        }
1413      }
1414  
1415      /**
1416       * runAfterBoth result completes exceptionally if either source cancelled
1417       */
1418 <    public void testRunAfterBoth4() {
1419 <        CompletableFuture<Integer> f = new CompletableFuture<>();
1420 <        CompletableFuture<Integer> f2 = new CompletableFuture<>();
1421 <        Noop r = new Noop();
1422 <        CompletableFuture<Void> g = f.runAfterBoth(f2, r);
1423 <        assertTrue(f.cancel(true));
1424 <        f2.complete(two);
1425 <        checkCompletedWithWrappedCancellationException(g);
1426 <        f = new CompletableFuture<>();
1427 <        f2 = new CompletableFuture<>();
1428 <        r = new Noop();
1429 <        g = f.runAfterBoth(f2, r);
1430 <        f.complete(one);
1431 <        assertTrue(f2.cancel(true));
1432 <        checkCompletedWithWrappedCancellationException(g);
1418 >    public void testRunAfterBoth_sourceCancelled1() {
1419 >        for (ExecutionMode m : ExecutionMode.values())
1420 >        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1421 >        for (Integer v1 : new Integer[] { 1, null }) {
1422 >
1423 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1424 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1425 >        final Noop r = new Noop();
1426 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1427 >
1428 >        assertTrue(f.cancel(mayInterruptIfRunning));
1429 >        checkIncomplete(h);
1430 >        g.complete(v1);
1431 >
1432 >        checkCompletedWithWrappedCancellationException(h);
1433 >        checkCancelled(f);
1434 >        assertFalse(r.ran);
1435 >        checkCompletedNormally(g, v1);
1436 >        }
1437 >    }
1438 >
1439 >    public void testRunAfterBoth_sourceCancelled2() {
1440 >        for (ExecutionMode m : ExecutionMode.values())
1441 >        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1442 >        for (Integer v1 : new Integer[] { 1, null }) {
1443 >
1444 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1445 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1446 >        final Noop r = new Noop();
1447 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1448 >
1449 >        assertTrue(g.cancel(mayInterruptIfRunning));
1450 >        checkIncomplete(h);
1451 >        f.complete(v1);
1452 >
1453 >        checkCompletedWithWrappedCancellationException(h);
1454 >        checkCancelled(g);
1455 >        assertFalse(r.ran);
1456 >        checkCompletedNormally(f, v1);
1457 >        }
1458 >    }
1459 >
1460 >    public void testRunAfterBoth_sourceCancelled3() {
1461 >        for (ExecutionMode m : ExecutionMode.values())
1462 >        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1463 >        for (Integer v1 : new Integer[] { 1, null }) {
1464 >
1465 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1466 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1467 >        final Noop r = new Noop();
1468 >
1469 >        assertTrue(g.cancel(mayInterruptIfRunning));
1470 >        f.complete(v1);
1471 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1472 >
1473 >        checkCompletedWithWrappedCancellationException(h);
1474 >        checkCancelled(g);
1475 >        assertFalse(r.ran);
1476 >        checkCompletedNormally(f, v1);
1477 >        }
1478 >    }
1479 >
1480 >    public void testRunAfterBoth_sourceCancelled4() {
1481 >        for (ExecutionMode m : ExecutionMode.values())
1482 >        for (boolean mayInterruptIfRunning : new boolean[] { true, false })
1483 >        for (Integer v1 : new Integer[] { 1, null }) {
1484 >
1485 >        final CompletableFuture<Integer> f = new CompletableFuture<>();
1486 >        final CompletableFuture<Integer> g = new CompletableFuture<>();
1487 >        final Noop r = new Noop();
1488 >
1489 >        assertTrue(f.cancel(mayInterruptIfRunning));
1490 >        g.complete(v1);
1491 >        final CompletableFuture<Void> h = m.runAfterBoth(f, g, r);
1492 >
1493 >        checkCompletedWithWrappedCancellationException(h);
1494 >        checkCancelled(f);
1495 >        assertFalse(r.ran);
1496 >        checkCompletedNormally(g, v1);
1497 >        }
1498      }
1499  
1500      /**
# Line 1138 | Line 1636 | public class CompletableFutureTest exten
1636          checkCompletedWithWrappedCancellationException(g);
1637      }
1638  
1141
1639      /**
1640       * runAfterEither result completes normally after normal completion
1641       * of either source
# Line 1287 | Line 1784 | public class CompletableFutureTest exten
1784          checkCompletedWithWrappedCancellationException(g);
1785      }
1786  
1290
1787      // asyncs
1788  
1789      /**
# Line 1320 | Line 1816 | public class CompletableFutureTest exten
1816          try {
1817              g.join();
1818              shouldThrow();
1819 <        } catch (Exception ok) {
1324 <        }
1819 >        } catch (CompletionException success) {}
1820          checkCompletedWithWrappedCFException(g);
1821      }
1822  
# Line 1552 | Line 2047 | public class CompletableFutureTest exten
2047      }
2048  
2049      /**
1555     * thenAcceptBothAsync result completes normally after normal
1556     * completion of sources
1557     */
1558    public void testThenAcceptBothAsync() {
1559        CompletableFuture<Integer> f, g;
1560        CompletableFuture<Void> h;
1561        SubtractAction r;
1562
1563        f = new CompletableFuture<>();
1564        g = new CompletableFuture<>();
1565        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1566        f.complete(3);
1567        checkIncomplete(h);
1568        g.complete(1);
1569        checkCompletedNormally(h, null);
1570        assertEquals(r.value, 2);
1571
1572        f = new CompletableFuture<>();
1573        g = new CompletableFuture<>();
1574        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1575        g.complete(1);
1576        checkIncomplete(h);
1577        f.complete(3);
1578        checkCompletedNormally(h, null);
1579        assertEquals(r.value, 2);
1580
1581        f = new CompletableFuture<>();
1582        g = new CompletableFuture<>();
1583        g.complete(1);
1584        f.complete(3);
1585        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1586        checkCompletedNormally(h, null);
1587        assertEquals(r.value, 2);
1588    }
1589
1590    /**
1591     * thenAcceptBothAsync result completes exceptionally after exceptional
1592     * completion of source
1593     */
1594    public void testThenAcceptBothAsync2() {
1595        CompletableFuture<Integer> f, g;
1596        CompletableFuture<Void> h;
1597        SubtractAction r;
1598
1599        f = new CompletableFuture<>();
1600        g = new CompletableFuture<>();
1601        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1602        f.completeExceptionally(new CFException());
1603        checkIncomplete(h);
1604        g.complete(1);
1605        checkCompletedWithWrappedCFException(h);
1606
1607        f = new CompletableFuture<>();
1608        g = new CompletableFuture<>();
1609        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1610        g.completeExceptionally(new CFException());
1611        checkIncomplete(h);
1612        f.complete(3);
1613        checkCompletedWithWrappedCFException(h);
1614
1615        f = new CompletableFuture<>();
1616        g = new CompletableFuture<>();
1617        f.complete(3);
1618        g.completeExceptionally(new CFException());
1619        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1620        checkCompletedWithWrappedCFException(h);
1621
1622        f = new CompletableFuture<>();
1623        g = new CompletableFuture<>();
1624        f.completeExceptionally(new CFException());
1625        g.complete(3);
1626        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1627        checkCompletedWithWrappedCFException(h);
1628    }
1629
1630    /**
1631     * thenAcceptBothAsync result completes exceptionally if action does
1632     */
1633    public void testThenAcceptBothAsync3() {
1634        CompletableFuture<Integer> f, g;
1635        CompletableFuture<Void> h;
1636        FailingBiConsumer r;
1637
1638        f = new CompletableFuture<>();
1639        g = new CompletableFuture<>();
1640        h = f.thenAcceptBothAsync(g, r = new FailingBiConsumer());
1641        f.complete(3);
1642        checkIncomplete(h);
1643        g.complete(1);
1644        checkCompletedWithWrappedCFException(h);
1645
1646        f = new CompletableFuture<>();
1647        g = new CompletableFuture<>();
1648        f.complete(3);
1649        g.complete(1);
1650        h = f.thenAcceptBothAsync(g, r = new FailingBiConsumer());
1651        checkCompletedWithWrappedCFException(h);
1652    }
1653
1654    /**
1655     * thenAcceptBothAsync result completes exceptionally if either source cancelled
1656     */
1657    public void testThenAcceptBothAsync4() {
1658        CompletableFuture<Integer> f, g;
1659        CompletableFuture<Void> h;
1660        SubtractAction r;
1661
1662        f = new CompletableFuture<>();
1663        g = new CompletableFuture<>();
1664        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1665        assertTrue(f.cancel(true));
1666        checkIncomplete(h);
1667        g.complete(1);
1668        checkCompletedWithWrappedCancellationException(h);
1669
1670        f = new CompletableFuture<>();
1671        g = new CompletableFuture<>();
1672        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1673        assertTrue(g.cancel(true));
1674        checkIncomplete(h);
1675        f.complete(3);
1676        checkCompletedWithWrappedCancellationException(h);
1677
1678        f = new CompletableFuture<>();
1679        g = new CompletableFuture<>();
1680        f.complete(3);
1681        assertTrue(g.cancel(true));
1682        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1683        checkCompletedWithWrappedCancellationException(h);
1684
1685        f = new CompletableFuture<>();
1686        g = new CompletableFuture<>();
1687        assertTrue(f.cancel(true));
1688        g.complete(3);
1689        h = f.thenAcceptBothAsync(g, r = new SubtractAction());
1690        checkCompletedWithWrappedCancellationException(h);
1691    }
1692
1693    /**
1694     * runAfterBothAsync result completes normally after normal
1695     * completion of sources
1696     */
1697    public void testRunAfterBothAsync() {
1698        CompletableFuture<Integer> f = new CompletableFuture<>();
1699        CompletableFuture<Integer> f2 = new CompletableFuture<>();
1700        Noop r = new Noop();
1701        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r);
1702        f.complete(one);
1703        checkIncomplete(g);
1704        f2.complete(two);
1705        checkCompletedNormally(g, null);
1706        assertTrue(r.ran);
1707    }
1708
1709    /**
1710     * runAfterBothAsync result completes exceptionally after exceptional
1711     * completion of source
1712     */
1713    public void testRunAfterBothAsync2() {
1714        CompletableFuture<Integer> f = new CompletableFuture<>();
1715        CompletableFuture<Integer> f2 = new CompletableFuture<>();
1716        Noop r = new Noop();
1717        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r);
1718        f.completeExceptionally(new CFException());
1719        f2.complete(two);
1720        checkCompletedWithWrappedCFException(g);
1721
1722        r = new Noop();
1723        f = new CompletableFuture<>();
1724        f2 = new CompletableFuture<>();
1725        g = f.runAfterBothAsync(f2, r);
1726        f.complete(one);
1727        f2.completeExceptionally(new CFException());
1728        checkCompletedWithWrappedCFException(g);
1729    }
1730
1731    /**
1732     * runAfterBothAsync result completes exceptionally if action does
1733     */
1734    public void testRunAfterBothAsync3() {
1735        CompletableFuture<Integer> f = new CompletableFuture<>();
1736        CompletableFuture<Integer> f2 = new CompletableFuture<>();
1737        FailingNoop r = new FailingNoop();
1738        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r);
1739        f.complete(one);
1740        checkIncomplete(g);
1741        f2.complete(two);
1742        checkCompletedWithWrappedCFException(g);
1743    }
1744
1745    /**
1746     * runAfterBothAsync result completes exceptionally if either source cancelled
1747     */
1748    public void testRunAfterBothAsync4() {
1749        CompletableFuture<Integer> f = new CompletableFuture<>();
1750        CompletableFuture<Integer> f2 = new CompletableFuture<>();
1751        Noop r = new Noop();
1752        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r);
1753        assertTrue(f.cancel(true));
1754        f2.complete(two);
1755        checkCompletedWithWrappedCancellationException(g);
1756
1757        r = new Noop();
1758        f = new CompletableFuture<>();
1759        f2 = new CompletableFuture<>();
1760        g = f.runAfterBothAsync(f2, r);
1761        f.complete(one);
1762        assertTrue(f2.cancel(true));
1763        checkCompletedWithWrappedCancellationException(g);
1764    }
1765
1766    /**
2050       * applyToEitherAsync result completes normally after normal
2051       * completion of sources
2052       */
# Line 2055 | Line 2338 | public class CompletableFutureTest exten
2338          checkCompletedWithWrappedCancellationException(g);
2339      }
2340  
2058
2341      // async with explicit executors
2342  
2343      /**
# Line 2088 | Line 2370 | public class CompletableFutureTest exten
2370          try {
2371              g.join();
2372              shouldThrow();
2373 <        } catch (Exception ok) {
2092 <        }
2373 >        } catch (CompletionException success) {}
2374          checkCompletedWithWrappedCFException(g);
2375      }
2376  
# Line 2334 | Line 2615 | public class CompletableFutureTest exten
2615      }
2616  
2617      /**
2337     * thenAcceptBothAsync result completes normally after normal
2338     * completion of sources
2339     */
2340    public void testThenAcceptBothAsyncE() {
2341        CompletableFuture<Integer> f, g;
2342        CompletableFuture<Void> h;
2343        SubtractAction r;
2344        ThreadExecutor e = new ThreadExecutor();
2345
2346        f = new CompletableFuture<>();
2347        g = new CompletableFuture<>();
2348        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2349        f.complete(3);
2350        checkIncomplete(h);
2351        g.complete(1);
2352        checkCompletedNormally(h, null);
2353        assertEquals(r.value, 2);
2354
2355        f = new CompletableFuture<>();
2356        g = new CompletableFuture<>();
2357        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2358        g.complete(1);
2359        checkIncomplete(h);
2360        f.complete(3);
2361        checkCompletedNormally(h, null);
2362        assertEquals(r.value, 2);
2363
2364        f = new CompletableFuture<>();
2365        g = new CompletableFuture<>();
2366        g.complete(1);
2367        f.complete(3);
2368        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2369        checkCompletedNormally(h, null);
2370        assertEquals(r.value, 2);
2371
2372        assertEquals(3, e.count.get());
2373    }
2374
2375    /**
2376     * thenAcceptBothAsync result completes exceptionally after exceptional
2377     * completion of source
2378     */
2379    public void testThenAcceptBothAsync2E() {
2380        CompletableFuture<Integer> f, g;
2381        CompletableFuture<Void> h;
2382        SubtractAction r;
2383        ThreadExecutor e = new ThreadExecutor();
2384
2385        f = new CompletableFuture<>();
2386        g = new CompletableFuture<>();
2387        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2388        f.completeExceptionally(new CFException());
2389        checkIncomplete(h);
2390        g.complete(1);
2391        checkCompletedWithWrappedCFException(h);
2392
2393        f = new CompletableFuture<>();
2394        g = new CompletableFuture<>();
2395        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2396        g.completeExceptionally(new CFException());
2397        checkIncomplete(h);
2398        f.complete(3);
2399        checkCompletedWithWrappedCFException(h);
2400
2401        f = new CompletableFuture<>();
2402        g = new CompletableFuture<>();
2403        f.complete(3);
2404        g.completeExceptionally(new CFException());
2405        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2406        checkCompletedWithWrappedCFException(h);
2407
2408        f = new CompletableFuture<>();
2409        g = new CompletableFuture<>();
2410        f.completeExceptionally(new CFException());
2411        g.complete(3);
2412        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2413        checkCompletedWithWrappedCFException(h);
2414
2415        assertEquals(0, e.count.get());
2416    }
2417
2418    /**
2419     * thenAcceptBothAsync result completes exceptionally if action does
2420     */
2421    public void testThenAcceptBothAsync3E() {
2422        CompletableFuture<Integer> f, g;
2423        CompletableFuture<Void> h;
2424        FailingBiConsumer r;
2425        ThreadExecutor e = new ThreadExecutor();
2426
2427        f = new CompletableFuture<>();
2428        g = new CompletableFuture<>();
2429        h = f.thenAcceptBothAsync(g, r = new FailingBiConsumer(), e);
2430        f.complete(3);
2431        checkIncomplete(h);
2432        g.complete(1);
2433        checkCompletedWithWrappedCFException(h);
2434
2435        f = new CompletableFuture<>();
2436        g = new CompletableFuture<>();
2437        f.complete(3);
2438        g.complete(1);
2439        h = f.thenAcceptBothAsync(g, r = new FailingBiConsumer(), e);
2440        checkCompletedWithWrappedCFException(h);
2441
2442        assertEquals(2, e.count.get());
2443    }
2444
2445    /**
2446     * thenAcceptBothAsync result completes exceptionally if either source cancelled
2447     */
2448    public void testThenAcceptBothAsync4E() {
2449        CompletableFuture<Integer> f, g;
2450        CompletableFuture<Void> h;
2451        SubtractAction r;
2452        ThreadExecutor e = new ThreadExecutor();
2453
2454        f = new CompletableFuture<>();
2455        g = new CompletableFuture<>();
2456        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2457        assertTrue(f.cancel(true));
2458        checkIncomplete(h);
2459        g.complete(1);
2460        checkCompletedWithWrappedCancellationException(h);
2461
2462        f = new CompletableFuture<>();
2463        g = new CompletableFuture<>();
2464        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2465        assertTrue(g.cancel(true));
2466        checkIncomplete(h);
2467        f.complete(3);
2468        checkCompletedWithWrappedCancellationException(h);
2469
2470        f = new CompletableFuture<>();
2471        g = new CompletableFuture<>();
2472        f.complete(3);
2473        assertTrue(g.cancel(true));
2474        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2475        checkCompletedWithWrappedCancellationException(h);
2476
2477        f = new CompletableFuture<>();
2478        g = new CompletableFuture<>();
2479        assertTrue(f.cancel(true));
2480        g.complete(3);
2481        h = f.thenAcceptBothAsync(g, r = new SubtractAction(), e);
2482        checkCompletedWithWrappedCancellationException(h);
2483
2484        assertEquals(0, e.count.get());
2485    }
2486
2487    /**
2488     * runAfterBothAsync result completes normally after normal
2489     * completion of sources
2490     */
2491    public void testRunAfterBothAsyncE() {
2492        CompletableFuture<Integer> f = new CompletableFuture<>();
2493        CompletableFuture<Integer> f2 = new CompletableFuture<>();
2494        Noop r = new Noop();
2495        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r, new ThreadExecutor());
2496        f.complete(one);
2497        checkIncomplete(g);
2498        f2.complete(two);
2499        checkCompletedNormally(g, null);
2500        assertTrue(r.ran);
2501    }
2502
2503    /**
2504     * runAfterBothAsync result completes exceptionally after exceptional
2505     * completion of source
2506     */
2507    public void testRunAfterBothAsync2E() {
2508        CompletableFuture<Integer> f = new CompletableFuture<>();
2509        CompletableFuture<Integer> f2 = new CompletableFuture<>();
2510        Noop r = new Noop();
2511        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r, new ThreadExecutor());
2512        f.completeExceptionally(new CFException());
2513        f2.complete(two);
2514        checkCompletedWithWrappedCFException(g);
2515
2516        r = new Noop();
2517        f = new CompletableFuture<>();
2518        f2 = new CompletableFuture<>();
2519        g = f.runAfterBothAsync(f2, r, new ThreadExecutor());
2520        f.complete(one);
2521        f2.completeExceptionally(new CFException());
2522        checkCompletedWithWrappedCFException(g);
2523    }
2524
2525    /**
2526     * runAfterBothAsync result completes exceptionally if action does
2527     */
2528    public void testRunAfterBothAsync3E() {
2529        CompletableFuture<Integer> f = new CompletableFuture<>();
2530        CompletableFuture<Integer> f2 = new CompletableFuture<>();
2531        FailingNoop r = new FailingNoop();
2532        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r, new ThreadExecutor());
2533        f.complete(one);
2534        checkIncomplete(g);
2535        f2.complete(two);
2536        checkCompletedWithWrappedCFException(g);
2537    }
2538
2539    /**
2540     * runAfterBothAsync result completes exceptionally if either source cancelled
2541     */
2542    public void testRunAfterBothAsync4E() {
2543        CompletableFuture<Integer> f = new CompletableFuture<>();
2544        CompletableFuture<Integer> f2 = new CompletableFuture<>();
2545        Noop r = new Noop();
2546        CompletableFuture<Void> g = f.runAfterBothAsync(f2, r, new ThreadExecutor());
2547        assertTrue(f.cancel(true));
2548        f2.complete(two);
2549        checkCompletedWithWrappedCancellationException(g);
2550
2551        r = new Noop();
2552        f = new CompletableFuture<>();
2553        f2 = new CompletableFuture<>();
2554        g = f.runAfterBothAsync(f2, r, new ThreadExecutor());
2555        f.complete(one);
2556        assertTrue(f2.cancel(true));
2557        checkCompletedWithWrappedCancellationException(g);
2558    }
2559
2560    /**
2618       * applyToEitherAsync result completes normally after normal
2619       * completion of sources
2620       */
# Line 2826 | Line 2883 | public class CompletableFutureTest exten
2883       * with the value null
2884       */
2885      public void testAllOf_empty() throws Exception {
2886 <        CompletableFuture<?> f = CompletableFuture.allOf();
2886 >        CompletableFuture<Void> f = CompletableFuture.allOf();
2887          checkCompletedNormally(f, null);
2888      }
2889  
2890      /**
2891 <     * allOf returns a future completed when all components complete
2891 >     * allOf returns a future completed normally with the value null
2892 >     * when all components complete normally
2893       */
2894 <    public void testAllOf() throws Exception {
2894 >    public void testAllOf_normal() throws Exception {
2895          for (int k = 1; k < 20; ++k) {
2896              CompletableFuture<Integer>[] fs = (CompletableFuture<Integer>[]) new CompletableFuture[k];
2897              for (int i = 0; i < k; ++i)
# Line 2841 | Line 2899 | public class CompletableFutureTest exten
2899              CompletableFuture<Void> f = CompletableFuture.allOf(fs);
2900              for (int i = 0; i < k; ++i) {
2901                  checkIncomplete(f);
2902 +                checkIncomplete(CompletableFuture.allOf(fs));
2903                  fs[i].complete(one);
2904              }
2905              checkCompletedNormally(f, null);
2906 +            checkCompletedNormally(CompletableFuture.allOf(fs), null);
2907          }
2908      }
2909  
# Line 2851 | Line 2911 | public class CompletableFutureTest exten
2911       * anyOf(no component futures) returns an incomplete future
2912       */
2913      public void testAnyOf_empty() throws Exception {
2914 <        CompletableFuture<?> f = CompletableFuture.anyOf();
2914 >        CompletableFuture<Object> f = CompletableFuture.anyOf();
2915          checkIncomplete(f);
2916      }
2917  
2918      /**
2919 <     * anyOf returns a future completed when any components complete
2919 >     * anyOf returns a future completed normally with a value when
2920 >     * a component future does
2921       */
2922 <    public void testAnyOf() throws Exception {
2923 <        for (int k = 1; k < 20; ++k) {
2922 >    public void testAnyOf_normal() throws Exception {
2923 >        for (int k = 0; k < 10; ++k) {
2924              CompletableFuture[] fs = new CompletableFuture[k];
2925              for (int i = 0; i < k; ++i)
2926                  fs[i] = new CompletableFuture<>();
# Line 2868 | Line 2929 | public class CompletableFutureTest exten
2929              for (int i = 0; i < k; ++i) {
2930                  fs[i].complete(one);
2931                  checkCompletedNormally(f, one);
2932 +                checkCompletedNormally(CompletableFuture.anyOf(fs), one);
2933 +            }
2934 +        }
2935 +    }
2936 +
2937 +    /**
2938 +     * anyOf result completes exceptionally when any component does.
2939 +     */
2940 +    public void testAnyOf_exceptional() throws Exception {
2941 +        for (int k = 0; k < 10; ++k) {
2942 +            CompletableFuture[] fs = new CompletableFuture[k];
2943 +            for (int i = 0; i < k; ++i)
2944 +                fs[i] = new CompletableFuture<>();
2945 +            CompletableFuture<Object> f = CompletableFuture.anyOf(fs);
2946 +            checkIncomplete(f);
2947 +            for (int i = 0; i < k; ++i) {
2948 +                fs[i].completeExceptionally(new CFException());
2949 +                checkCompletedWithWrappedCFException(f);
2950 +                checkCompletedWithWrappedCFException(CompletableFuture.anyOf(fs));
2951              }
2952          }
2953      }
# Line 2883 | Line 2963 | public class CompletableFutureTest exten
2963          ThreadExecutor exec = new ThreadExecutor();
2964  
2965          Runnable[] throwingActions = {
2966 <            () -> { CompletableFuture.supplyAsync(null); },
2967 <            () -> { CompletableFuture.supplyAsync(null, exec); },
2968 <            () -> { CompletableFuture.supplyAsync(supplyOne, null); },
2969 <
2970 <            () -> { CompletableFuture.runAsync(null); },
2971 <            () -> { CompletableFuture.runAsync(null, exec); },
2972 <            () -> { CompletableFuture.runAsync(() -> {}, null); },
2973 <
2974 <            () -> { f.completeExceptionally(null); },
2975 <
2976 <            () -> { f.thenApply(null); },
2977 <            () -> { f.thenApplyAsync(null); },
2978 <            () -> { f.thenApplyAsync((x) -> x, null); },
2979 <            () -> { f.thenApplyAsync(null, exec); },
2980 <
2981 <            () -> { f.thenAccept(null); },
2982 <            () -> { f.thenAcceptAsync(null); },
2983 <            () -> { f.thenAcceptAsync((x) -> { ; }, null); },
2984 <            () -> { f.thenAcceptAsync(null, exec); },
2985 <
2986 <            () -> { f.thenRun(null); },
2987 <            () -> { f.thenRunAsync(null); },
2988 <            () -> { f.thenRunAsync(() -> { ; }, null); },
2989 <            () -> { f.thenRunAsync(null, exec); },
2990 <
2991 <            () -> { f.thenCombine(g, null); },
2992 <            () -> { f.thenCombineAsync(g, null); },
2993 <            () -> { f.thenCombineAsync(g, null, exec); },
2994 <            () -> { f.thenCombine(nullFuture, (x, y) -> x); },
2995 <            () -> { f.thenCombineAsync(nullFuture, (x, y) -> x); },
2996 <            () -> { f.thenCombineAsync(nullFuture, (x, y) -> x, exec); },
2997 <            () -> { f.thenCombineAsync(g, (x, y) -> x, null); },
2998 <
2999 <            () -> { f.thenAcceptBoth(g, null); },
3000 <            () -> { f.thenAcceptBothAsync(g, null); },
3001 <            () -> { f.thenAcceptBothAsync(g, null, exec); },
3002 <            () -> { f.thenAcceptBoth(nullFuture, (x, y) -> {}); },
3003 <            () -> { f.thenAcceptBothAsync(nullFuture, (x, y) -> {}); },
3004 <            () -> { f.thenAcceptBothAsync(nullFuture, (x, y) -> {}, exec); },
3005 <            () -> { f.thenAcceptBothAsync(g, (x, y) -> {}, null); },
3006 <
3007 <            () -> { f.runAfterBoth(g, null); },
3008 <            () -> { f.runAfterBothAsync(g, null); },
3009 <            () -> { f.runAfterBothAsync(g, null, exec); },
3010 <            () -> { f.runAfterBoth(nullFuture, () -> {}); },
3011 <            () -> { f.runAfterBothAsync(nullFuture, () -> {}); },
3012 <            () -> { f.runAfterBothAsync(nullFuture, () -> {}, exec); },
3013 <            () -> { f.runAfterBothAsync(g, () -> {}, null); },
3014 <
3015 <            () -> { f.applyToEither(g, null); },
3016 <            () -> { f.applyToEitherAsync(g, null); },
3017 <            () -> { f.applyToEitherAsync(g, null, exec); },
3018 <            () -> { f.applyToEither(nullFuture, (x) -> x); },
3019 <            () -> { f.applyToEitherAsync(nullFuture, (x) -> x); },
3020 <            () -> { f.applyToEitherAsync(nullFuture, (x) -> x, exec); },
3021 <            () -> { f.applyToEitherAsync(g, (x) -> x, null); },
3022 <
3023 <            () -> { f.acceptEither(g, null); },
3024 <            () -> { f.acceptEitherAsync(g, null); },
3025 <            () -> { f.acceptEitherAsync(g, null, exec); },
3026 <            () -> { f.acceptEither(nullFuture, (x) -> {}); },
3027 <            () -> { f.acceptEitherAsync(nullFuture, (x) -> {}); },
3028 <            () -> { f.acceptEitherAsync(nullFuture, (x) -> {}, exec); },
3029 <            () -> { f.acceptEitherAsync(g, (x) -> {}, null); },
3030 <
3031 <            () -> { f.runAfterEither(g, null); },
3032 <            () -> { f.runAfterEitherAsync(g, null); },
3033 <            () -> { f.runAfterEitherAsync(g, null, exec); },
3034 <            () -> { f.runAfterEither(nullFuture, () -> {}); },
3035 <            () -> { f.runAfterEitherAsync(nullFuture, () -> {}); },
3036 <            () -> { f.runAfterEitherAsync(nullFuture, () -> {}, exec); },
3037 <            () -> { f.runAfterEitherAsync(g, () -> {}, null); },
3038 <
3039 <            () -> { f.thenCompose(null); },
3040 <            () -> { f.thenComposeAsync(null); },
3041 <            () -> { f.thenComposeAsync(new CompletableFutureInc(), null); },
3042 <            () -> { f.thenComposeAsync(null, exec); },
3043 <
3044 <            () -> { f.exceptionally(null); },
3045 <
3046 <            () -> { f.handle(null); },
3047 <
3048 <            () -> { CompletableFuture.allOf((CompletableFuture<?>)null); },
3049 <            () -> { CompletableFuture.allOf((CompletableFuture<?>[])null); },
3050 <            () -> { CompletableFuture.allOf(f, null); },
3051 <            () -> { CompletableFuture.allOf(null, f); },
3052 <
3053 <            () -> { CompletableFuture.anyOf((CompletableFuture<?>)null); },
3054 <            () -> { CompletableFuture.anyOf((CompletableFuture<?>[])null); },
3055 <            () -> { CompletableFuture.anyOf(f, null); },
3056 <            () -> { CompletableFuture.anyOf(null, f); },
2966 >            () -> CompletableFuture.supplyAsync(null),
2967 >            () -> CompletableFuture.supplyAsync(null, exec),
2968 >            () -> CompletableFuture.supplyAsync(supplyOne, null),
2969 >
2970 >            () -> CompletableFuture.runAsync(null),
2971 >            () -> CompletableFuture.runAsync(null, exec),
2972 >            () -> CompletableFuture.runAsync(() -> {}, null),
2973 >
2974 >            () -> f.completeExceptionally(null),
2975 >
2976 >            () -> f.thenApply(null),
2977 >            () -> f.thenApplyAsync(null),
2978 >            () -> f.thenApplyAsync((x) -> x, null),
2979 >            () -> f.thenApplyAsync(null, exec),
2980 >
2981 >            () -> f.thenAccept(null),
2982 >            () -> f.thenAcceptAsync(null),
2983 >            () -> f.thenAcceptAsync((x) -> {} , null),
2984 >            () -> f.thenAcceptAsync(null, exec),
2985 >
2986 >            () -> f.thenRun(null),
2987 >            () -> f.thenRunAsync(null),
2988 >            () -> f.thenRunAsync(() -> {} , null),
2989 >            () -> f.thenRunAsync(null, exec),
2990 >
2991 >            () -> f.thenCombine(g, null),
2992 >            () -> f.thenCombineAsync(g, null),
2993 >            () -> f.thenCombineAsync(g, null, exec),
2994 >            () -> f.thenCombine(nullFuture, (x, y) -> x),
2995 >            () -> f.thenCombineAsync(nullFuture, (x, y) -> x),
2996 >            () -> f.thenCombineAsync(nullFuture, (x, y) -> x, exec),
2997 >            () -> f.thenCombineAsync(g, (x, y) -> x, null),
2998 >
2999 >            () -> f.thenAcceptBoth(g, null),
3000 >            () -> f.thenAcceptBothAsync(g, null),
3001 >            () -> f.thenAcceptBothAsync(g, null, exec),
3002 >            () -> f.thenAcceptBoth(nullFuture, (x, y) -> {}),
3003 >            () -> f.thenAcceptBothAsync(nullFuture, (x, y) -> {}),
3004 >            () -> f.thenAcceptBothAsync(nullFuture, (x, y) -> {}, exec),
3005 >            () -> f.thenAcceptBothAsync(g, (x, y) -> {}, null),
3006 >
3007 >            () -> f.runAfterBoth(g, null),
3008 >            () -> f.runAfterBothAsync(g, null),
3009 >            () -> f.runAfterBothAsync(g, null, exec),
3010 >            () -> f.runAfterBoth(nullFuture, () -> {}),
3011 >            () -> f.runAfterBothAsync(nullFuture, () -> {}),
3012 >            () -> f.runAfterBothAsync(nullFuture, () -> {}, exec),
3013 >            () -> f.runAfterBothAsync(g, () -> {}, null),
3014 >
3015 >            () -> f.applyToEither(g, null),
3016 >            () -> f.applyToEitherAsync(g, null),
3017 >            () -> f.applyToEitherAsync(g, null, exec),
3018 >            () -> f.applyToEither(nullFuture, (x) -> x),
3019 >            () -> f.applyToEitherAsync(nullFuture, (x) -> x),
3020 >            () -> f.applyToEitherAsync(nullFuture, (x) -> x, exec),
3021 >            () -> f.applyToEitherAsync(g, (x) -> x, null),
3022 >
3023 >            () -> f.acceptEither(g, null),
3024 >            () -> f.acceptEitherAsync(g, null),
3025 >            () -> f.acceptEitherAsync(g, null, exec),
3026 >            () -> f.acceptEither(nullFuture, (x) -> {}),
3027 >            () -> f.acceptEitherAsync(nullFuture, (x) -> {}),
3028 >            () -> f.acceptEitherAsync(nullFuture, (x) -> {}, exec),
3029 >            () -> f.acceptEitherAsync(g, (x) -> {}, null),
3030 >
3031 >            () -> f.runAfterEither(g, null),
3032 >            () -> f.runAfterEitherAsync(g, null),
3033 >            () -> f.runAfterEitherAsync(g, null, exec),
3034 >            () -> f.runAfterEither(nullFuture, () -> {}),
3035 >            () -> f.runAfterEitherAsync(nullFuture, () -> {}),
3036 >            () -> f.runAfterEitherAsync(nullFuture, () -> {}, exec),
3037 >            () -> f.runAfterEitherAsync(g, () -> {}, null),
3038 >
3039 >            () -> f.thenCompose(null),
3040 >            () -> f.thenComposeAsync(null),
3041 >            () -> f.thenComposeAsync(new CompletableFutureInc(), null),
3042 >            () -> f.thenComposeAsync(null, exec),
3043 >
3044 >            () -> f.exceptionally(null),
3045 >
3046 >            () -> f.handle(null),
3047 >
3048 >            () -> CompletableFuture.allOf((CompletableFuture<?>)null),
3049 >            () -> CompletableFuture.allOf((CompletableFuture<?>[])null),
3050 >            () -> CompletableFuture.allOf(f, null),
3051 >            () -> CompletableFuture.allOf(null, f),
3052 >
3053 >            () -> CompletableFuture.anyOf((CompletableFuture<?>)null),
3054 >            () -> CompletableFuture.anyOf((CompletableFuture<?>[])null),
3055 >            () -> CompletableFuture.anyOf(f, null),
3056 >            () -> CompletableFuture.anyOf(null, f),
3057 >
3058 >            () -> f.obtrudeException(null),
3059          };
3060  
3061          assertThrows(NullPointerException.class, throwingActions);
3062          assertEquals(0, exec.count.get());
3063      }
3064  
3065 +    /**
3066 +     * toCompletableFuture returns this CompletableFuture.
3067 +     */
3068 +    public void testToCompletableFuture() {
3069 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3070 +        assertSame(f, f.toCompletableFuture());
3071 +    }
3072 +
3073 +    /**
3074 +     * whenComplete action executes on normal completion, propagating
3075 +     * source result.
3076 +     */
3077 +    public void testWhenComplete1() {
3078 +        final AtomicInteger a = new AtomicInteger();
3079 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3080 +        CompletableFuture<Integer> g =
3081 +            f.whenComplete((Integer x, Throwable t) -> a.getAndIncrement());
3082 +        f.complete(three);
3083 +        checkCompletedNormally(f, three);
3084 +        checkCompletedNormally(g, three);
3085 +        assertEquals(a.get(), 1);
3086 +    }
3087 +
3088 +    /**
3089 +     * whenComplete action executes on exceptional completion, propagating
3090 +     * source result.
3091 +     */
3092 +    public void testWhenComplete2() {
3093 +        final AtomicInteger a = new AtomicInteger();
3094 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3095 +        CompletableFuture<Integer> g =
3096 +            f.whenComplete((Integer x, Throwable t) -> a.getAndIncrement());
3097 +        f.completeExceptionally(new CFException());
3098 +        assertTrue(f.isCompletedExceptionally());
3099 +        assertTrue(g.isCompletedExceptionally());
3100 +        assertEquals(a.get(), 1);
3101 +    }
3102 +
3103 +    /**
3104 +     * If a whenComplete action throws an exception when triggered by
3105 +     * a normal completion, it completes exceptionally
3106 +     */
3107 +    public void testWhenComplete3() {
3108 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3109 +        CompletableFuture<Integer> g =
3110 +            f.whenComplete((Integer x, Throwable t) ->
3111 +                           { throw new CFException(); } );
3112 +        f.complete(three);
3113 +        checkCompletedNormally(f, three);
3114 +        assertTrue(g.isCompletedExceptionally());
3115 +        checkCompletedWithWrappedCFException(g);
3116 +    }
3117 +
3118 +    /**
3119 +     * whenCompleteAsync action executes on normal completion, propagating
3120 +     * source result.
3121 +     */
3122 +    public void testWhenCompleteAsync1() {
3123 +        final AtomicInteger a = new AtomicInteger();
3124 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3125 +        CompletableFuture<Integer> g =
3126 +            f.whenCompleteAsync((Integer x, Throwable t) -> a.getAndIncrement());
3127 +        f.complete(three);
3128 +        checkCompletedNormally(f, three);
3129 +        checkCompletedNormally(g, three);
3130 +        assertEquals(a.get(), 1);
3131 +    }
3132 +
3133 +    /**
3134 +     * whenCompleteAsync action executes on exceptional completion, propagating
3135 +     * source result.
3136 +     */
3137 +    public void testWhenCompleteAsync2() {
3138 +        final AtomicInteger a = new AtomicInteger();
3139 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3140 +        CompletableFuture<Integer> g =
3141 +            f.whenCompleteAsync((Integer x, Throwable t) -> a.getAndIncrement());
3142 +        f.completeExceptionally(new CFException());
3143 +        checkCompletedWithWrappedCFException(f);
3144 +        checkCompletedWithWrappedCFException(g);
3145 +    }
3146 +
3147 +    /**
3148 +     * If a whenCompleteAsync action throws an exception when
3149 +     * triggered by a normal completion, it completes exceptionally
3150 +     */
3151 +    public void testWhenCompleteAsync3() {
3152 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3153 +        CompletableFuture<Integer> g =
3154 +            f.whenCompleteAsync((Integer x, Throwable t) ->
3155 +                           { throw new CFException(); } );
3156 +        f.complete(three);
3157 +        checkCompletedNormally(f, three);
3158 +        checkCompletedWithWrappedCFException(g);
3159 +    }
3160 +
3161 +    /**
3162 +     * whenCompleteAsync action executes on normal completion, propagating
3163 +     * source result.
3164 +     */
3165 +    public void testWhenCompleteAsync1e() {
3166 +        final AtomicInteger a = new AtomicInteger();
3167 +        ThreadExecutor exec = new ThreadExecutor();
3168 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3169 +        CompletableFuture<Integer> g =
3170 +            f.whenCompleteAsync((Integer x, Throwable t) -> a.getAndIncrement(),
3171 +                                exec);
3172 +        f.complete(three);
3173 +        checkCompletedNormally(f, three);
3174 +        checkCompletedNormally(g, three);
3175 +        assertEquals(a.get(), 1);
3176 +    }
3177 +
3178 +    /**
3179 +     * whenCompleteAsync action executes on exceptional completion, propagating
3180 +     * source result.
3181 +     */
3182 +    public void testWhenCompleteAsync2e() {
3183 +        final AtomicInteger a = new AtomicInteger();
3184 +        ThreadExecutor exec = new ThreadExecutor();
3185 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3186 +        CompletableFuture<Integer> g =
3187 +            f.whenCompleteAsync((Integer x, Throwable t) -> a.getAndIncrement(),
3188 +                                exec);
3189 +        f.completeExceptionally(new CFException());
3190 +        checkCompletedWithWrappedCFException(f);
3191 +        checkCompletedWithWrappedCFException(g);
3192 +    }
3193 +
3194 +    /**
3195 +     * If a whenCompleteAsync action throws an exception when triggered
3196 +     * by a normal completion, it completes exceptionally
3197 +     */
3198 +    public void testWhenCompleteAsync3e() {
3199 +        ThreadExecutor exec = new ThreadExecutor();
3200 +        CompletableFuture<Integer> f = new CompletableFuture<>();
3201 +        CompletableFuture<Integer> g =
3202 +            f.whenCompleteAsync((Integer x, Throwable t) ->
3203 +                                { throw new CFException(); },
3204 +                                exec);
3205 +        f.complete(three);
3206 +        checkCompletedNormally(f, three);
3207 +        checkCompletedWithWrappedCFException(g);
3208 +    }
3209 +
3210 +    /**
3211 +     * handleAsync action completes normally with function value on
3212 +     * either normal or exceptional completion of source
3213 +     */
3214 +    public void testHandleAsync() {
3215 +        CompletableFuture<Integer> f, g;
3216 +        IntegerHandler r;
3217 +
3218 +        f = new CompletableFuture<>();
3219 +        g = f.handleAsync(r = new IntegerHandler());
3220 +        assertFalse(r.ran);
3221 +        f.completeExceptionally(new CFException());
3222 +        checkCompletedWithWrappedCFException(f);
3223 +        checkCompletedNormally(g, three);
3224 +        assertTrue(r.ran);
3225 +
3226 +        f = new CompletableFuture<>();
3227 +        g = f.handleAsync(r = new IntegerHandler());
3228 +        assertFalse(r.ran);
3229 +        f.completeExceptionally(new CFException());
3230 +        checkCompletedWithWrappedCFException(f);
3231 +        checkCompletedNormally(g, three);
3232 +        assertTrue(r.ran);
3233 +
3234 +        f = new CompletableFuture<>();
3235 +        g = f.handleAsync(r = new IntegerHandler());
3236 +        assertFalse(r.ran);
3237 +        f.complete(one);
3238 +        checkCompletedNormally(f, one);
3239 +        checkCompletedNormally(g, two);
3240 +        assertTrue(r.ran);
3241 +
3242 +        f = new CompletableFuture<>();
3243 +        g = f.handleAsync(r = new IntegerHandler());
3244 +        assertFalse(r.ran);
3245 +        f.complete(one);
3246 +        checkCompletedNormally(f, one);
3247 +        checkCompletedNormally(g, two);
3248 +        assertTrue(r.ran);
3249 +    }
3250 +
3251 +    /**
3252 +     * handleAsync action with Executor completes normally with
3253 +     * function value on either normal or exceptional completion of
3254 +     * source
3255 +     */
3256 +    public void testHandleAsync2() {
3257 +        CompletableFuture<Integer> f, g;
3258 +        ThreadExecutor exec = new ThreadExecutor();
3259 +        IntegerHandler r;
3260 +
3261 +        f = new CompletableFuture<>();
3262 +        g = f.handleAsync(r = new IntegerHandler(), exec);
3263 +        assertFalse(r.ran);
3264 +        f.completeExceptionally(new CFException());
3265 +        checkCompletedWithWrappedCFException(f);
3266 +        checkCompletedNormally(g, three);
3267 +        assertTrue(r.ran);
3268 +
3269 +        f = new CompletableFuture<>();
3270 +        g = f.handleAsync(r = new IntegerHandler(), exec);
3271 +        assertFalse(r.ran);
3272 +        f.completeExceptionally(new CFException());
3273 +        checkCompletedWithWrappedCFException(f);
3274 +        checkCompletedNormally(g, three);
3275 +        assertTrue(r.ran);
3276 +
3277 +        f = new CompletableFuture<>();
3278 +        g = f.handleAsync(r = new IntegerHandler(), exec);
3279 +        assertFalse(r.ran);
3280 +        f.complete(one);
3281 +        checkCompletedNormally(f, one);
3282 +        checkCompletedNormally(g, two);
3283 +        assertTrue(r.ran);
3284 +
3285 +        f = new CompletableFuture<>();
3286 +        g = f.handleAsync(r = new IntegerHandler(), exec);
3287 +        assertFalse(r.ran);
3288 +        f.complete(one);
3289 +        checkCompletedNormally(f, one);
3290 +        checkCompletedNormally(g, two);
3291 +        assertTrue(r.ran);
3292 +    }
3293 +
3294   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines