package com.red.circle.other.app.service.game;

import com.red.circle.component.redis.service.RedisService;
import com.red.circle.framework.core.dto.ReqSysOrigin;
import com.red.circle.other.app.dto.cmd.SpinsTaskProgressUpdateCmd;
import com.red.circle.other.app.dto.cmd.activity.RankingDataUpdateCmd;
import com.red.circle.other.app.service.SpinsUserTaskProgressService;
import com.red.circle.other.app.service.activity.RankingActivityService;
import com.red.circle.other.app.util.DateTimeAsiaRiyadhUtils;
import com.red.circle.other.domain.ranking.RankingActivityType;
import com.red.circle.other.domain.ranking.RankingCycleType;
import com.red.circle.other.domain.ranking.RankingDimension;
import com.red.circle.tool.core.date.ZonedDateTimeAsiaRiyadhUtils;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.util.concurrent.TimeUnit;

/**
 * 游戏活动服务
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class GameActivityService {

    private static final long MAX_DAILY_SPEND = 500000L;
    private static final String REDIS_KEY_PREFIX = "spins:daily:game:save:";

    private final RedisService redisService;
    private final SpinsUserTaskProgressService spinsUserTaskProgressService;
    private final RankingActivityService rankingActivityService;

    /**
     * 处理游戏消费/获得任务
     *
     * @param userId 用户ID
     * @param spendAmount 本次消费/获得金额
     */
    public void handleGameSpendTask(Long userId, Long spendAmount) {
        try {
            if (spendAmount <= 0) {
                return;
            }

            String redisKey = REDIS_KEY_PREFIX + userId;
            
            Long totalSpend = redisService.increment(redisKey, spendAmount);
            
            // 首次创建时设置过期时间
            if (totalSpend.equals(spendAmount)) {
                long expireSeconds = DateTimeAsiaRiyadhUtils.getSecondsUntilMidnight();
                redisService.expire(redisKey, expireSeconds, TimeUnit.SECONDS);
            }

            // 如果累计已经超过500000，不再处理任务
            if (totalSpend - spendAmount >= MAX_DAILY_SPEND) {
                log.info("Spins游戏消费任务已达上限, userId={}, totalSpend={}", userId, totalSpend);
                return;
            }

            log.info("Spins游戏消费任务, userId={}, spendAmount={}, totalSpend={}", userId, spendAmount, totalSpend);

            int progressValue = totalSpend.intValue();
            updateGameSpendProgress(userId, progressValue);

            log.info("Spins游戏消费任务处理成功, userId={}, totalSpend={}", userId, totalSpend);
        } catch (Exception e) {
            log.error("处理Spins游戏消费任务失败, userId={}, spendAmount={}", userId, spendAmount, e);
        }
    }

    public void incKingGameDaily(Long userId, Long rewardAmount, String gameId) {
        RankingDataUpdateCmd receiverCmd = new RankingDataUpdateCmd();
        receiverCmd.setUserId(userId);
        receiverCmd.setUserSex(1);
        receiverCmd.setActivityType(RankingActivityType.KING_GAMES_DAILY.getCode());
        receiverCmd.setCycleType(RankingCycleType.DAILY.getCode());
        receiverCmd.setCycleKey(ZonedDateTimeAsiaRiyadhUtils.nowDateToInt().toString());
        receiverCmd.setDimension(RankingDimension.GAME_WIN.getCode());
        receiverCmd.setIncrementQuantity(rewardAmount);
        receiverCmd.setBizNo(gameId);
        receiverCmd.setReqSysOrigin(ReqSysOrigin.of("LIKEI"));
        rankingActivityService.accumulateRankingData(receiverCmd);
    }


    /**
     * 更新游戏进度
     */
    private void updateGameSpendProgress(Long userId, int progressValue) {
        spinsUserTaskProgressService.updateTaskProgress(
                new SpinsTaskProgressUpdateCmd()
                        .setUserId(userId)
                        .setTaskCode("SP_SAVE_50000")
                        .setProgressValue(progressValue)
        );

        spinsUserTaskProgressService.updateTaskProgress(
                new SpinsTaskProgressUpdateCmd()
                        .setUserId(userId)
                        .setTaskCode("SP_SAVE_100000")
                        .setProgressValue(progressValue)
        );

        spinsUserTaskProgressService.updateTaskProgress(
                new SpinsTaskProgressUpdateCmd()
                        .setUserId(userId)
                        .setTaskCode("SP_SAVE_500000")
                        .setProgressValue(progressValue)
        );

    }
}
