mirror of
https://github.com/InsanusMokrassar/PlaguPoster.git
synced 2025-01-08 14:09:54 +00:00
0.5.1
This commit is contained in:
parent
ba3d054f0f
commit
58b1f26502
@ -1,5 +1,9 @@
|
|||||||
# PlaguPoster
|
# PlaguPoster
|
||||||
|
|
||||||
|
## 0.5.1
|
||||||
|
|
||||||
|
* Add opportunity to set unique
|
||||||
|
|
||||||
## 0.5.0
|
## 0.5.0
|
||||||
|
|
||||||
* Dependencies update
|
* Dependencies update
|
||||||
|
@ -10,4 +10,4 @@ android.enableJetifier=true
|
|||||||
# Project data
|
# Project data
|
||||||
|
|
||||||
group=dev.inmo
|
group=dev.inmo
|
||||||
version=0.5.0
|
version=0.5.1
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
package dev.inmo.plaguposter.ratings.selector
|
package dev.inmo.plaguposter.ratings.selector
|
||||||
|
|
||||||
|
import dev.inmo.micro_utils.repos.KeyValueRepo
|
||||||
import korlibs.time.DateTime
|
import korlibs.time.DateTime
|
||||||
import dev.inmo.plaguposter.posts.models.PostId
|
import dev.inmo.plaguposter.posts.models.PostId
|
||||||
import dev.inmo.plaguposter.posts.repo.PostsRepo
|
import dev.inmo.plaguposter.posts.repo.PostsRepo
|
||||||
@ -9,13 +10,14 @@ import dev.inmo.plaguposter.ratings.selector.models.SelectorConfig
|
|||||||
class DefaultSelector (
|
class DefaultSelector (
|
||||||
private val config: SelectorConfig,
|
private val config: SelectorConfig,
|
||||||
private val ratingsRepo: RatingsRepo,
|
private val ratingsRepo: RatingsRepo,
|
||||||
private val postsRepo: PostsRepo
|
private val postsRepo: PostsRepo,
|
||||||
|
private val latestChosenRepo: KeyValueRepo<PostId, DateTime>
|
||||||
) : Selector {
|
) : Selector {
|
||||||
override suspend fun take(n: Int, now: DateTime, exclude: List<PostId>): List<PostId> {
|
override suspend fun take(n: Int, now: DateTime, exclude: List<PostId>): List<PostId> {
|
||||||
val result = mutableListOf<PostId>()
|
val result = mutableListOf<PostId>()
|
||||||
|
|
||||||
do {
|
do {
|
||||||
val selected = config.active(now.time) ?.rating ?.select(ratingsRepo, postsRepo, result + exclude, now) ?: break
|
val selected = config.active(now.time) ?.rating ?.select(ratingsRepo, postsRepo, result + exclude, now, latestChosenRepo) ?: break
|
||||||
result.add(selected)
|
result.add(selected)
|
||||||
} while (result.size < n)
|
} while (result.size < n)
|
||||||
|
|
||||||
|
@ -2,11 +2,9 @@ package dev.inmo.plaguposter.ratings.selector.models
|
|||||||
|
|
||||||
import korlibs.time.DateTime
|
import korlibs.time.DateTime
|
||||||
import korlibs.time.seconds
|
import korlibs.time.seconds
|
||||||
import dev.inmo.micro_utils.pagination.FirstPagePagination
|
|
||||||
import dev.inmo.micro_utils.pagination.Pagination
|
|
||||||
import dev.inmo.micro_utils.pagination.utils.getAllByWithNextPaging
|
import dev.inmo.micro_utils.pagination.utils.getAllByWithNextPaging
|
||||||
import dev.inmo.micro_utils.repos.pagination.getAll
|
import dev.inmo.micro_utils.repos.KeyValueRepo
|
||||||
import dev.inmo.plaguposter.common.DateTimeSerializer
|
import dev.inmo.micro_utils.repos.unset
|
||||||
import dev.inmo.plaguposter.posts.models.PostId
|
import dev.inmo.plaguposter.posts.models.PostId
|
||||||
import dev.inmo.plaguposter.posts.repo.PostsRepo
|
import dev.inmo.plaguposter.posts.repo.PostsRepo
|
||||||
import dev.inmo.plaguposter.ratings.models.Rating
|
import dev.inmo.plaguposter.ratings.models.Rating
|
||||||
@ -25,17 +23,23 @@ data class RatingConfig(
|
|||||||
val max: Rating? = null,
|
val max: Rating? = null,
|
||||||
val prefer: Prefer = Prefer.Random,
|
val prefer: Prefer = Prefer.Random,
|
||||||
val otherwise: RatingConfig? = null,
|
val otherwise: RatingConfig? = null,
|
||||||
val postAge: Seconds? = null
|
val postAge: Seconds? = null,
|
||||||
|
val uniqueCount: Int? = null
|
||||||
) {
|
) {
|
||||||
suspend fun select(
|
suspend fun select(
|
||||||
ratingsRepo: RatingsRepo,
|
ratingsRepo: RatingsRepo,
|
||||||
postsRepo: PostsRepo,
|
postsRepo: PostsRepo,
|
||||||
exclude: List<PostId>,
|
exclude: List<PostId>,
|
||||||
now: DateTime
|
now: DateTime,
|
||||||
|
latestChosenRepo: KeyValueRepo<PostId, DateTime>
|
||||||
): PostId? {
|
): PostId? {
|
||||||
var reversed: Boolean = false
|
var reversed: Boolean = false
|
||||||
var count: Int? = null
|
var count: Int? = null
|
||||||
val allowedCreationTime = now - (postAge ?: 0).seconds
|
val allowedCreationTime = now - (postAge ?: 0).seconds
|
||||||
|
val excludedByRepo = uniqueCount ?.let {
|
||||||
|
latestChosenRepo.getAll().toList().sortedBy { it.second }.takeLast(uniqueCount).map { it.first }
|
||||||
|
} ?: emptyList()
|
||||||
|
val resultExcluded = exclude + excludedByRepo
|
||||||
|
|
||||||
when (prefer) {
|
when (prefer) {
|
||||||
Prefer.Max -> {
|
Prefer.Max -> {
|
||||||
@ -59,40 +63,53 @@ data class RatingConfig(
|
|||||||
ratingsRepo.getAllByWithNextPaging { keys(it) }
|
ratingsRepo.getAllByWithNextPaging { keys(it) }
|
||||||
}
|
}
|
||||||
else -> {
|
else -> {
|
||||||
ratingsRepo.getPostsWithRatingLessEq(max, exclude = exclude).keys
|
ratingsRepo.getPostsWithRatingLessEq(max, exclude = resultExcluded).keys
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else -> {
|
else -> {
|
||||||
when (max) {
|
when (max) {
|
||||||
null -> {
|
null -> {
|
||||||
ratingsRepo.getPostsWithRatingGreaterEq(min, exclude = exclude).keys
|
ratingsRepo.getPostsWithRatingGreaterEq(min, exclude = resultExcluded).keys
|
||||||
}
|
}
|
||||||
else -> {
|
else -> {
|
||||||
ratingsRepo.getPosts(min .. max, reversed, count, exclude = exclude).keys
|
ratingsRepo.getPosts(min .. max, reversed, count, exclude = resultExcluded).keys
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.filter {
|
}.filter {
|
||||||
it !in exclude && (postsRepo.getPostCreationTime(it) ?.let { it < allowedCreationTime } ?: true)
|
it !in resultExcluded && (postsRepo.getPostCreationTime(it) ?.let { it < allowedCreationTime } ?: true)
|
||||||
}
|
}
|
||||||
|
|
||||||
return when (prefer) {
|
val resultPosts: PostId = when (prefer) {
|
||||||
Prefer.Max,
|
Prefer.Max,
|
||||||
Prefer.Min -> posts.firstOrNull()
|
Prefer.Min -> posts.firstOrNull()
|
||||||
Prefer.Random -> posts.randomOrNull()
|
Prefer.Random -> posts.randomOrNull()
|
||||||
} ?: otherwise ?.select(ratingsRepo, postsRepo, exclude, now)
|
} ?: otherwise ?.select(ratingsRepo, postsRepo, resultExcluded, now, latestChosenRepo) ?: return null
|
||||||
|
|
||||||
|
val postsToKeep = uniqueCount ?.let {
|
||||||
|
(excludedByRepo + resultPosts).takeLast(it)
|
||||||
|
} ?: return resultPosts
|
||||||
|
|
||||||
|
val postsToRemoveFromKeep = excludedByRepo.filter { it !in postsToKeep }
|
||||||
|
latestChosenRepo.unset(postsToRemoveFromKeep)
|
||||||
|
val postsToAdd = postsToKeep.filter { it !in excludedByRepo }
|
||||||
|
latestChosenRepo.set(
|
||||||
|
postsToAdd.associateWith { DateTime.now() }
|
||||||
|
)
|
||||||
|
|
||||||
|
return resultPosts
|
||||||
}
|
}
|
||||||
|
|
||||||
@Serializable(Prefer.Serializer::class)
|
@Serializable(Prefer.Serializer::class)
|
||||||
sealed interface Prefer {
|
sealed interface Prefer {
|
||||||
val type: String
|
val type: String
|
||||||
@Serializable(Serializer::class)
|
@Serializable(Serializer::class)
|
||||||
object Max : Prefer { override val type: String = "max" }
|
data object Max : Prefer { override val type: String = "max" }
|
||||||
@Serializable(Serializer::class)
|
@Serializable(Serializer::class)
|
||||||
object Min : Prefer { override val type: String = "min" }
|
data object Min : Prefer { override val type: String = "min" }
|
||||||
@Serializable(Serializer::class)
|
@Serializable(Serializer::class)
|
||||||
object Random : Prefer { override val type: String = "random" }
|
data object Random : Prefer { override val type: String = "random" }
|
||||||
|
|
||||||
object Serializer : KSerializer<Prefer> {
|
object Serializer : KSerializer<Prefer> {
|
||||||
override val descriptor: SerialDescriptor = String.serializer().descriptor
|
override val descriptor: SerialDescriptor = String.serializer().descriptor
|
||||||
|
@ -1,14 +1,33 @@
|
|||||||
package dev.inmo.plaguposter.ratings.selector
|
package dev.inmo.plaguposter.ratings.selector
|
||||||
|
|
||||||
|
import dev.inmo.micro_utils.repos.KeyValueRepo
|
||||||
|
import dev.inmo.micro_utils.repos.exposed.keyvalue.ExposedKeyValueRepo
|
||||||
|
import dev.inmo.micro_utils.repos.mappers.withMapper
|
||||||
import dev.inmo.plagubot.Plugin
|
import dev.inmo.plagubot.Plugin
|
||||||
|
import dev.inmo.plaguposter.posts.models.PostId
|
||||||
import dev.inmo.plaguposter.ratings.selector.models.SelectorConfig
|
import dev.inmo.plaguposter.ratings.selector.models.SelectorConfig
|
||||||
|
import korlibs.time.DateTime
|
||||||
import kotlinx.serialization.json.*
|
import kotlinx.serialization.json.*
|
||||||
import org.jetbrains.exposed.sql.Database
|
import org.jetbrains.exposed.sql.Database
|
||||||
import org.koin.core.module.Module
|
import org.koin.core.module.Module
|
||||||
|
import org.koin.core.qualifier.qualifier
|
||||||
|
|
||||||
object Plugin : Plugin {
|
object Plugin : Plugin {
|
||||||
override fun Module.setupDI(database: Database, params: JsonObject) {
|
override fun Module.setupDI(database: Database, params: JsonObject) {
|
||||||
single { get<Json>().decodeFromJsonElement(SelectorConfig.serializer(), params["selector"] ?: return@single null) }
|
single { get<Json>().decodeFromJsonElement(SelectorConfig.serializer(), params["selector"] ?: return@single null) }
|
||||||
single<Selector> { DefaultSelector(get(), get(), get()) }
|
single<KeyValueRepo<PostId, DateTime>>(qualifier("latestChosenRepo")) {
|
||||||
|
ExposedKeyValueRepo(
|
||||||
|
get(),
|
||||||
|
{ text("post_id") },
|
||||||
|
{ double("date_time") },
|
||||||
|
"LatestChosenRepo"
|
||||||
|
).withMapper(
|
||||||
|
{ string },
|
||||||
|
{ unixMillis },
|
||||||
|
{ PostId(this) },
|
||||||
|
{ DateTime(this) }
|
||||||
|
)
|
||||||
|
}
|
||||||
|
single<Selector> { DefaultSelector(get(), get(), get(), get(qualifier("latestChosenRepo"))) }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -51,7 +51,8 @@
|
|||||||
"to": "23:59"
|
"to": "23:59"
|
||||||
},
|
},
|
||||||
"rating": {
|
"rating": {
|
||||||
"prefer": "max"
|
"prefer": "max",
|
||||||
|
"uniqueCount": 1
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@ -60,7 +61,8 @@
|
|||||||
"to": "00:00"
|
"to": "00:00"
|
||||||
},
|
},
|
||||||
"rating": {
|
"rating": {
|
||||||
"prefer": "max"
|
"prefer": "max",
|
||||||
|
"uniqueCount": 1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
Loading…
Reference in New Issue
Block a user