更新
基于反馈和John的回答,我已经更新了答案,不再使用@Tolerate
或@Data
,而是通过@Getter
和@Setter
创建访问器和变量,通过@NoArgsConstructor
创建默认构造函数,最终通过@AllArgsConstructor
创建建造者所需的所有参数构造函数。
由于您想要使用建造者模式,我想您希望限制构造函数和变量方法的可见性。
为实现此目的,我们通过@NoArgsConstructor
和@AllArgsConstructor
注释上的access
属性以及@Setter
注释上的value
属性设置可见性为package private
。
重要提示
请记得正确覆盖toString
、equals
和hashCode
方法。
有关详细信息,请参阅Vlad Mihalcea的以下文章:
package com.stackoverflow.SO34299054;
import static org.junit.Assert.*;
import java.util.Random;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import org.junit.Test;
import lombok.AccessLevel;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
@SuppressWarnings("javadoc")
public class Answer {
@Entity
@Builder(toBuilder = true)
@AllArgsConstructor(access = AccessLevel.PACKAGE)
@NoArgsConstructor(access = AccessLevel.PACKAGE)
@Setter(value = AccessLevel.PACKAGE)
@Getter
public static class Person {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
}
@Test
public void testPersonBuilder() {
final Long expectedId = new Random().nextLong();
final Person fromBuilder = Person.builder()
.id(expectedId)
.build();
assertEquals(expectedId, fromBuilder.getId());
}
@Test
public void testPersonConstructor() {
final Long expectedId = new Random().nextLong();
final Person fromNoArgConstructor = new Person();
fromNoArgConstructor.setId(expectedId);
assertEquals(expectedId, fromNoArgConstructor.getId());
}
}
使用 @Tolerate
和 @Data
的旧版本:
使用 @Tolerate
可以添加一个无参构造函数。
由于您想要使用生成器模式,我想您希望控制 setter 方法的可见性。
@Data
注释使生成的 setter 方法为 public
,将 @Setter(value = AccessLevel.PROTECTED)
应用于字段会使它们为 protected
。
记得正确地重写 toString
、equals
和 hashCode
。请参考 Vlad Mihalcea 的以下文章获取详细信息:
package lombok.javac.handlers.stackoverflow;
import static org.junit.Assert.*;
import java.util.Random;
import javax.persistence.GenerationType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import lombok.AccessLevel;
import lombok.Builder;
import lombok.Data;
import lombok.Setter;
import lombok.experimental.Tolerate;
import org.junit.Test;
public class So34241718 {
@Builder
@Data
public static class Person {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Setter(value = AccessLevel.PROTECTED)
Long id;
@Tolerate
Person() {}
}
@Test
public void testPersonBuilder() {
Long expectedId = new Random().nextLong();
final Person fromBuilder = Person.builder()
.id(expectedId)
.build();
assertEquals(expectedId, fromBuilder.getId());
}
@Test
public void testPersonConstructor() {
Long expectedId = new Random().nextLong();
final Person fromNoArgConstructor = new Person();
fromNoArgConstructor .setId(expectedId);
assertEquals(expectedId, fromNoArgConstructor.getId());
}
}
@NoArgsConstructor
。https://projectlombok.org/api/lombok/NoArgsConstructor.html - Robert Niestroj@Builder
不会覆盖您的无参构造函数。 - Ken Chan