package com.bonus.canteen.core.account.mq;

import com.bonus.canteen.core.account.constants.AccStatusEnum;
import com.bonus.canteen.core.account.domain.bo.AccStatusChange;
import com.bonus.canteen.core.common.utils.MqUtil;
import com.bonus.canteen.core.common.utils.TenantContextHolder;
import com.bonus.common.core.constant.SecurityConstants;
import com.bonus.common.core.web.domain.AjaxResult;
import com.bonus.common.houqin.mq.constant.LeMqConstant;
import com.bonus.common.houqin.utils.JacksonUtil;
import com.bonus.system.api.RemoteUserService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Map;
import java.util.Objects;

@Component
public class AccMqSender {
   private static final Logger log = LoggerFactory.getLogger(AccMqSender.class);
   @Resource
   private RemoteUserService remoteUserService;
   public void accChangeMQ(List<Long> userIds, Integer accStatus) {
      // 校验输入参数
      if (userIds == null || accStatus == null) {
         log.warn("用户ID列表或账户状态为空，无法发送MQ。userIds: {}, accStatus: {}", userIds, accStatus);
         return;
      }

      if (!AccStatusEnum.DEACTIVATE.getKey().equals(accStatus)) {
         log.warn("账户状态不在允许范围内，无法发送MQ。accStatus: {}", accStatus);
         return;
      }

      try {
         log.info("账户状态变动发送mq-入参人员数量： {} 账户状态： {}", userIds.size(), accStatus);

         AjaxResult resultList = remoteUserService.getUsers(userIds.toArray(EMPTY_LONG_ARRAY), SecurityConstants.INNER);

         // 校验远程调用结果
         if (resultList == null || resultList.get(AjaxResult.DATA_TAG) == null) {
            log.error("远程用户服务返回数据为空");
            return;
         }

         List sysUserList = resultList.getDataAs(List.class);
         if (sysUserList == null || sysUserList.isEmpty()) {
            log.warn("用户列表为空，无需发送MQ");
            return;
         }

         Long tenantId = TenantContextHolder.getTenantId();
         if (tenantId == null) {
            log.error("租户ID为空，无法发送MQ");
            return;
         }
         LocalDateTime now = LocalDateTime.now();
         sysUserList.stream()
                 .filter(Objects::nonNull)
                 .map(item -> processUserItem((Map<String, Object>) item, tenantId, accStatus, now))
                 .filter(Objects::nonNull)
                 .forEach(accStatusChange -> sendMqMessage((AccStatusChange)accStatusChange));

      } catch (Exception e) {
         log.error("账户状态变动发送MQ失败", e);
      }
   }

   private AccStatusChange processUserItem(Map<String, Object> map, Long tenantId, Integer accStatus, LocalDateTime now) {
      if (map == null || !map.containsKey("userId") || !map.containsKey("userName")) {
         log.warn("用户数据不完整，跳过处理。map: {}", map);
         return null;
      }

      AccStatusChange accStatusChange = new AccStatusChange();
      accStatusChange.setUserId((String)map.get("userId"));
      accStatusChange.setNickName((String) map.get("nickName"));
      accStatusChange.setMerchantId(tenantId);
      accStatusChange.setAccStatus(accStatus);
      accStatusChange.setUpdateDateTime(now);
      return accStatusChange;
   }

   private void sendMqMessage(AccStatusChange accStatusChange) {
      String jsonString = JacksonUtil.writeValueAsString(accStatusChange);
      if (jsonString == null) {
         log.error("序列化账户状态变更对象失败：{}", accStatusChange);
         return;
      }

      log.info("账户状态变动发送mq内容：{}", jsonString);
      try {
         MqUtil.pushToTenantAllDevice(jsonString, LeMqConstant.Topic.ACC_DATA_CHANGE_ACC_STATUS);
      } catch (Exception e) {
         log.error("发送MQ消息失败：{}", jsonString, e);
      }
   }
   private static final Long[] EMPTY_LONG_ARRAY = new Long[0];
}
