Last active
September 1, 2021 16:34
-
-
Save jeroenknoef/3814cab50ec6aaa387048cc6707c0fbf to your computer and use it in GitHub Desktop.
Micronaut - KMongo - Jackson
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Example controller | |
@Controller | |
@Validated | |
class DemoBeanController( | |
private val service: Service // Injected by Micronaut | |
) { | |
@Get("/{id}") | |
// Micronaut 1.3 supports coroutines, this also works in earlier versions. | |
fun find(@ValidObjectId id: String): CompletableFuture<DemoBean?> = CoroutineScope(Dispatchers.Default).future { | |
service.findById(ObjectId(id).toId()) | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Place this class somewhere in your project. Micronaut will wire this together automatically. | |
import com.fasterxml.jackson.databind.Module | |
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule | |
import com.mongodb.MongoClientSettings | |
import com.mongodb.reactivestreams.client.MongoClient | |
import io.micronaut.context.annotation.Factory | |
import io.micronaut.context.annotation.Requires | |
import org.bson.codecs.configuration.CodecRegistry | |
import org.litote.kmongo.reactivestreams.KMongo | |
import org.litote.kmongo.coroutine.CoroutineClient | |
import org.litote.kmongo.coroutine.coroutine | |
import org.litote.kmongo.id.jackson.IdJacksonModule | |
import org.litote.kmongo.service.ClassMappingType | |
import org.litote.kmongo.util.CollectionNameFormatter | |
import javax.inject.Singleton | |
@Factory | |
@Requires(classes = [KMongo::class]) | |
class KMongoFactory { | |
init { | |
// KMongo: construct lower case collection names from bean classes. | |
CollectionNameFormatter.useLowerCaseCollectionNameBuilder() | |
} | |
/** | |
* Inject KMongo's [CodecRegistry] for mapping data classes. | |
*/ | |
@Singleton | |
fun codecRegistry(): CodecRegistry = ClassMappingType.codecRegistry(MongoClientSettings.getDefaultCodecRegistry()) | |
/** | |
* Inject KMongo's [CoroutineClient] instead of the default [MongoClient]. | |
*/ | |
@Singleton | |
fun coroutineClient(client: MongoClient): CoroutineClient = client.coroutine | |
/** | |
* Jackson: convert Mongo ObjectId's to string and vice versa. | |
*/ | |
@Singleton | |
fun idJacksonModule(): Module = IdJacksonModule() | |
/** | |
* Jackson: convert [java.time.LocalDate] to and from strings. | |
*/ | |
@Singleton | |
fun javaTimeJacksonModule(): Module = JavaTimeModule() | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// A service that accesses a collection of DemoBean objects. | |
data class DemoBean( | |
@BsonId | |
val id: Id<DemoBean>, | |
... | |
) | |
@Singleton | |
class DemoBeanService( | |
client: CoroutineClient, // Injected by Micronaut, defined in KMongoFactory. | |
@Property(name = "mongodb.database") database: String | |
) { | |
private val collection: CoroutineCollection<DemoBean> by lazy { | |
// We can't use `getCollection<T>` on the coroutine database, because reified types are not supported on classes. | |
// Therefore, get a handle to the collection via the MongoDatabase and the bean class. | |
val db = client.getDatabase(database).database | |
db.getCollection(KMongoUtil.defaultCollectionName(DemoBean::class), DemoBean::class.java).coroutine | |
} | |
suspend fun findById(id: Id<DemoBean>): DemoBean? = collection.find().first() // ... | |
suspend fun save(bean: DemoBean) = collection.save(bean) | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Custom validation for incoming Mongo ObjectIds | |
import javax.validation.Constraint | |
import javax.validation.Payload | |
import javax.validation.constraints.NotNull | |
import javax.validation.constraints.Pattern | |
import kotlin.reflect.KClass | |
@NotNull | |
@Pattern(regexp = "[a-f0-9]{24}", message = "objectid") | |
@Target(AnnotationTarget.FIELD, AnnotationTarget.VALUE_PARAMETER) | |
@Retention(AnnotationRetention.RUNTIME) | |
@Constraint(validatedBy = []) | |
annotation class ValidObjectId(val message: String = "objectid", val groups: Array<KClass<*>> = [], val payload: Array<KClass<out Payload>> = []) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment