package com.red.circle.other.app.command.activity;

import com.fasterxml.jackson.core.type.TypeReference;
import com.google.common.collect.Lists;
import com.red.circle.common.business.dto.cmd.app.AppIdLongCmd;
import com.red.circle.common.business.enums.SendPropsOrigin;
import com.red.circle.framework.core.asserts.ResponseAssert;
import com.red.circle.framework.core.response.CommonErrorCode;
import com.red.circle.other.infra.common.activity.PropsActivitySendCommon;
import com.red.circle.other.infra.common.activity.send.SendRewardGroup;
import com.red.circle.other.infra.database.cache.service.user.UserInviteCacheService;
import com.red.circle.other.infra.database.rds.entity.activity.PropsActivityRuleConfig;
import com.red.circle.other.infra.database.rds.entity.user.user.InviteUserSummary;
import com.red.circle.other.infra.database.rds.service.activity.PropsActivityRuleConfigService;
import com.red.circle.other.infra.database.rds.service.user.user.InviteUserSummaryService;
import com.red.circle.other.inner.asserts.PropsErrorCode;
import com.red.circle.other.inner.asserts.user.UserErrorCode;
import com.red.circle.other.inner.model.dto.activity.rule.CumulativeRechargeContent;
import com.red.circle.tool.core.json.JacksonUtils;
import java.util.List;
import java.util.Objects;
import java.util.Optional;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Component;

/**
 * 邀请用户注册活动 领奖.
 *
 * @author pengshigang
 * @since 2022-05-24
 */
@Component
@RequiredArgsConstructor
public class InviteUserReceiveAwardExe {

  private final UserInviteCacheService userInviteCacheService;
  private final PropsActivitySendCommon propsActivitySendCommon;
  private final InviteUserSummaryService inviteUserSummaryService;
  private final PropsActivityRuleConfigService propsActivityRuleConfigService;

  public void execute(AppIdLongCmd cmd) {

    PropsActivityRuleConfig config = propsActivityRuleConfigService.getById(cmd.getId());
    ResponseAssert.notNull(CommonErrorCode.DATA_ERROR, config);

    String idsStr = userInviteCacheService.getRewardsReceivedRuleIds(cmd.getReqUserId());
    //已领取的奖励组ID
    List<Long> ruleConfigIds = Optional.ofNullable(JacksonUtils.readValue(idsStr, new
            TypeReference<List<Long>>() {
            }))
        .orElse(Lists.newArrayList());

    //已拥有的邀请数
    InviteUserSummary summary = inviteUserSummaryService.getByUserId(cmd.getReqUserId());
    Long userCount = 0L;
    if (Objects.nonNull(summary)) {
      userCount = summary.getQuantity();
    }

    // 2046 不可领取
    ResponseAssert.isFalse(PropsErrorCode.UNCLAIMABLE, userCount <= 0);

    CumulativeRechargeContent content = CumulativeRechargeContent
        .serializable(config.getJsonData());

    // 2040 配置错误
    ResponseAssert.isTrue(CommonErrorCode.CONFIGURATION_ERROR,
        Objects.nonNull(content) && content.getQuantity().longValue() > 0);

    ResponseAssert.isTrue(PropsErrorCode.UNCLAIMABLE,
        userCount >= content.getQuantity().longValue());

    //校验是否已领取
    ResponseAssert.isTrue(UserErrorCode.AWARD_RECEIVED, !ruleConfigIds.contains(config.getId()));

    //发送奖励
    SendRewardGroup param = SendRewardGroup.builder().build();
    param.setResourceGroupId(config.getResourceGroupId());
    param.setAcceptUserId(cmd.getReqUserId());
    param.setOrigin(SendPropsOrigin.INVITE_USER_REWARDS);
    param.setTrackId(config.getId());
    param.setSysOrigin(cmd.requireReqSysOriginEnum());
    propsActivitySendCommon.sendActivityGroup(param);
    ruleConfigIds.add(config.getId());
    userInviteCacheService
        .setRewardsReceivedRuleIds(cmd.getReqUserId(), JacksonUtils.toJson(ruleConfigIds));
  }


}
