This is how you use @Builder.
//Employee.Java
import lombok.Builder;
import lombok.ToString;
@Builder
@ToString
public class Employee {
private final String empName;
private final int salary;
}
// Main.java
public class Main {
public static void main(String[] args) {
Employee emp = Employee.builder().empName("Deendaya").salary(100).build();
System.out.println(emp);
}
}
Answer from Deendayal Garg on Stack OverflowVideos
This is how you use @Builder.
//Employee.Java
import lombok.Builder;
import lombok.ToString;
@Builder
@ToString
public class Employee {
private final String empName;
private final int salary;
}
// Main.java
public class Main {
public static void main(String[] args) {
Employee emp = Employee.builder().empName("Deendaya").salary(100).build();
System.out.println(emp);
}
}
Using @Builder on method to create a Dog and Cat instance.
In this example @Value creates a final immutable value object with accessor methods (getters), an all args constructor, equals(), hashCode() and toString().
import static org.junit.Assert.*;
import lombok.Builder;
import lombok.Value;
import org.junit.Test;
@SuppressWarnings("javadoc")
public class ImmutableAnimals {
@Builder(builderMethodName = "dogBuilder")
public static Dog newDog(String color, String barkSound) {
return new Dog(color, barkSound);
}
@Builder(builderMethodName = "catBuilder")
public static Cat newCat(String color, String meowSound) {
return new Cat(color, meowSound);
}
public static interface Animal {
String getColor();
}
@Value
public static class Cat implements Animal {
String color;
String meowSound;
}
@Value
public static class Dog implements Animal {
String color;
String barkSound;
}
@Test
public void testDog() {
final String expectedBarkSound = "woof";
final String expectedColor = "brown";
final Dog dog = ImmutableAnimals.dogBuilder()
.barkSound(expectedBarkSound)
.color(expectedColor)
.build();
assertEquals(expectedBarkSound, dog.getBarkSound());
assertEquals(expectedColor, dog.getColor());
}
@Test
public void testCat() {
final String expectedMeowSound = "purr";
final String expectedColor = "white";
final Cat cat = ImmutableAnimals.catBuilder()
.meowSound(expectedMeowSound)
.color(expectedColor)
.build();
assertEquals(expectedMeowSound, cat.getMeowSound());
assertEquals(expectedColor, cat.getColor());
}
}
Here's another example with the same domain classes but using mutable values. However, as always favor immutability whenever possible.
import static org.junit.Assert.*;
import lombok.Builder;
import lombok.Data;
import org.junit.Test;
@SuppressWarnings("javadoc")
public class MutableAnimals {
@Builder(builderMethodName = "dogBuilder")
public static Dog newDog(String color, String barkSound) {
final Dog dog = new Dog();
dog.setBarkSound(barkSound);
dog.setColor(color);
return dog;
}
@Builder(builderMethodName = "catBuilder")
public static Cat newCat(String color, String meowSound) {
final Cat cat = new Cat();
cat.setMeowSound(meowSound);
cat.setColor(color);
return cat;
}
public static interface Animal {
String getColor();
}
@Data
public static class Cat implements Animal {
String color;
String meowSound;
}
@Data
public static class Dog implements Animal {
String color;
String barkSound;
}
@Test
public void testDog() {
final String expectedBarkSound = "woof";
final String expectedColor = "brown";
final Dog dog = MutableAnimals.dogBuilder()
.barkSound(expectedBarkSound)
.color(expectedColor)
.build();
assertEquals(expectedBarkSound, dog.getBarkSound());
assertEquals(expectedColor, dog.getColor());
}
@Test
public void testCat() {
final String expectedMeowSound = "purr";
final String expectedColor = "white";
final Cat cat = MutableAnimals.catBuilder()
.meowSound(expectedMeowSound)
.color(expectedColor)
.build();
assertEquals(expectedMeowSound, cat.getMeowSound());
assertEquals(expectedColor, cat.getColor());
}
}
As per @Builder docs this annotation can work together with @NonNull. If the field marked @NonNull is null you will get an NullPointerException preventing creation of invalid object:
@Builder
static class Person {
@NonNull
private final String name;
@NonNull
private final Integer age;
}
public static void main(String[] args) {
Person.builder()
.name("Fred")
.build(); // java.lang.NullPointerException: age is marked @NonNull but is null
}
To go further you can define the builder method yourself. If the method is present Lombok won't generate it and you can now force the arguments compile time.
@Builder
static class Person {
@NonNull
private final String name;
@NonNull
private final Integer age;
public static PersonBuilder builder(String name, Integer age) {
return new PersonBuilder().name(name).age(age);
}
}
public static void main(String[] args) {
Person.builder("Fred", 11)
.build();
}
However one could still create a builder by writing new Person.PersonBuilder() because the builder class is still accessible.
Also, in extension can be used:
@Builder.Default <modifier><instanceVariable>=<default-value>,
like: @Builder.Default private String myVariable = "".
Please read this: @Builder default properties
Avoids compiler errors asking for required properties that won't be set in some scenarios such as persistence, indexing, etc. (update/deleteBy/findBy from id or reduced properties set, without having a full object graph).
It's an elegant solution for not overriding .build() or setters as suggested.