package com.czg.market.service;

import cn.hutool.core.exceptions.ValidateException;
import com.czg.account.entity.UserInfo;
import com.czg.constant.TableValueConstant;
import com.czg.exception.CzgException;
import com.czg.market.dto.MkDistributionUserDTO;
import com.czg.market.dto.MkDistributionWithdrawFlowDTO;
import com.czg.market.entity.MkDistributionConfig;
import com.czg.market.entity.MkDistributionFlow;
import com.czg.market.entity.MkDistributionUser;
import com.czg.market.vo.DistributionCenterShopVO;
import com.czg.market.vo.InviteUserVO;
import com.czg.order.dto.MkDistributionPayDTO;
import com.czg.order.entity.OrderInfo;
import com.mybatisflex.core.paginate.Page;
import com.mybatisflex.core.service.IService;

import java.math.BigDecimal;
import java.util.Map;

/**
 * 分销员表 服务层。
 *
 * @author ww
 * @since 2025-10-27
 */
public interface MkDistributionUserService extends IService<MkDistributionUser> {

    /**
     * 分销员中心-用户信息
     */
    Map<String, Object> centerUser(Long userId);

    /**
     * 分销员中心-已激活店铺
     */
    Page<DistributionCenterShopVO> activates(Long userId, Integer page, Integer size);

    /**
     * 分销员中心-未激活店铺
     */
    Page<DistributionCenterShopVO> unActivates(Long userId, Integer page, Integer size);


    /**
     * 分销员中心-配置信息
     */
    Map<String, Object> centerConfig(Long userId, Long shopId);

    /**
     * 分销员中心-获取邀请码
     */
    String getInviteCode(Long shopId, Long shopUserId)  throws CzgException, ValidateException ;

    /**
     * 分销员中心-实名认证
     */
    void realNameAuth(UserInfo userInfo);

    /**
     * 分销员中心-绑定邀请人
     * 通过邀请码
     */
    void bindInviteUser(MkDistributionUserDTO param) throws CzgException, ValidateException;


    /**
     * 分销员中心-绑定邀请人
     * 通过邀请人id
     * @param fromUserId    shopUserId 邀请人
     * @param toUserId      被邀请人邀请人
     */
    void bindInviteUser(Long fromUserId, Long toUserId, Long shopId) throws CzgException, ValidateException;
    /**
     * 获取分销员分页列表
     */
    Page<MkDistributionUserDTO> getDistributionUser(MkDistributionUserDTO param);

    /**
     * 获取分销员邀请人分页列表
     */
    Page<InviteUserVO> getInviteUser(Long id, Long shopId, Long shopUserId, Long distributionLevelId, Integer page, Integer size);

    /**
     * 分销员：按消费金额升级等级
     */
    void costUpgradeLevelBefore(Long userId, Long shopId);

    /**
     * 添加分销员
     * shop_id 和 shop_user_id 必填 opening_method 必填
     * 如果distribution_level_id指定 则  distribution_level_name 也填
     */
    MkDistributionUser addDistributionUser(MkDistributionUser param);

    /**
     * 更新分销员
     */
    void updateDistributionUserById(MkDistributionUserDTO param);

    /**
     * 重置分销员等级
     */
    void resetDistributionUserLevel(MkDistributionUserDTO param);


    void initLevel(MkDistributionConfig config, MkDistributionUser distributionUser);

    /**
     * 删除分销员
     * 逻辑删除分销员
     */
    void deleteDistributionUser(Long id, Long shopId);


    Boolean cashPayOrder(long adminId, MkDistributionPayDTO payParam);

    /**
     * 分销员开通
     *
     * @param shopUserId 用户
     * @param amount     金额
     * @param shopId     店铺id
     */
    void open(Long shopUserId, BigDecimal amount, Long shopId, Long sourceId);

    /**
     * 分销商户运营余额充值回调
     */
    void rechargeCallBack(Long shopId, BigDecimal amount, Long paymentId);

    BigDecimal updateShopInfoAmount(Long shopId, BigDecimal changeAmount, Long sourceId, TableValueConstant.DistributionAmountFlow.Type type, String remark);

    void refund(Long orderId, String orderNo);

    void distributionUserAmount(MkDistributionFlow item, OrderInfo orderInfo);

    /**
     * 发放分销奖励
     *
     * @param sourceId 来源id
     * @param orderNo  订单编号
     * @param amount   金额
     * @param userId   用户id
     * @param shopId   店铺id
     */
    void distribute(Long sourceId, String orderNo, BigDecimal amount, Long userId, Long shopId, String type);

    void updateIncome(BigDecimal pendingIncome, BigDecimal receivedIncome, BigDecimal withdrawIncome, Long id, Long userId, Long shopUserId, Long shopId, Integer isOne);


    Boolean withdraw(long userId, MkDistributionWithdrawFlowDTO withdrawFlowDTO);

    Map<String, Object> withdrawDetail(long userId, Long id);

    /**
     * 微信转账回调
     *
     * @param outBillNo 转账单号
     * @param state     ACCEPTED：单据已受理
     *                  PROCESSING：单据处理中，转账结果尚未明确，如一直处于此状态，建议检查账户余额是否足够
     *                  WAIT_USER_CONFIRM：待收款用户确认，可拉起微信收款确认页面进行收款确认
     *                  TRANSFERING：转账中，转账结果尚未明确，可拉起微信收款确认页面再次重试确认收款
     *                  SUCCESS： 转账成功
     *                  FAIL： 转账失败
     *                  CANCELING： 撤销中
     *                  CANCELLED： 已撤销
     */
    void withdrawNotify(String outBillNo, String state, String failReason);

    MkDistributionUser getMkDistributionUserByIdAndShopId(Long shopUserId, Long shopId);
}
