简体   繁体   中英

Is it possible to make Lombok's builder public?

I am using Lombok library in my project and I am not able to use a class annotated with @Builder in outer packages.

Is there a way to make the builder public?

MyClass instance = new MyClass.MyClassBuilder().build();

The error is:

'MyClassBuilder()' is not public in 'com.foo.MyClass.MyClassBuilder'. Cannot be accessed from outside package

@Builder already produces public methods. You should use the static builder() method instead of trying to instantiate the builder yourself:

Buildable foo = Buildable.builder()
    .property("hello, world")
    .build();

Just to show you everything that gets generated, I wrote the following class:

@Builder
public class Buildable
{
    private final String property;
}

I then ran it through delombok to see everything that was generated. As you can see, everything is public:

public class Buildable
{
    private final String property;

    @java.beans.ConstructorProperties({"property"})
    Buildable(final String property) {
        this.property = property;
    }

    public static BuildableBuilder builder() {
        return new BuildableBuilder();
    }

    public static class BuildableBuilder
    {
        private String property;

        BuildableBuilder() { }

        public BuildableBuilder property(final String property) {
            this.property = property;
            return this;
        }

        public Buildable build() {
            return new Buildable(property);
        }

        public String toString() {
            return "Buildable.BuildableBuilder(property=" + this.property + ")";
        }
    }
}

The problem is you are using @Builder in the wrong way.

When Builder Pattern is used, you only need to use the static method to invoke it and then build, for example:

MyClass instance = MyClass.builder().build(); .

Please do not new the MyClassBuilder again, it breaks the encapsulation the pattern has since you are directly using the inner MyClassBuilder class. This constructor is been hided from outside, that's why you get the not accessible error. Instead it provides you the static method builder() .

The problem with this builder annotation is that, if you delombok you'll see, the generated constructor for the builder has no access indicator (public, private, protected) therefore is only visible within the same package. This would work if the extended classes were in the same package.

I'm having the same problem and I think that lombok does not support this, for now. I was able to find the feature request in here https://github.com/rzwitserloot/lombok/issues/1489

My suggestion is to hard implement builder pattern in this class.

I have found this neat workaround:

import lombok.Builder;
import lombok.Getter;
import lombok.Setter;

@Getter
@Setter
@Builder
public class Customer {
    private String id;
    private String name;

    public static MessageBuilder builder() {return new CustomerBuilder();}
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM