Это определенно не дубликат Только с использованием @JsonIgnore во время сериализации, но не десериализации . Проблема та же, но в контексте Immutables .
Когда модель (DTO / DAO) оформлена как неизменяемая, я не могу выборочно @JsonIgnore одно из свойств во время сериализации. Предположим, что у нас есть UserDto, который определен как неизменный, как следует
@Value.Immutable
@Value.Style(defaults = @Value.Immutable(copy = false), init = "set*")
@JsonSerialize(as = ImmutableUserDto.class)
@JsonDeserialize(builder = ImmutableUserDto.Builder.class)
public abstract class UserDto {
@JsonProperty("id")
@Value.Default
public int getId() {
return 0;
}
@JsonProperty("username")
public abstract String getUsername();
@JsonProperty("email")
public abstract String getEmail();
@JsonProperty("password")
public abstract String getPassword();
}
Я полагаю, что было бы справедливо ожидать, что во время сериализации мы бы хотели игнорировать password
из ответа службы.
Без использования Immutables, если мы работали с простым классом, есть много способов сделать это. Например - аннотируйте только получатель с @JsonIgnore
. Или, если возможно, определите другой метод доступа (то, что не имеет префикса get) и определите только метод обычного установщика ... и т. Д.
Если я попытаюсь использовать тот же метод доступа Immutables для пароля, как показано ниже:
@Value.Immutable
@Value.Style(defaults = @Value.Immutable(copy = false), init = "set*")
@JsonSersonIgnoreialize(as = ImmutableUserDto.class)
@JsonDeserialize(builder = ImmutableUserDto.Builder.class)
public abstract class UserDto {
....
@JsonProperty("password")
@JsonIgnore
public abstract String getPassword();
}
затем сгенерированный ImmutableUserDto добавляет @JsonIgnore как к получателю, так и к установщику, как показано ниже.
@Generated(from = "UserDto", generator = "Immutables")
@SuppressWarnings({"all"})
@ParametersAreNonnullByDefault
@javax.annotation.Generated("org.immutables.processor.ProxyProcessor")
@Immutable
@CheckReturnValue
public final class ImmutableUserDto extends UserDto {
...
...
private final String password;
...
...
/**
* @return The value of the {@code password} attribute
*/
@JsonProperty("password")
@JsonIgnore
@Override
public String getPassword() {
return password;
}
...
...
...
@Generated(from = "UserDto", generator = "Immutables")
@NotThreadSafe
public static final class Builder {
...
...
private String password;
@JsonProperty("password")
@JsonIgnore
public final Builder setPassword(String password) {
this.password = password;
return this;
}
}
}
Сериализация будет работать как положено. Атрибут password
будет исключен из JSON. Но при попытке десериализации я получаю следующую ошибку:
java.lang.IllegalStateException: Cannot build UserDto, some of the required attributes are not set [password]
Это очевидно, поскольку Immutables также добавил @JsonIgnore
в сеттер.
Документация не сильно поможет. В их Вещи, которые нужно знать о разделе, он просто упоминает следующее относительно @JsonIgnore
Если вы используете @JsonIgnore, вы должны явно указать атрибут
необязательный. В неизменяемых атрибутах можно объявить как
не обязательно через @Nullable, Optional или @ Value.Default, которые все
различаются по своему действию, и мы ничего не получаем автоматически.
Использование @Nullable
или Optional
или @Value.Default
бесполезно для таких полей, как password
.
Я просмотрел список проблем на их странице GitHub, и похожая проблема была похожа, но пользователь запрашивал немного другой вариант использования, и использование @Nullable могло бы решить проблему, которая не работает в моем случае.
Я также пытался использовать один из ответов здесь . По-прежнему приводит к той же ошибке.
Похоже, это не поддерживается библиотекой Immutables. Я создал новый выпуск сам. Как только я получу отзывы пользователей о SOF, я, вероятно, создам sscce .