add in memory map based crud implementation

This commit is contained in:
InsanusMokrassar 2020-10-14 14:22:58 +06:00
parent 88f442a16d
commit 0ba93d0e60
4 changed files with 142 additions and 0 deletions

View File

@ -0,0 +1,35 @@
package dev.inmo.micro_utils.pagination.utils
import dev.inmo.micro_utils.pagination.*
fun <T> Iterable<T>.paginate(with: Pagination): PaginationResult<T> {
var i = 0
val result = mutableListOf<T>()
val lowerIndex = with.firstIndex
val greatestIndex = with.lastIndex
for (item in this) {
when {
i < lowerIndex || i > greatestIndex -> i++
else -> {
result.add(item)
i++
}
}
}
return result.createPaginationResult(with, i.toLong())
}
fun <T> List<T>.paginate(with: Pagination): PaginationResult<T> {
return subList(with.firstIndex, with.lastIndex + 1).createPaginationResult(
with,
size.toLong()
)
}
fun <T> Set<T>.paginate(with: Pagination): PaginationResult<T> {
return this.drop(with.firstIndex).take(with.size).createPaginationResult(
with,
size.toLong()
)
}

View File

@ -0,0 +1,17 @@
plugins {
id "org.jetbrains.kotlin.multiplatform"
id "org.jetbrains.kotlin.plugin.serialization"
}
apply from: "$mppProjectWithSerializationPresetPath"
kotlin {
sourceSets {
commonMain {
dependencies {
api internalProject("micro_utils.repos.common")
api internalProject("micro_utils.coroutines")
}
}
}
}

View File

@ -0,0 +1,89 @@
package dev.inmo.micro_utils.repos
import dev.inmo.micro_utils.coroutines.BroadcastFlow
import dev.inmo.micro_utils.pagination.*
import kotlinx.coroutines.flow.Flow
class MapCRUDRepo<ObjectType, IdType>(
private val map: Map<IdType, ObjectType> = emptyMap()
) : ReadStandardCRUDRepo<ObjectType, IdType> {
override suspend fun getByPagination(pagination: Pagination): PaginationResult<ObjectType> {
return map.keys.drop(pagination.firstIndex).take(pagination.size).mapNotNull {
map[it]
}.createPaginationResult(
pagination,
map.size.toLong()
)
}
override suspend fun getById(id: IdType): ObjectType? = map[id]
override suspend fun contains(id: IdType): Boolean = map.containsKey(id)
}
abstract class MutableMapCRUDRepo<ObjectType, IdType, InputValueType>(
private val map: MutableMap<IdType, ObjectType> = mutableMapOf()
) : WriteStandardCRUDRepo<ObjectType, IdType, InputValueType> {
private val _newObjectsFlow: BroadcastFlow<ObjectType> = BroadcastFlow()
override val newObjectsFlow: Flow<ObjectType>
get() = _newObjectsFlow
private val _updatedObjectsFlow: BroadcastFlow<ObjectType> = BroadcastFlow()
override val updatedObjectsFlow: Flow<ObjectType>
get() = _updatedObjectsFlow
private val _deletedObjectsIdsFlow: BroadcastFlow<IdType> = BroadcastFlow()
override val deletedObjectsIdsFlow: Flow<IdType>
get() = _deletedObjectsIdsFlow
protected abstract suspend fun updateObject(newValue: InputValueType, id: IdType, old: ObjectType): ObjectType
protected abstract suspend fun createObject(newValue: InputValueType): Pair<IdType, ObjectType>
override suspend fun create(values: List<InputValueType>): List<ObjectType> {
return values.map {
val (id, newObject) = createObject(it)
map[id] = newObject
newObject.also { _ ->
_newObjectsFlow.send(newObject)
}
}
}
override suspend fun update(id: IdType, value: InputValueType): ObjectType? {
val newValue = updateObject(value, id, map[id] ?: return null)
return newValue.also {
map[id] = it
_updatedObjectsFlow.send(it)
}
}
override suspend fun update(values: List<UpdatedValuePair<IdType, InputValueType>>): List<ObjectType> {
return values.mapNotNull { update(it.first, it.second) }
}
override suspend fun deleteById(ids: List<IdType>) {
ids.forEach {
map.remove(it) ?.also { _ -> _deletedObjectsIdsFlow.send(it) }
}
}
}
abstract class HashMapCRUDRepo<ObjectType, IdType, InputValueType>(
map: MutableMap<IdType, ObjectType>
) : StandardCRUDRepo<ObjectType, IdType, InputValueType>,
ReadStandardCRUDRepo<ObjectType, IdType> by MapCRUDRepo(map),
MutableMapCRUDRepo<ObjectType, IdType, InputValueType>(map)
fun <ObjectType, IdType, InputValueType> HashMapCRUDRepo(
map: MutableMap<IdType, ObjectType>,
updateCallback: suspend (newValue: InputValueType, id: IdType, old: ObjectType) -> ObjectType,
createCallback: suspend (newValue: InputValueType) -> Pair<IdType, ObjectType>
) = object : HashMapCRUDRepo<ObjectType, IdType, InputValueType>(map) {
override suspend fun updateObject(
newValue: InputValueType,
id: IdType,
old: ObjectType
): ObjectType = updateCallback(newValue, id, old)
override suspend fun createObject(newValue: InputValueType): Pair<IdType, ObjectType> = createCallback(newValue)
}

View File

@ -9,6 +9,7 @@ String[] includes = [
":mime_types",
":repos:common",
":repos:exposed",
":repos:inmemory",
":repos:ktor:client",
":repos:ktor:common",
":repos:ktor:server",