Skip to content

Commit 15426f9

Browse files
author
Vincent Potucek
committed
deprecated ObjectUtils defaultIfNull add getIfNull and getFirstNonNull
1 parent 8f9f302 commit 15426f9

File tree

7 files changed

+96
-9
lines changed

7 files changed

+96
-9
lines changed

src/main/java/org/apache/commons/lang3/ObjectUtils.java

+52-2
Original file line numberDiff line numberDiff line change
@@ -580,7 +580,7 @@ public static short CONST_SHORT(final int v) {
580580
* @param object the {@link Object} to test, may be {@code null}
581581
* @param defaultValue the default value to return, may be {@code null}
582582
* @return {@code object} if it is not {@code null}, defaultValue otherwise
583-
* TODO Rename to getIfNull in 4.0
583+
* @deprecated use {@link ObjectUtils#getIfNull(Object, Object)}
584584
*/
585585
public static <T> T defaultIfNull(final T object, final T defaultValue) {
586586
return object != null ? object : defaultValue;
@@ -640,6 +640,36 @@ public static <T> T firstNonNull(final T... values) {
640640
return Streams.of(values).filter(Objects::nonNull).findFirst().orElse(null);
641641
}
642642

643+
/**
644+
* Returns the first non-null value in the collection. If all values are {@code null},
645+
* or if the collection is {@code null} or empty, an empty {@link Optional} is returned.
646+
*
647+
* <p>Examples:
648+
* <pre>
649+
* ObjectUtils.firstNonNull(Arrays.asList(null, null)) = Optional.empty()
650+
* ObjectUtils.firstNonNull(Arrays.asList(null, "")) = Optional.of("")
651+
* ObjectUtils.firstNonNull(Arrays.asList(null, null, "")) = Optional.of("")
652+
* ObjectUtils.firstNonNull(Arrays.asList(null, "zz")) = Optional.of("zz")
653+
* ObjectUtils.firstNonNull(Arrays.asList("abc", *)) = Optional.of("abc")
654+
* ObjectUtils.firstNonNull(Arrays.asList(null, "xyz", *)) = Optional.of("xyz")
655+
* ObjectUtils.firstNonNull(Arrays.asList(Boolean.TRUE, *)) = Optional.of(Boolean.TRUE)
656+
* ObjectUtils.firstNonNull(Collections.emptyList()) = Optional.empty()
657+
* ObjectUtils.firstNonNull(null) = Optional.empty()
658+
* </pre>
659+
*
660+
* @param <T> the type of elements in the collection
661+
* @param values the collection to test, may be {@code null} or empty
662+
* @return an {@link Optional} containing the first non-null value in the collection,
663+
* or an empty {@link Optional} if no non-null value is found
664+
* @since 3.18.0
665+
*/
666+
public static <T> Optional<T> firstNonNull(final Collection<T> values) {
667+
if (Objects.isNull(values) || values.isEmpty()) {
668+
return Optional.empty();
669+
}
670+
return values.stream().filter(Objects::nonNull).findFirst();
671+
}
672+
643673
/**
644674
* Delegates to {@link Object#getClass()} using generics.
645675
*
@@ -709,6 +739,26 @@ public static <T> T getIfNull(final T object, final Supplier<T> defaultSupplier)
709739
return object != null ? object : Suppliers.get(defaultSupplier);
710740
}
711741

742+
/**
743+
* Returns a default value if the object passed is {@code null}.
744+
*
745+
* <pre>
746+
* ObjectUtils.getIfNull(null, null) = null
747+
* ObjectUtils.getIfNull(null, "") = ""
748+
* ObjectUtils.getIfNull(null, "zz") = "zz"
749+
* ObjectUtils.getIfNull("abc", *) = "abc"
750+
* ObjectUtils.getIfNull(Boolean.TRUE, *) = Boolean.TRUE
751+
* </pre>
752+
*
753+
* @param <T> the type of the object
754+
* @param object the {@link Object} to test, may be {@code null}
755+
* @param defaultValue the default value to return, may be {@code null}
756+
* @return {@code object} if it is not {@code null}, defaultValue otherwise
757+
*/
758+
public static <T> T getIfNull(final T object, final T defaultValue) {
759+
return object != null ? object : defaultValue;
760+
}
761+
712762
/**
713763
* Gets the hash code of an object returning zero when the
714764
* object is {@code null}.
@@ -1382,7 +1432,7 @@ public static void wait(final Object obj, final Duration duration) throws Interr
13821432
/**
13831433
* {@link ObjectUtils} instances should NOT be constructed in
13841434
* standard programming. Instead, the static methods on the class should
1385-
* be used, such as {@code ObjectUtils.defaultIfNull("a","b");}.
1435+
* be used, such as {@code ObjectUtils.getIfNull("a","b");}.
13861436
*
13871437
* <p>This constructor is public to permit tools that require a JavaBean
13881438
* instance to operate.</p>

src/main/java/org/apache/commons/lang3/builder/Diff.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ public abstract class Diff<T> extends Pair<T, T> {
5656
*/
5757
protected Diff(final String fieldName) {
5858
this.fieldName = Objects.requireNonNull(fieldName);
59-
this.type = ObjectUtils.defaultIfNull(TypeUtils.getTypeArguments(getClass(), Diff.class).get(Diff.class.getTypeParameters()[0]), Object.class);
59+
this.type = ObjectUtils.getIfNull(TypeUtils.getTypeArguments(getClass(), Diff.class).get(Diff.class.getTypeParameters()[0]), Object.class);
6060
}
6161

6262
Diff(final String fieldName, final Type type) {

src/main/java/org/apache/commons/lang3/reflect/TypeUtils.java

+2-2
Original file line numberDiff line numberDiff line change
@@ -236,8 +236,8 @@ private static final class WildcardTypeImpl implements WildcardType {
236236
* @param lowerBounds of this type
237237
*/
238238
private WildcardTypeImpl(final Type[] upperBounds, final Type[] lowerBounds) {
239-
this.upperBounds = ObjectUtils.defaultIfNull(upperBounds, ArrayUtils.EMPTY_TYPE_ARRAY);
240-
this.lowerBounds = ObjectUtils.defaultIfNull(lowerBounds, ArrayUtils.EMPTY_TYPE_ARRAY);
239+
this.upperBounds = ObjectUtils.getIfNull(upperBounds, ArrayUtils.EMPTY_TYPE_ARRAY);
240+
this.lowerBounds = ObjectUtils.getIfNull(lowerBounds, ArrayUtils.EMPTY_TYPE_ARRAY);
241241
}
242242

243243
/**

src/main/java/org/apache/commons/lang3/text/FormattableUtils.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@ public static Formatter append(final CharSequence seq, final Formatter formatter
9797
"Specified ellipsis '%1$s' exceeds precision of %2$s", ellipsis, Integer.valueOf(precision));
9898
final StringBuilder buf = new StringBuilder(seq);
9999
if (precision >= 0 && precision < seq.length()) {
100-
final CharSequence actualEllipsis = ObjectUtils.defaultIfNull(ellipsis, StringUtils.EMPTY);
100+
final CharSequence actualEllipsis = ObjectUtils.getIfNull(ellipsis, StringUtils.EMPTY);
101101
buf.replace(precision - actualEllipsis.length(), seq.length(), actualEllipsis.toString());
102102
}
103103
final boolean leftJustify = (flags & FormattableFlags.LEFT_JUSTIFY) == FormattableFlags.LEFT_JUSTIFY;

src/main/java/org/apache/commons/lang3/time/DurationUtils.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -219,7 +219,7 @@ public static int toMillisInt(final Duration duration) {
219219
* @return The given duration or {@link Duration#ZERO}.
220220
*/
221221
public static Duration zeroIfNull(final Duration duration) {
222-
return ObjectUtils.defaultIfNull(duration, Duration.ZERO);
222+
return ObjectUtils.getIfNull(duration, Duration.ZERO);
223223
}
224224

225225
/**

src/test/java/org/apache/commons/lang3/ObjectUtilsTest.java

+38-1
Original file line numberDiff line numberDiff line change
@@ -423,6 +423,9 @@ public void testConstructor() {
423423
assertFalse(Modifier.isFinal(ObjectUtils.class.getModifiers()));
424424
}
425425

426+
/**
427+
* @deprecated
428+
*/
426429
@Test
427430
public void testDefaultIfNull() {
428431
final Object o = FOO;
@@ -444,6 +447,27 @@ public void testDefaultIfNull() {
444447
assertEquals(1, callsCounter.getValue());
445448
}
446449

450+
@Test
451+
public void testGetIfNull() {
452+
final Object o = FOO;
453+
final Object dflt = BAR;
454+
assertSame(dflt, ObjectUtils.getIfNull(null, dflt), "dflt was not returned when o was null");
455+
assertSame(o, ObjectUtils.getIfNull(o, dflt), "dflt was returned when o was not null");
456+
assertSame(dflt, ObjectUtils.getIfNull(null, () -> dflt), "dflt was not returned when o was null");
457+
assertSame(o, ObjectUtils.getIfNull(o, () -> dflt), "dflt was returned when o was not null");
458+
assertSame(o, ObjectUtils.getIfNull(FOO, () -> dflt), "dflt was returned when o was not null");
459+
assertSame(o, ObjectUtils.getIfNull("foo", () -> dflt), "dflt was returned when o was not null");
460+
final MutableInt callsCounter = new MutableInt(0);
461+
final Supplier<Object> countingDefaultSupplier = () -> {
462+
callsCounter.increment();
463+
return dflt;
464+
};
465+
ObjectUtils.getIfNull(o, countingDefaultSupplier);
466+
assertEquals(0, callsCounter.getValue());
467+
ObjectUtils.getIfNull(null, countingDefaultSupplier);
468+
assertEquals(1, callsCounter.getValue());
469+
}
470+
447471
@Test
448472
public void testEquals() {
449473
assertTrue(ObjectUtils.equals(null, null), "ObjectUtils.equals(null, null) returned false");
@@ -454,7 +478,7 @@ public void testEquals() {
454478
}
455479

456480
@Test
457-
public void testFirstNonNull() {
481+
public void testFirstNonNullArray() {
458482
assertEquals("", ObjectUtils.firstNonNull(null, ""));
459483
final String firstNonNullGenerics = ObjectUtils.firstNonNull(null, null, "123", "456");
460484
assertEquals("123", firstNonNullGenerics);
@@ -471,6 +495,19 @@ public void testFirstNonNull() {
471495
assertNull(ObjectUtils.firstNonNull((Object[]) null));
472496
}
473497

498+
@Test
499+
void testFirstNonNullCollection() {
500+
assertEquals("123", ObjectUtils.firstNonNull(Arrays.asList(null, null, "123", "456")).get());
501+
assertEquals("", ObjectUtils.firstNonNull(Collections.singletonList("")).get());
502+
assertEquals("123", ObjectUtils.firstNonNull(Arrays.asList("123", null, "456", null)).get());
503+
assertSame(Boolean.TRUE, ObjectUtils.firstNonNull(Collections.singletonList(Boolean.TRUE)).get());
504+
505+
// Ensure an empty collection returns empty optional
506+
assertEquals(false, ObjectUtils.firstNonNull(Collections.emptyList()).isPresent());
507+
// Ensure collection with only nulls returns empty optional
508+
assertEquals(false, ObjectUtils.firstNonNull(Arrays.asList(null, null)).isPresent());
509+
}
510+
474511
@Test
475512
public void testGetClass() {
476513
final String[] newArray = ArrayUtils.EMPTY_STRING_ARRAY;

src/test/java/org/apache/commons/lang3/function/Objects.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@
5252
*
5353
* This class is somewhat redundant with regards to {@link ObjectUtils}.
5454
* For example, {@link #requireNonNull(Object, Object)} is almost equivalent
55-
* with {@link ObjectUtils#defaultIfNull(Object, Object)}. However, it isn't
55+
* with {@link ObjectUtils#getIfNull(Object, Object)}. However, it isn't
5656
* quite the same, because the latter can, in fact, return null. The former
5757
* can't, and the Java compiler confirms this.(An alternative to redundancy
5858
* would have been to change the {@code ObjectUtils} class. However, that

0 commit comments

Comments
 (0)