Reputation: 33789
How can I create a Lombok builder for a third party class (i.e. I cannot modify its source code)?
I have an existing class that I cannot change:
public class ThirdPartyPojo {
// one of many properties
private String name;
public ThirdPartyPojo() {
// default no-args constructor
}
String getName() {
return this.name;
}
void setName(String name) {
this.name = name;
}
// many more getters and setters
}
Now I would like to create a @Builder
so that I get a fluent builder API to simplify instantiation of ThirdPartyPojo
with default values.
This is what I tried:
@Builder
public class ThirdPartyPojoBuilder extends ThirdPartyPojo {
@Default
private String name = "default name";
// many more default values for other properties
}
The code compiles and I am able to reference the builder, e.g.
ThirdPartyPojo pojoWithDefaultName = ThirdPartyPojoBuilder.builder().build();
ThirdPartyPojo pojoWithCustomName = ThirdPartyPojoBuilder.builder().name("custom name").build();
System.out.println(pojoWithDefaultName.getName());
System.out.println(pojoWithCustomName.getName());
However, this does not work as getName()
returns null
for both pojoWithDefaultName
and pojoWithCustomName
.
Upvotes: 6
Views: 1942
Reputation: 33789
Based on pirho's answer, I found a feasible solution that also honors default values.
@Builder
annotation on class level@Default
and assign values to any fields that should have a default valuethis.set*(...)
for each constructor parametere.g.
@Builder
public class ThirdPartyPojoBuilder extends ThirdPartyPojo {
@Default
private String name = "default name"
public ThirdPartyPojoBuilder(String name) {
this.setName(name);
}
}
which also supports default values:
ThirdPartyPojo pojoWithDefaultName = ThirdPartyPojoBuilder.builder().build();
ThirdPartyPojo pojoWithCustomName = ThirdPartyPojoBuilder.builder().name("custom name").build();
System.out.println(pojoWithDefaultName.getName()); // prints "default name"
System.out.println(pojoWithCustomName.getName()); // prints "custom name"
Upvotes: 3
Reputation: 12245
I am afraid there is no easy way out to have Lombok automagically generate builder the way you might want. What Lombok @Builder does in general is:
Finally, applying @Builder to a class is as if you added @AllArgsConstructor(access = AccessLevel.PACKAGE) to the class and applied the @Builder annotation to this all-args-constructor.
So that is - I think - all that you can do:
public class ThirdPartyPojoBuilder extends ThirdPartyPojo {
@Builder
public ThirdPartyPojoBuilder(String name) {
this.setName(name);
}
}
Then it is possible - for example:
var thirdPartyPojo = ThirdPartyPojoBuilder.builder().name("A Name").build();
Upvotes: 2