Java Lombok | Automatically Generating Constructors - @NoArgsConstructor @RequiredArgsConstructor @AllArgsConstructor
Automatically Generating Constructors
There are three annotations that automatically generate constructors.
@NoArgsConstructor: Automatically generates a constructor with no arguments.@RequiredArgsConstructor: Automatically generates a constructor with only fields declared asfinalas arguments.@AllArgsConstructor: Automatically generates a constructor with all fields as arguments.
Using @NoArgsConstructor
You can declare the @NoArgsConstructor annotation to generate a constructor with no arguments.
package com.devkuma.tutorial.lombok;
import lombok.NoArgsConstructor;
@NoArgsConstructor
public class NoArgsConstructorTutorial {
public NoArgsConstructorTutorial(String string) {
}
public static void main(String[] args) {
new NoArgsConstructorTutorial();
}
}
Using @RequiredArgsConstructor
You can declare the @RequiredArgsConstructor annotation to automatically generate a constructor that takes only fields declared as final as arguments.
package com.devkuma.tutorial.lombok;
import lombok.RequiredArgsConstructor;
@RequiredArgsConstructor
public class RequiredArgsConstructorTutorial {
private String optional;
private final int required;
public static void main(String[] args) {
new RequiredArgsConstructorTutorial(1);
}
}
Using @AllArgsConstructor
You can declare the @AllArgsConstructor annotation to automatically generate a constructor that takes all fields as arguments.
package com.devkuma.tutorial.lombok;
import lombok.AllArgsConstructor;
@AllArgsConstructor
public class AllArgsConstructorTutorial {
private String string;
private int number;
public static void main(String[] args) {
new AllArgsConstructorTutorial("devkuma", 999);
}
}
Defining a static Factory Method
By specifying the staticName attribute on each annotation, you can automatically generate a static factory method.
package com.devkuma.tutorial.lombok;
import lombok.RequiredArgsConstructor;
@RequiredArgsConstructor(staticName="of")
public class StaticFactoryOfTututorial {
private final String required;
private int optional;
public static void main(String[] args) {
StaticFactoryOfTututorial tututorial = StaticFactoryOfTututorial.of("devkuma");
}
}
Notes on Usage
@AllArgsConstructor and @RequiredArgsConstructor are very convenient for generating constructors, but using them without thought can lead to serious bugs.
Problem Code
The example below declares @AllArgsConstructor so that the x and y arguments are automatically generated in order.
package com.devkuma.tutorial.lombok.warning;
import lombok.AllArgsConstructor;
import lombok.ToString;
@AllArgsConstructor
@ToString
public class ConstructorWarning {
private String x;
private String y;
public static void main(String[] args) {
ConstructorWarning warning = new ConstructorWarning("x", "y");
System.out.println(warning);
}
}
Execution result:
ConstructorWarning(x=x, y=y)
The Problem
At this point, if you reorganize the code and change the order of the x and y arguments as follows, the values of the two arguments are swapped.
private String y;
private String x;
Execution result:
ConstructorWarning(x=y, y=x)
No error occurs, and the bug can slip in without the developer noticing it.
Solution
You can solve this problem by using the @Builder annotation.
package com.devkuma.tutorial.lombok.warning;
import lombok.Builder;
@Builder
public class ConstructorSolve {
private String x;
private String y;
public static void main(String[] args) {
ConstructorSolve warning = ConstructorSolve.builder()
.x("x")
.y("y")
.build();
System.out.println(warning);
}
}
With this style, even if the order of the x and y fields changes, the values of the two arguments will not be swapped.