I am trying to serialize a MongoDB ObjectId using a Kotlin, Spring Boot, KMongo and Kotlinx. The problem is, that the ObjectId is getting serialized as timestamp: Expected Result:
{"name":"Game 1","url":"game1.url","id":"62332fc4112cd3545bc129ef"}
Actual Result:
{
"name" : "Game 1",
"url" : "game1.url",
"id" : {
"id" : {
"timestamp" : 1647521732,
"date" : "2022-03-17T12:55:32.000+00:00"
}
}
}
I tried many different approaches (e.g. this one recommended by KMongo) but they didn't work. Any suggestions where the error might be?
GamesController
@RestController
class GamesController(private val gamesService: GamesService) {
@PostMapping("/games")
fun addGame(@RequestBody addGameRequest: AddGameRequest): Game {
return = gamesService.addGame(addGameRequest)
}
}
AddGameRequest
data class AddGameRequest(@JsonProperty("name") val name: String, @JsonProperty("url") val url: String)
GamesService
@Service
class GamesService(
mongoDBClient: MongoDBClient,
@Value("\${gamesservice.collectionname}") final val collectionName: String
) {
var gamesCollection: MongoCollection<Game> = mongoDBClient.gamesBlogDB.getCollection<Game>(collectionName)
fun addGame(addGameRequest: AddGameRequest): Game {
val newGame = Game(addGameRequest.name, addGameRequest.url)
val result = newGame.apply { gamesCollection.insertOne(newGame) }
return result
}
}
Game
@Serializable
data class Game(
var name: String,
var url: String,
@SerialName("_id") @Serializable(with = ObjectIdAsStringSerializer::class) var id: Id<Game> = newId()
) : RepresentationModel<Game>()
ObjectIdAsStringSerializer
object ObjectIdAsStringSerializer : KSerializer<Id<Game>> {
override val descriptor: SerialDescriptor
get() = PrimitiveSerialDescriptor("Id<Game>", PrimitiveKind.STRING)
@Suppress("UNCHECKED_CAST")
override fun deserialize(decoder: Decoder): Id<Game> {
return IdGenerator.defaultGenerator.create(decoder.decodeString()) as Id<Game>
}
override fun serialize(encoder: Encoder, value: Id<Game>) {
encoder.encodeString(value.toString())
}
}