Skip to content

Commit

Permalink
fix: daily stats
Browse files Browse the repository at this point in the history
  • Loading branch information
elegantShock2258 committed Feb 4, 2024
1 parent 2ffbf93 commit b371cca
Show file tree
Hide file tree
Showing 9 changed files with 97 additions and 132 deletions.
16 changes: 0 additions & 16 deletions docs/spec/CodeCharacter-API.yml
Original file line number Diff line number Diff line change
Expand Up @@ -1970,34 +1970,18 @@ components:
type: object
description: User Match Stat model
properties:
maxAtk:
type: number
default: 0
minAtk:
type: number
default: 0
avgAtk:
type: number
default: 0
dc_wins:
type: number
default: 0
dc_losses:
type: number
default: 0
dc_destruction:
type: number
default: 0
coins:
type: number
default: 0
required:
- maxAtk
- minAtk
- avgAtk
- dc_wins
- dc_losses
- dc_destruction
- coins

DailyChallengeGetRequest:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,34 +16,18 @@ import java.math.BigDecimal

/**
* User Match Stat model
* @param maxAtk
* @param minAtk
* @param avgAtk
* @param dcWins
* @param dcLosses
* @param dcDestruction
* @param coins
*/
data class UserMatchStatDto(

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("maxAtk", required = true) val maxAtk: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("minAtk", required = true) val minAtk: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("avgAtk", required = true) val avgAtk: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("dc_wins", required = true) val dcWins: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("dc_losses", required = true) val dcLosses: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("dc_destruction", required = true) val dcDestruction: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("coins", required = true) val coins: java.math.BigDecimal = BigDecimal.ZERO
) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,34 +17,18 @@ import java.math.BigDecimal

/**
*
* @param maxAtk
* @param minAtk
* @param avgAtk
* @param dcWins
* @param dcLosses
* @param dcDestruction
* @param coins
*/
data class UserMatchStatsInnerDto(

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("maxAtk", required = true) val maxAtk: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("minAtk", required = true) val minAtk: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("avgAtk", required = true) val avgAtk: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("dc_wins", required = true) val dcWins: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("dc_losses", required = true) val dcLosses: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("dc_destruction", required = true) val dcDestruction: java.math.BigDecimal = BigDecimal.ZERO,

@Schema(example = "null", required = true, description = "")
@get:JsonProperty("coins", required = true) val coins: java.math.BigDecimal = BigDecimal.ZERO
) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -485,7 +485,7 @@ class MatchService(
statsService.updateStats(
userId = match.user.userId,
verdict = verdict,
atkDmg = updatedGame.destruction,
atkDmg = 0.0,
dcAttempts = 1,
coins = updatedGame.coinsUsed
)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,47 +1,47 @@
package delta.codecharacter.server.schedulers

import delta.codecharacter.server.code.code_revision.CodeRevisionService
import delta.codecharacter.server.code.latest_code.LatestCodeService
import delta.codecharacter.server.code.locked_code.LockedCodeService
import delta.codecharacter.server.game_map.latest_map.LatestMapService
import delta.codecharacter.server.game_map.locked_map.LockedMapService
import delta.codecharacter.server.game_map.map_revision.MapRevisionService
import delta.codecharacter.server.match.MatchService
import delta.codecharacter.server.user.public_user.PublicUserService
import org.slf4j.Logger
import org.slf4j.LoggerFactory
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.scheduling.annotation.Scheduled
import org.springframework.stereotype.Service

@Service
class SchedulingService(
@Autowired private val publicUserService: PublicUserService,
@Autowired private val matchService: MatchService,
@Autowired private val codeRevisionService: CodeRevisionService,
@Autowired private val latestCodeService: LatestCodeService,
@Autowired private val lockedCodeService: LockedCodeService,
@Autowired private val latestMapService: LatestMapService,
@Autowired private val lockedMapService: LockedMapService,
@Autowired private val mapRevisionService: MapRevisionService
) {
private val logger: Logger = LoggerFactory.getLogger(SchedulingService::class.java)

@Scheduled(cron = "\${environment.registration-time}", zone = "GMT+5:30")
fun updateTempLeaderboard() {
logger.info("Practice phase ended!!")
publicUserService.resetRatingsAfterPracticePhase()
codeRevisionService.resetCodeRevisionAfterPracticePhase()
latestCodeService.resetLatestCodeAfterPracticePhase()
lockedCodeService.resetLockedCodeAfterPracticePhase()
latestMapService.resetLatestMapAfterPracticePhase()
lockedMapService.resetLockedMapAfterPracticePhase()
mapRevisionService.resetMapRevisionAfterPracticePhase()
publicUserService.updateLeaderboardAfterPracticePhase()
}

@Scheduled(cron = "\${environment.promote-demote-time}", zone = "GMT+5:30")
fun createAutoMatch() {
matchService.createAutoMatch()
}
}
// package delta.codecharacter.server.schedulers
//
// import delta.codecharacter.server.code.code_revision.CodeRevisionService
// import delta.codecharacter.server.code.latest_code.LatestCodeService
// import delta.codecharacter.server.code.locked_code.LockedCodeService
// import delta.codecharacter.server.game_map.latest_map.LatestMapService
// import delta.codecharacter.server.game_map.locked_map.LockedMapService
// import delta.codecharacter.server.game_map.map_revision.MapRevisionService
// import delta.codecharacter.server.match.MatchService
// import delta.codecharacter.server.user.public_user.PublicUserService
// import org.slf4j.Logger
// import org.slf4j.LoggerFactory
// import org.springframework.beans.factory.annotation.Autowired
// import org.springframework.scheduling.annotation.Scheduled
// import org.springframework.stereotype.Service
//
// @Service
// class SchedulingService(
// @Autowired private val publicUserService: PublicUserService,
// @Autowired private val matchService: MatchService,
// @Autowired private val codeRevisionService: CodeRevisionService,
// @Autowired private val latestCodeService: LatestCodeService,
// @Autowired private val lockedCodeService: LockedCodeService,
// @Autowired private val latestMapService: LatestMapService,
// @Autowired private val lockedMapService: LockedMapService,
// @Autowired private val mapRevisionService: MapRevisionService
// ) {
// private val logger: Logger = LoggerFactory.getLogger(SchedulingService::class.java)
//
// @Scheduled(cron = "\${environment.registration-time}", zone = "GMT+5:30")
// fun updateTempLeaderboard() {
// logger.info("Practice phase ended!!")
// publicUserService.resetRatingsAfterPracticePhase()
// codeRevisionService.resetCodeRevisionAfterPracticePhase()
// latestCodeService.resetLatestCodeAfterPracticePhase()
// lockedCodeService.resetLockedCodeAfterPracticePhase()
// latestMapService.resetLatestMapAfterPracticePhase()
// lockedMapService.resetLockedMapAfterPracticePhase()
// mapRevisionService.resetMapRevisionAfterPracticePhase()
// publicUserService.updateLeaderboardAfterPracticePhase()
// }
//
// @Scheduled(cron = "\${environment.promote-demote-time}", zone = "GMT+5:30")
// fun createAutoMatch() {
// matchService.createAutoMatch()
// }
// }
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
package delta.codecharacter.server.stats

import delta.codecharacter.server.user.public_user.DailyChallengeHistory
import org.springframework.data.annotation.Id
import org.springframework.data.mongodb.core.mapping.Document
import java.util.*

@Document(collection="stats")
data class PublicStatEntity(
@Id val userId: UUID,
val stats : List<StatEntity>
var stats: HashMap<Int, StatEntity>
)
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
package delta.codecharacter.server.stats

import delta.codecharacter.server.match.MatchModeEnum
import java.time.Instant

data class StatEntity (
val maxAtk :Double,
val minAtk : Double,
val avgAtk : Double,
val dc_wins : Int,
val dc_losses : Int,
val dc_destruction: Int,
val coins : Int
val coins : Int,
val createdAt: Instant,
)
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,4 @@ class StatsController(@Autowired private val statsService: StatsService) : Stats
val user = SecurityContextHolder.getContext().authentication.principal as UserEntity
return ResponseEntity.ok(statsService.getInfo(user.id))
}


}
Original file line number Diff line number Diff line change
@@ -1,55 +1,73 @@
package delta.codecharacter.server.stats

import delta.codecharacter.dtos.UserMatchStatsInnerDto
import delta.codecharacter.server.daily_challenge.DailyChallengeService
import delta.codecharacter.server.daily_challenge.match.DailyChallengeMatchVerdictEnum
import delta.codecharacter.server.schedulers.SchedulingService
import delta.codecharacter.server.user.public_user.PublicUserRepository
import org.slf4j.Logger
import org.slf4j.LoggerFactory
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.beans.factory.annotation.Value
import org.springframework.data.domain.PageRequest
import org.springframework.data.domain.Sort
import org.springframework.stereotype.Service
import java.math.BigDecimal
import java.time.Duration
import java.time.Instant
import java.util.*
import kotlin.collections.ArrayList
import kotlin.math.max
import kotlin.collections.HashMap
import kotlin.math.min

@Service
class StatsService(@Autowired private val statsRepository:StatsRepository,
@Autowired private val publicUserRepository: PublicUserRepository){

@Value("\${environment.event-start-date}") private lateinit var startDate: String
fun findNumberOfDays(): Int {
val givenDateTime = Instant.parse(startDate)
val nowDateTime = Instant.now()
val period: Duration = Duration.between(givenDateTime, nowDateTime)
return period.toDays().toInt()
}
fun updateStats(
userId: UUID,
atkDmg: Double,
coins: Int,
dcAttempts: Int,
verdict: DailyChallengeMatchVerdictEnum?,
) {
val currentDay = findNumberOfDays()
if(statsRepository.existsById(userId)) {
val userList = statsRepository.findById(userId).get()
val user = userList.stats.last()
val user = (statsRepository.findById(userId).get())
val userStats:StatEntity;
if(user.stats.containsKey(currentDay)){
userStats = user.stats[currentDay]!!
} else {
var win = 0
if(dcAttempts!=0){
win = if(verdict == DailyChallengeMatchVerdictEnum.SUCCESS) 1 else 0
}
user.stats[currentDay] = StatEntity(atkDmg,win,coins, Instant.now());
userStats = user.stats[currentDay]!!
}
val updatedUserStat =
user.copy(
maxAtk = max(user.maxAtk, atkDmg),
minAtk = min(user.minAtk, atkDmg),
avgAtk = (user.avgAtk * userList.stats.size + atkDmg) / (1+userList.stats.size),
coins = (user.coins * userList.stats.size + coins) / (1+userList.stats.size),
dc_losses =
if (dcAttempts != 0 && verdict == DailyChallengeMatchVerdictEnum.FAILURE)
user.dc_losses + 1
else user.dc_losses,
userStats.copy(
avgAtk = (userStats.avgAtk * user.stats.size + atkDmg) / (1+user.stats.size),
coins = (userStats.coins * user.stats.size + coins) / (1+user.stats.size),
dc_wins =
if (dcAttempts != 0 && verdict == DailyChallengeMatchVerdictEnum.SUCCESS)
user.dc_wins + 1
else user.dc_wins,
userStats.dc_wins + 1
else userStats.dc_wins,
)
val updatedUserList = (userList.stats.toMutableList())
updatedUserList.add(updatedUserStat)
val updatedUser = userList.copy(stats = updatedUserList)
statsRepository.save(updatedUser)
user.stats[currentDay] = updatedUserStat;
statsRepository.save(user)
} else {
statsRepository.insert((PublicStatEntity(userId,listOf(StatEntity(atkDmg,atkDmg,atkDmg,0,0,0,coins)))))
val initialMap = HashMap<Int,StatEntity>();
var win = 0
if(dcAttempts!=0){
win = if(verdict == DailyChallengeMatchVerdictEnum.SUCCESS) 1 else 0
}
initialMap[currentDay] = StatEntity(atkDmg,win,coins,Instant.now())
statsRepository.insert(PublicStatEntity(userId,initialMap))
}
}
fun getInfo(userId: UUID): List<List<UserMatchStatsInnerDto>> {
Expand All @@ -68,7 +86,7 @@ class StatsService(@Autowired private val statsRepository:StatsRepository,
l.add(lTop)
return l
}
val currentUserStats = statsRepository.findById(userId).get();
val currentUserStats = statsRepository.findById(userId).get()
var lUser = convertToDTO(currentUserStats)

val minEle = min(lUser.size,lTop.size)
Expand All @@ -83,14 +101,10 @@ class StatsService(@Autowired private val statsRepository:StatsRepository,
}

private fun convertToDTO(currentUserStatsArr: PublicStatEntity): List<UserMatchStatsInnerDto> {
return currentUserStatsArr.stats.map {it ->
return currentUserStatsArr.stats.values.map {it ->
UserMatchStatsInnerDto(
maxAtk = BigDecimal(it.maxAtk),
minAtk = BigDecimal(it.minAtk),
avgAtk = BigDecimal(it.avgAtk),
dcWins = BigDecimal(it.dc_wins),
dcLosses = BigDecimal(it.dc_losses),
dcDestruction = BigDecimal(it.dc_destruction),
coins = BigDecimal(it.coins)
)
}
Expand Down

0 comments on commit b371cca

Please sign in to comment.