java - poo - Usar un modificador personalizado en el constructor de Lombok.
programacion ats herencia (3)
Tengo un configurador personalizado en mi POJO con base en Lombok:
@Data
@Builder
public class User {
private static final PasswordEncoder ENCODER = new BCryptPasswordEncoder();
private String password = null;
public void setPassword(String password) {
Assert.notNull(password);
this.password = ENCODER.encode(password);
}
pero cuando uso el generador generado por Lombok:
User user = User.builder()
.password(password)
.build();
mi configurador personalizado no se invoca, por lo que la contraseña no está codificada. Esto me pone triste.
Mi configurador personalizado es, por supuesto, invocado cuando lo uso directamente:
public void changePassword(String password, User user) {
user.setPassword(password);
}
¿Qué puedo hacer para que el constructor de Lombok use mi configurador personalizado?
Está utilizando setPassword en lugar del método set del constructor.
Esto es lo que funcionó para mí:
import lombok.Builder;
import lombok.Data;
@Builder
@Data
public class User {
private String username;
private String password;
public static class UserBuilder {
private String password;
public UserBuilder password(String password ) {
this.password ="ENCRIYP " + password;
return this;
}
}
public static void main(String[] args) {
System.out.println(User.builder().username("This is my username").password("Password").build().toString());
}
}
El resultado fue: User(username=This is my username, password=ENCRIYP Password)
He aceptado la respuesta de chrylis , pero para completar, aquí hay algunas formas de minimizar la personalización y la duplicación.
Preparador personalizado y constructor con ayudante estático.
Se puede usar un ayudante estático para compartir la mayor parte de la funcionalidad de contraseña establecida en el User.UserBuilder::password
personalizado User.UserBuilder::password
y el método personalizado User::setPassword
:
@Data
@Builder
public class User {
private static final PasswordEncoder ENCODER = new BCryptPasswordEncoder();
private String password = null;
public void setPassword(String password) {
this.password = _encodePassword(password);
}
public static class UserBuilder {
public UserBuilder password(String password) {
this.password = _encodePassword(password)
return this;
}
}
private static String _encodePassword(String password) {
Assert.notNull(password);
return ENCODER.encode(password);
}
}
Setter personalizado y constructor
Un constructor personalizado puede usar User::setPassword
que es invocado por User.UserBuilder::build()
generado por Lombok:
@Data
@Builder
public class User {
private static final PasswordEncoder ENCODER = new BCryptPasswordEncoder();
private String password = null;
User(String password) {
setPassword(password);
}
public void setPassword(String password) {
Assert.notNull(password);
this.password = ENCODER.encode(password);
}
}
Preparador personalizado y constructor con ayudante estático.
O, un poco más elegante, con un constructor personalizado y un método auxiliar estático:
@Data
@Builder
public class User {
private static final PasswordEncoder ENCODER = new BCryptPasswordEncoder();
private String password = null;
User(String password) {
_encodePassword(password, this);
}
public void setPassword(String password) {
_encodePassword(password, this);
}
private static _encodePassword(String password, User user) {
Assert.notNull(password);
user.password = ENCODER.encode(password);
}
}
Por la documentación para @Builder
: Simplemente defina suficiente esqueleto usted mismo. En particular, Lombok generará una clase UserBuilder
, campos que reflejarán los campos de User
y métodos de construcción, y usted puede proporcionar todo esto o todo usted mismo.
@Builder
public class User {
private static final PasswordEncoder ENCODER = new BCryptPasswordEncoder();
private String username;
private String password;
public static class UserBuilder {
public UserBuilder password(String password) {
this.password = ENCODER.encode(password);
return this;
}
}
}