Fix user stats
continuous-integration/drone/push Build is passing Details

pull/17/head
avalin 11 months ago
parent 4db74afce2
commit 90b099183c

@ -7,5 +7,4 @@ interface ParticipationDataSource {
fun getParticipationFromBetId(betid: String): List<Participation> fun getParticipationFromBetId(betid: String): List<Participation>
fun getParticipationFromUserId(username: String, betid: String): List<Participation> fun getParticipationFromUserId(username: String, betid: String): List<Participation>
fun deleteParticipation(id: String): Boolean fun deleteParticipation(id: String): Boolean
fun getBestWinFromUserid(userId: String): Int?
} }

@ -88,9 +88,4 @@ class MockParticipationDataSource(private val mockData: MockDataSource.MockData)
return result return result
} }
override fun getBestWinFromUserid(userId: String) =
mockData.participations.filter { it.id == userId }.maxBy { it.stake }.stake
} }

@ -10,21 +10,30 @@ class MockUserDataSource(private val mockData: MockDataSource.MockData) : UserDa
private val lastGifts get() = mockData.lastGifts private val lastGifts get() = mockData.lastGifts
override fun getUserByUsername(username: String): Pair<UserDTO?, String?> = override fun getUserByUsername(username: String): Pair<UserDTO?, String?> =
users.find { (it.username == username) or (it.email == username) }?.let { users.find { (it.username == username) or (it.email == username) }?.let { usr ->
Pair( Pair(
UserDTO( UserDTO(
id = it.id, id = usr.id,
username = it.username, username = usr.username,
email = it.email, email = usr.email,
nbCoins = it.nbCoins, nbCoins = usr.nbCoins,
token = it.token, token = usr.token,
image = null, image = null,
nbBets = MockBetDataSource(mockData).getHistory(it.username).count(), nbBets = mockData.participations.count { it.username == usr.username },
nbFriends = MockFriendDataSource(mockData).getFriendFromUserId(it.id).count(), nbFriends = mockData.friends.count { f ->
bestWin = MockParticipationDataSource(mockData).getBestWinFromUserid(it.id), f.receiver == usr.username &&
mockData.friends.any { it.sender == usr.username && it.receiver == f.sender }
},
bestWin = mockData.participations
.filter {
(it.id == usr.id) &&
(mockData.results.find { r -> r.betId == it.betId })?.result == it.answer
}
.maxBy { it.stake }
.stake,
friendStatus = null, friendStatus = null,
), ),
it.password usr.password
) )
} ?: Pair(null, null) } ?: Pair(null, null)

@ -5,11 +5,13 @@ import allin.data.postgres.entities.FriendEntity
import allin.data.postgres.entities.friends import allin.data.postgres.entities.friends
import allin.data.postgres.entities.users import allin.data.postgres.entities.users
import allin.dto.UserDTO import allin.dto.UserDTO
import allin.ext.length
import allin.ext.levenshteinLessEq import allin.ext.levenshteinLessEq
import allin.ext.toLowerCase import allin.ext.toLowerCase
import allin.model.FriendStatus import allin.model.FriendStatus
import org.ktorm.database.Database import org.ktorm.database.Database
import org.ktorm.dsl.and import org.ktorm.dsl.and
import org.ktorm.dsl.div
import org.ktorm.dsl.eq import org.ktorm.dsl.eq
import org.ktorm.dsl.notEq import org.ktorm.dsl.notEq
import org.ktorm.entity.* import org.ktorm.entity.*
@ -67,24 +69,29 @@ class PostgresFriendDataSource(private val database: Database) : FriendDataSourc
database.friends.any { (it.sender eq firstUser) and (it.receiver eq secondUser) } database.friends.any { (it.sender eq firstUser) and (it.receiver eq secondUser) }
override fun filterUsersByUsername(fromUserId: String, search: String): List<UserDTO> { override fun filterUsersByUsername(fromUserId: String, search: String): List<UserDTO> {
val maxSize = search.length / 2
return database.users return database.users
.filter { (it.id notEq fromUserId) } .filter { (it.id notEq fromUserId) }
.mapColumns { .mapColumns {
tupleOf( tupleOf(
it.id, it.id,
it.username.toLowerCase().levenshteinLessEq(search.lowercase(), maxSize) it.username,
it.username.toLowerCase().levenshteinLessEq(
search.lowercase(),
(it.username.length() / 2)
)
) )
} }
.filter { (_, distance) -> .filter { (_, username, distance) ->
val maxSize = ((username?.length ?: 0) / 2)
distance?.let { it <= maxSize } ?: false distance?.let { it <= maxSize } ?: false
} }
.sortedBy { it.second } .sortedBy { it.second }
.mapNotNull { (id, _) -> .mapNotNull { (id, _, _) ->
id?.let { id?.let {
val user = database.users.find { it.id eq id } val user = database.users.find { it.id eq id }
user?.toUserDTO(database, friendStatus = getFriendStatus(fromUserId, user.id)) user?.toUserDTO(database, friendStatus = getFriendStatus(fromUserId, user.id))
} }
} }
} }
} }

@ -68,9 +68,6 @@ class PostgresParticipationDataSource(private val database: Database) : Particip
return participation.delete() > 0 return participation.delete() > 0
} }
override fun getBestWinFromUserid(userId: String) =
database.participations.filter { it.id eq userId }.maxBy { it.stake }
} }

@ -93,12 +93,16 @@ class PostgresUserDataSource(private val database: Database) : UserDataSource {
} }
override fun getImage(userid: String): String? { override fun getImage(userid: String): String? {
val resultSet = database.executeWithResult("SELECT encode(image, 'base64') AS image FROM userimage WHERE user_id = '${userid}'")?: return null val resultSet =
database.executeWithResult(
"""
SELECT encode(image, 'base64') AS image
FROM userimage
WHERE user_id = '${userid}'
""".trimIndent()
) ?: return null
if (resultSet.next()) { if (resultSet.next()) {
val base64Image: String? = resultSet.getString("image") resultSet.getString("image")?.let { return it }
if (base64Image != null) {
return base64Image
}
} }
return null return null
} }

@ -1,17 +1,13 @@
package allin.data.postgres.entities package allin.data.postgres.entities
import allin.data.postgres.PostgresBetDataSource
import allin.data.postgres.PostgresFriendDataSource
import allin.data.postgres.PostgresParticipationDataSource
import allin.dto.UserDTO import allin.dto.UserDTO
import allin.model.FriendStatus import allin.model.FriendStatus
import allin.routing.imageManagerUser import allin.routing.imageManagerUser
import allin.utils.AppConfig import allin.utils.AppConfig
import org.ktorm.database.Database import org.ktorm.database.Database
import org.ktorm.dsl.and
import org.ktorm.dsl.eq import org.ktorm.dsl.eq
import org.ktorm.entity.Entity import org.ktorm.entity.*
import org.ktorm.entity.find
import org.ktorm.entity.sequenceOf
import org.ktorm.schema.Table import org.ktorm.schema.Table
import org.ktorm.schema.int import org.ktorm.schema.int
import org.ktorm.schema.timestamp import org.ktorm.schema.timestamp
@ -36,9 +32,19 @@ interface UserEntity : Entity<UserEntity> {
nbCoins = nbCoins, nbCoins = nbCoins,
token = null, token = null,
image = getImage(id, database), image = getImage(id, database),
nbBets = PostgresBetDataSource(database).getHistory(username).count(), nbBets = database.participations.count { it.username eq this.username },
nbFriends = PostgresFriendDataSource(database).getFriendFromUserId(id).count(), nbFriends = database.friends
bestWin = PostgresParticipationDataSource(database).getBestWinFromUserid(id)?: 0, .filter { it.receiver eq this.id }
.mapNotNull { p -> database.friends.any { (it.sender eq this.id) and (it.receiver eq p.sender) } }
.count(),
bestWin = database.participations
.filter { (it.id eq this.id) }
.mapNotNull { p ->
if (database.betResults.any { (it.betId eq p.bet.id) and (it.result eq p.answer) }) {
p.stake
} else null
}
.maxOrNull() ?: 0,
friendStatus = friendStatus friendStatus = friendStatus
) )

@ -14,5 +14,5 @@ data class UserDTO(
var nbBets: Int, var nbBets: Int,
var nbFriends: Int, var nbFriends: Int,
var bestWin: Int, var bestWin: Int,
var friendStatus: FriendStatus?, var friendStatus: FriendStatus?
) )

@ -1,7 +1,6 @@
package allin.ext package allin.ext
import org.ktorm.database.Database import org.ktorm.database.Database
import org.ktorm.expression.ArgumentExpression
import org.ktorm.expression.FunctionExpression import org.ktorm.expression.FunctionExpression
import org.ktorm.schema.ColumnDeclaring import org.ktorm.schema.ColumnDeclaring
import org.ktorm.schema.IntSqlType import org.ktorm.schema.IntSqlType
@ -33,6 +32,14 @@ fun Database.execute(request: String) {
} }
} }
fun ColumnDeclaring<String>.length(): FunctionExpression<Int> {
return FunctionExpression(
functionName = "LENGTH",
arguments = listOf(this.asExpression()),
sqlType = IntSqlType
)
}
fun ColumnDeclaring<String>.toLowerCase(): FunctionExpression<String> { fun ColumnDeclaring<String>.toLowerCase(): FunctionExpression<String> {
return FunctionExpression( return FunctionExpression(
functionName = "LOWER", functionName = "LOWER",
@ -60,8 +67,8 @@ fun ColumnDeclaring<String>.levenshteinLessEq(
) )
} }
fun ColumnDeclaring<String>.levenshteinLessEq(target: String, max: Int): FunctionExpression<Int> = fun ColumnDeclaring<String>.levenshteinLessEq(target: String, max: ColumnDeclaring<Int>): FunctionExpression<Int> =
levenshteinLessEq( levenshteinLessEq(
wrapArgument(target), wrapArgument(target),
ArgumentExpression(max, IntSqlType) max
) )
Loading…
Cancel
Save