This commit is contained in:
tursom 2020-02-19 05:05:17 +08:00
parent 79ed71efae
commit 61e221857c
2 changed files with 64 additions and 20 deletions

View File

@ -1,5 +1,6 @@
package cn.tursom.mongodb
import cn.tursom.core.isStatic
import cn.tursom.core.isTransient
import cn.tursom.mongodb.annotation.Ignore
import com.mongodb.client.MongoCollection
@ -14,25 +15,22 @@ import kotlin.reflect.KProperty1
@Suppress("MemberVisibilityCanBePrivate", "CanBeParameter", "unused")
class MongoOperator<T : Any>(
val collection: MongoCollection<T>,
val collection: MongoCollection<Document>,
val clazz: Class<T>
) {
constructor(clazz: Class<T>, database: MongoDatabase) : this(database.getCollection(MongoUtil.collectionName(clazz), clazz), clazz)
constructor(clazz: Class<T>, database: MongoDatabase) : this(database.getCollection(MongoUtil.collectionName(clazz)), clazz)
private val fields = clazz.declaredFields.filter {
it.isAccessible = true
!it.isTransient() && it.getAnnotation(Ignore::class.java) == null
!it.isStatic() && !it.isTransient() && it.getAnnotation(Ignore::class.java) == null
}
fun save(entity: T, options: InsertOneOptions = InsertOneOptions()) {
collection.insertOne(entity, options)
collection.insertOne(convertToBson(entity), options)
}
fun save(entities: Collection<T>, options: InsertManyOptions = InsertManyOptions()) {
collection.insertMany(when (entities) {
is List<T> -> entities
else -> entities.toList()
}, options)
collection.insertMany(entities.map { convertToBson(it) }, options)
}
fun update(update: Bson, where: Bson, options: UpdateOptions = UpdateOptions()): UpdateResult {
@ -64,11 +62,11 @@ class MongoOperator<T : Any>(
return add(field, 1, where)
}
private fun convertToBson(entity: Any): Bson {
private fun convertToBson(entity: Any): Document {
System.err.println(entity)
val bson = Document()
fields.forEach {
val value = it.get(entity) ?: return@forEach
bson[MongoUtil.fieldName(it)] = value
MongoUtil.injectValue(bson, it.get(entity) ?: return@forEach, it)
}
return bson
}

View File

@ -1,8 +1,10 @@
package cn.tursom.mongodb
import cn.tursom.core.isStatic
import cn.tursom.core.isTransient
import cn.tursom.mongodb.annotation.Collection
import cn.tursom.mongodb.annotation.Ignore
import org.bson.BsonValue
import org.bson.Document
import org.bson.conversions.Bson
import java.lang.reflect.Field
@ -25,15 +27,59 @@ object MongoUtil {
?: property.name
}
fun convertToBson(entity: Any): Bson {
val bson = Document()
entity.javaClass.declaredFields.filter {
it.isAccessible = true
!it.isTransient() && it.getAnnotation(Ignore::class.java) == null
}.forEach {
val value = it.get(entity) ?: return@forEach
bson[fieldName(it)] = value
fun convertToBson(entity: Any): Document {
return when (entity) {
is Map<*, *> -> entity.convert()
else -> {
val bson = Document()
entity.javaClass.declaredFields.filter {
it.isAccessible = true
!it.isStatic() && !it.isTransient() && it.getAnnotation(Ignore::class.java) == null
}.forEach {
injectValue(bson, it.get(entity) ?: return@forEach, it)
}
bson
}
}
return bson
}
fun injectValue(bson: Document, value: Any, field: Field) {
when (value) {
is Pair<*, *> -> bson[value.first?.toString() ?: return] = convertToBson(value.second ?: return)
is Map.Entry<*, *> -> bson[value.key?.toString() ?: return] =
convertToBson(value.value ?: return)
else -> bson[fieldName(field)] = value.convert() ?: return
}
}
private fun Iterator<*>.convert(): List<*> {
val list = ArrayList<Any?>()
forEach {
list.add(it.convert() ?: return@forEach)
}
return list
}
private fun Map<*, *>.convert(): Document {
val doc = Document()
forEach { any, u ->
any ?: return@forEach
doc[any.toString()] = u.convert() ?: return@forEach
}
return doc
}
private fun Any?.convert() = when (this) {
null -> null
is Enum<*> -> name
is Boolean -> this
is Number -> this
is String -> this
is Bson -> this
is BsonValue -> this
is Map<*, *> -> this.convert()
is Iterator<*> -> this.convert()
is Iterable<*> -> this.iterator().convert()
else -> convertToBson(this)
}
}