Error occurs while validation org.springframework.data.redis.serializer.SerializationException:
Could not read JSON: Cannot construct instance
redis를 통해서 로그인시 사용자 정보를 캐싱하고
이후 요청에 대해서 사용자 검증을 캐시데이터를 조회하는식으로 구조를 잡았었다.
의도와는 다르게 정상적으로 데이터가 있고, 생성자도 있었음에도 문제가 발생하고 있었다.
다음은 내 UserDto 코드이다.
@JsonIgnoreProperties(ignoreUnknown = true)
data class User (
val userName: String,
val _password: String,
val userRole: UserRole? = null,
@JsonIgnore
var registeredAt: LocalDateTime? = null,
@JsonIgnore
var updatedAt: LocalDateTime? = null,
@JsonIgnore
var deletedAt: LocalDateTime? = null,
var id: Long? = null,
) : UserDetails{
constructor(entity: UserEntity): this(
entity.userName,
entity.password,
entity.role,
entity.registeredAt,
entity.updatedAt,
entity.deletedAt,
entity.id,
)
companion object {
fun fixture(
userName: String ="userName",
password: String ="password",
userRole: UserRole? = null,
registeredAt: LocalDateTime? = null,
updatedAt: LocalDateTime? = null,
deletedAt: LocalDateTime? = null,
id: Long? = null,
) : User {
return User(
userName = userName,
_password = password,
userRole = userRole,
registeredAt = registeredAt,
updatedAt = updatedAt,
deletedAt = deletedAt,
id = id,
)
}
}
fun toEntity(): UserEntity {
return UserEntity(userName, _password, userRole, registeredAt, updatedAt, deletedAt, id)
}
// 스프링 시큐리티 관련 //
}
간단하게 필드가 정의되어 있고,
Entity
메소드를 통해 dto를 생성하는 생성자,
fixture
메소드를 두어 테스트코드의 편의성
toEntity
메소드를 통해 JPA활용시 Entity 객체로 변경해주는 코드였다.
코틀린은 보일러코드의 양을 줄여주고,
data class로 선언해두어서 당연히 기본생성자를 제공할 수 있을것이라고 생각한 것이 문제였다.
정확히 파악하려면 내부동작을 더 파악해보아야 겠지만,
객체를 생성하는 과정에서 기본생성자가 없었기 때문이였다.
@NoArgsConstructor
어노테이션이랑은 별개로 데이터를 역직렬화 하는 과정에서
명시적으로 선언된 Entity
를 통해 dto를 생성하는 메소드를 사용하는것 처럼 보였다.
따라서 스프링은 '내가 받은건 Json 타입이고 변환을 해야 하는데 왠 UserEntity? 나이거 변환못해!'
라는 듯한 에러를 던져주는 문제였다.
이에따라
기본 생성자를 명시적으로 추가해주었다,
constructor(): this("","") // Json 역직렬화시 사용
constructor(entity: UserEntity): this(
entity.userName,
entity.password,
entity.role,
entity.registeredAt,
entity.updatedAt,
entity.deletedAt,
entity.id,
)
constructor(): this("","")
코드를 통해서 해당문제를 해결할 수 있었다.