package com.jeesharp.business.modules.mall.application;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.jeesharp.business.modules.mall.convert.MallMemberAddressConvert;
import com.jeesharp.business.modules.mall.dto.MallMemberAddressSaveDTO;
import com.jeesharp.business.modules.mall.entity.MallMemberAddress;
import com.jeesharp.business.modules.mall.service.MallMemberAddressService;
import com.jeesharp.business.modules.mall.vo.MallMemberAddressInfoVO;
import com.jeesharp.business.modules.mall.vo.MallMemberAddressListVO;
import com.jeesharp.business.modules.mall.vo.MallMemberAddressQueryVO;
import com.jeesharp.business.modules.member.service.MemberService;
import com.jeesharp.framework.exception.BizErrorException;
import com.jeesharp.framework.pojo.Page;
import com.jeesharp.framework.pojo.query.PageRespVO;
import lombok.AllArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Collections;
import java.util.List;

/**
 * 会员地址 Application Service：编排地址领域服务与会员展示补全。
 *
 * @author jeesharp
 * @since 2026-02-05
 */
@Service
@AllArgsConstructor
@Transactional(readOnly = true)
public class MallMemberAddressApplicationService {

    private final MallMemberAddressService mallMemberAddressService;
    private final MemberService memberService;

    public MallMemberAddressInfoVO get(String id) {
        MallMemberAddressInfoVO vo = MallMemberAddressConvert.INSTANCE.toInfoVO(mallMemberAddressService.get(id));
        memberService.enrichMemberDisplay(vo);
        return vo;
    }

    public PageRespVO<MallMemberAddressListVO> findPage(Page<MallMemberAddress> page, MallMemberAddressQueryVO query) {
        MallMemberAddressQueryVO prepared = prepareQuery(query);
        if (prepared == null) {
            return emptyPage(page);
        }
        Page<MallMemberAddress> result = mallMemberAddressService.findPage(page, prepared);
        PageRespVO<MallMemberAddressListVO> pageVo = MallMemberAddressConvert.INSTANCE.toPageRespVO(result);
        memberService.enrichMemberDisplay(pageVo.getRecords());
        return pageVo;
    }

    @Transactional(readOnly = false)
    public void save(MallMemberAddressSaveDTO dto) {
        saveReturningId(dto);
    }

    /**
     * 保存地址并返回主键（新增后由持久化回填 id）。
     */
    @Transactional(readOnly = false)
    public String saveReturningId(MallMemberAddressSaveDTO dto) {
        MallMemberAddress entity = MallMemberAddressConvert.INSTANCE.toEntity(dto);
        if (StrUtil.isBlank(dto.getId())) {
            mallMemberAddressService.createAddress(entity);
            return StrUtil.blankToDefault(entity.getId(), "");
        }
        mallMemberAddressService.updateAddress(entity);
        return StrUtil.blankToDefault(dto.getId(), "");
    }

    @Transactional(readOnly = false)
    public void delete(String ids) {
        mallMemberAddressService.batchDelete(StrUtil.splitTrim(ids, ','));
    }

    /**
     * 获取会员的地址列表
     */
    public List<MallMemberAddress> getMemberAddresses(String memberId) {
        return mallMemberAddressService.getMemberAddresses(memberId);
    }

    /**
     * 获取会员的默认地址
     */
    public MallMemberAddress getDefaultAddress(String memberId) {
        return mallMemberAddressService.getDefaultAddress(memberId);
    }

    /**
     * 获取下单使用的会员地址，并校验地址归属。
     */
    public MallMemberAddress getMemberAddressForOrder(String memberId, String addressId) {
        if (StrUtil.isBlank(memberId)) {
            throw new BizErrorException("会员ID不能为空");
        }
        if (StrUtil.isBlank(addressId)) {
            throw new BizErrorException("配送地址不能为空");
        }
        MallMemberAddress address = mallMemberAddressService.get(addressId);
        if (address == null || !StrUtil.equals(memberId, address.getMemberId()) || !"0".equals(address.getDelFlag())) {
            throw new BizErrorException("配送地址不存在");
        }
        return address;
    }

    /**
     * 设置默认地址
     */
    @Transactional(readOnly = false)
    public void setDefaultAddress(String addressId, String memberId) {
        mallMemberAddressService.setDefaultAddress(addressId, memberId);
    }

    /**
     * 取消默认地址
     */
    @Transactional(readOnly = false)
    public void cancelDefaultAddress(String memberId) {
        mallMemberAddressService.cancelDefaultAddress(memberId);
    }

    /**
     * 获取完整的地址字符串
     */
    public String getFullAddress(MallMemberAddress address) {
        return mallMemberAddressService.getFullAddress(address);
    }

    /**
     * 会员关键词 → memberIdIn 筛选条件（编排，不含会员数据组装）。
     */
    private MallMemberAddressQueryVO prepareQuery(MallMemberAddressQueryVO query) {
        MallMemberAddressQueryVO q = query != null ? query : new MallMemberAddressQueryVO();
        if (StrUtil.isBlank(q.getMemberKeyword())) {
            return q;
        }
        List<String> memberIds = memberService.findIdsByKeyword(q.getMemberKeyword().trim());
        q.setMemberKeyword(null);
        if (CollUtil.isEmpty(memberIds)) {
            return null;
        }
        q.setMemberIdIn(memberIds);
        return q;
    }

    private PageRespVO<MallMemberAddressListVO> emptyPage(Page<MallMemberAddress> page) {
        PageRespVO<MallMemberAddressListVO> empty = new PageRespVO<>();
        empty.setRecords(Collections.emptyList());
        empty.setTotal(0L);
        empty.setPageNo(page.getPageNo());
        empty.setPageSize(page.getPageSize());
        empty.setPages(0L);
        return empty;
    }
}
