test/java/util/Optional/Basic.java

Print this page
rev 7596 : 8015317: Optional.filter, map, and flatMap
Reviewed-by:
Contributed-by: brian.goetz@oracle.com, henry.jen@oracle.com

@@ -114,9 +114,119 @@
         assertSame(Boolean.TRUE, present.orElseGet(()-> Boolean.FALSE));
         assertSame(Boolean.TRUE, present.<RuntimeException>orElseThrow( null));
         assertSame(Boolean.TRUE, present.<RuntimeException>orElseThrow(ObscureException::new));
     }
 
+    @Test(groups = "unit")
+    public void testOfNullable() {
+        Optional<String> instance = Optional.ofNullable(null);
+        assertFalse(instance.isPresent());
+
+        instance = Optional.ofNullable("Duke");
+        assertTrue(instance.isPresent());
+        assertEquals(instance.get(), "Duke");
+    }
+
+    @Test(groups = "unit")
+    public void testFilter() {
+        // Null mapper function
+        Optional<String> empty = Optional.empty();
+        Optional<String> duke = Optional.of("Duke");
+
+        try {
+            Optional<String> result = empty.filter(null);
+            fail("Should throw NPE on null mapping function");
+        } catch (NullPointerException npe) {
+            // expected
+        }
+
+        Optional<String> result = empty.filter(String::isEmpty);
+        assertFalse(result.isPresent());
+
+        result = duke.filter(String::isEmpty);
+        assertFalse(result.isPresent());
+        result = duke.filter(s -> s.startsWith("D"));
+        assertTrue(result.isPresent());
+        assertEquals(result.get(), "Duke");
+
+        Optional<String> emptyString = Optional.of("");
+        result = emptyString.filter(String::isEmpty);
+        assertTrue(result.isPresent());
+        assertEquals(result.get(), "");
+    }
+
+    @Test(groups = "unit")
+    public void testMap() {
+        Optional<String> empty = Optional.empty();
+        Optional<String> duke = Optional.of("Duke");
+
+        // Null mapper function
+        try {
+            Optional<Boolean> b = empty.map(null);
+            fail("Should throw NPE on null mapping function");
+        } catch (NullPointerException npe) {
+            // expected
+        }
+
+        // Map an empty value
+        Optional<Boolean> b = empty.map(String::isEmpty);
+        assertFalse(b.isPresent());
+
+        // Map into null
+        b = empty.map(n -> null);
+        assertFalse(b.isPresent());
+        b = duke.map(s -> null);
+        assertFalse(b.isPresent());
+
+        // Map to value
+        Optional<Integer> l = duke.map(String::length);
+        assertEquals(l.get().intValue(), 4);
+    }
+
+    @Test(groups = "unit")
+    public void testFlatMap() {
+        Optional<String> empty = Optional.empty();
+        Optional<String> duke = Optional.of("Duke");
+
+        // Null mapper function
+        try {
+            Optional<Boolean> b = empty.flatMap(null);
+            fail("Should throw NPE on null mapping function");
+        } catch (NullPointerException npe) {
+            // expected
+        }
+
+        // Map into null
+        try {
+            Optional<Boolean> b = duke.flatMap(s -> null);
+            fail("Should throw NPE when mapper return null");
+        } catch (NullPointerException npe) {
+            // expected
+        }
+
+        // Empty won't invoke mapper function
+        try {
+            Optional<Boolean> b = empty.flatMap(s -> null);
+            assertFalse(b.isPresent());
+        } catch (NullPointerException npe) {
+            fail("Mapper function should not be invoked");
+        }
+
+        // Map an empty value
+        Optional<Integer> l = empty.flatMap(s -> Optional.of(s.length()));
+        assertFalse(l.isPresent());
+
+        // Map to value
+        Optional<Integer> fixture = Optional.of(Integer.MAX_VALUE);
+        l = duke.flatMap(s -> Optional.of(s.length()));
+        assertTrue(l.isPresent());
+        assertEquals(l.get().intValue(), 4);
+
+        // Verify same instance
+        l = duke.flatMap(s -> fixture);
+        assertSame(l, fixture);
+    }
+
     private static class ObscureException extends RuntimeException {
 
     }
 }