druid1123
druid1123

Reputation: 108

Using Java Optional.ofNullable effectively

I can extract a particular section using Java8 like below

request.getBody()
       .getSections()
       .filter(section -> "name".equals(section.getName))
       .findFirst();

But how do I do the same using optional in a single line. I might have body or sections null.

I tried the below but not working

Optional.ofNullable(request)
        .map(Request::getBody)
        .map(Body::getSections)
        .filter(section -> "name".equals(section.getName)) //compliation error. section is coming as a list here
        .findFirst();

I am not able to get this working in a single line. I tried doing flatMap but not working as well. Please advise if we can achieve this in a singe line.

Below is the complete schema for reference

class Request {
    Body body;

    public Body getBody() {
        return body;
    }

    public void setBody(Body body) {
        this.body = body;
    }

}

class Body {
    List<Section> sections;

    public List<Section> getSections() {
        return sections;
    }

    public void setSections(List<Section> sections) {
        this.sections = sections;
    }

}

class Section {
    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

}

Upvotes: 4

Views: 5301

Answers (2)

Beri
Beri

Reputation: 11620

This should work for you:

Optional.ofNullable(request)
    .map(Request::getBody)
    .map(Body::getSections)
    .orElse(Collections.emptyList())
    .stream()
    .filter(section -> "name".equals(section.getName))
    .findFirst();

Upvotes: 3

Kayaman
Kayaman

Reputation: 73568

You need to convert from Optional which represents a single value, to a Stream to finish with the filter and findFirst() operations. At least one way is to map to an empty Stream (or empty List as in the neighbouring answer) in case of any nulls:

Optional.ofNullable(request)
    .map(Request::getBody)
    .map(Body::getSections)
    .map(List::stream)
    .orElse(Stream.empty())
    .filter(section -> "name".equals(section.getName))
    .findFirst();

Upvotes: 6

Related Questions