package com.ruoyi.web.modules.trading.service.impl;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.web.modules.trading.domain.BizSupplier;
import com.ruoyi.web.modules.trading.domain.BizSupplierSettlement;
import com.ruoyi.web.modules.trading.domain.BizTradeOrder;
import com.ruoyi.web.modules.trading.domain.BizTradeOrderLine;
import com.ruoyi.web.modules.trading.mapper.BizMarketEntryEarTagMapper;
import com.ruoyi.web.modules.trading.mapper.BizTradeOrderLineMapper;
import com.ruoyi.web.modules.trading.mapper.BizTradeOrderMapper;
import com.ruoyi.web.modules.trading.service.IBizTradeOrderService;
import com.ruoyi.web.modules.trading.support.SettlementOnPayService;
import com.ruoyi.web.modules.trading.support.TradeOrderEarTagResolver;
import com.ruoyi.web.modules.trading.support.TradeOrderNoGenerator;
import com.ruoyi.web.modules.trading.support.TradeOrderRules;
import com.ruoyi.web.modules.trading.support.TradeOrderValidation;

/**
 * 交易订单服务实现。
 */
@Service
public class BizTradeOrderServiceImpl implements IBizTradeOrderService
{
    @Autowired
    private BizTradeOrderMapper bizTradeOrderMapper;

    @Autowired
    private BizTradeOrderLineMapper bizTradeOrderLineMapper;

    @Autowired
    private BizMarketEntryEarTagMapper bizMarketEntryEarTagMapper;

    @Autowired
    private TradeOrderValidation tradeOrderValidation;

    @Autowired
    private TradeOrderEarTagResolver tradeOrderEarTagResolver;

    @Autowired
    private TradeOrderNoGenerator tradeOrderNoGenerator;

    @Autowired
    private SettlementOnPayService settlementOnPayService;

    @Override
    public BizTradeOrder selectBizTradeOrderById(Long id)
    {
        BizTradeOrder row = bizTradeOrderMapper.selectBizTradeOrderById(id);
        enrichOrder(row);
        return row;
    }

    @Override
    public List<BizTradeOrder> selectBizTradeOrderList(BizTradeOrder query)
    {
        List<BizTradeOrder> list = bizTradeOrderMapper.selectBizTradeOrderList(query);
        if (list != null)
        {
            for (BizTradeOrder row : list)
            {
                enrichLineSummary(row);
                if (row != null)
                {
                    row.setOrderStatusName(TradeOrderRules.orderStatusName(row.getOrderStatus()));
                }
            }
        }
        return list;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int insertBizTradeOrder(BizTradeOrder row)
    {
        tradeOrderValidation.prepareAndValidateForSave(row);
        row.setOrderNo(tradeOrderNoGenerator.allocateNextOrderNo());
        row.setOrderStatus(TradeOrderRules.ORDER_STATUS_PENDING);
        row.setDelFlag(TradeOrderRules.DEL_FLAG_NORMAL);
        int rows = bizTradeOrderMapper.insertBizTradeOrder(row);
        saveLines(row);
        return rows;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int updateBizTradeOrder(BizTradeOrder row)
    {
        if (row.getId() == null)
        {
            throw new ServiceException("主键不能为空");
        }
        BizTradeOrder existing = bizTradeOrderMapper.selectBizTradeOrderById(row.getId());
        tradeOrderValidation.assertPendingForUpdate(existing);
        tradeOrderValidation.prepareAndValidateForSave(row);
        row.setDelFlag(TradeOrderRules.DEL_FLAG_NORMAL);
        int rows = bizTradeOrderMapper.updateBizTradeOrder(row);
        if (rows == 0)
        {
            throw new ServiceException(TradeOrderRules.MSG_NOT_FOUND);
        }
        bizTradeOrderLineMapper.deleteLineByOrderId(row.getId());
        saveLines(row);
        return rows;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int deleteBizTradeOrderByIds(Long[] ids, String updateBy)
    {
        if (ids == null || ids.length == 0)
        {
            return 0;
        }
        List<Long> cleaned = new ArrayList<>();
        for (Long id : ids)
        {
            if (id != null)
            {
                cleaned.add(id);
            }
        }
        if (cleaned.isEmpty())
        {
            return 0;
        }
        for (Long id : cleaned)
        {
            BizTradeOrder row = bizTradeOrderMapper.selectBizTradeOrderByIdAny(id);
            if (row == null || TradeOrderRules.DEL_FLAG_DELETED.equals(row.getDelFlag()))
            {
                continue;
            }
            if (TradeOrderRules.ORDER_STATUS_COMPLETED.equals(row.getOrderStatus()))
            {
                throw new ServiceException(TradeOrderRules.MSG_COMPLETED_NO_DELETE);
            }
        }
        return bizTradeOrderMapper.logicDeleteBizTradeOrderByIds(
                cleaned.toArray(new Long[0]), updateBy);
    }

    @Override
    public List<String> selectSupplierEarTags(Long supplierId)
    {
        tradeOrderValidation.assertSupplierActiveForQuery(supplierId);
        return tradeOrderEarTagResolver.listSupplierEarTagOptions(supplierId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public BizTradeOrder completePay(BizTradeOrder payRequest, String operator)
    {
        tradeOrderValidation.validatePayVoucher(payRequest);
        BizTradeOrder order = bizTradeOrderMapper.selectBizTradeOrderById(payRequest.getId());
        if (order == null)
        {
            throw new ServiceException(TradeOrderRules.MSG_NOT_FOUND);
        }
        if (!TradeOrderRules.ORDER_STATUS_PENDING.equals(order.getOrderStatus()))
        {
            throw new ServiceException(TradeOrderRules.MSG_NOT_PENDING);
        }
        enrichOrder(order);
        tradeOrderValidation.validateOrderStillValidForPay(order);
        BizSupplier supplier = tradeOrderValidation.assertSupplierFeeConfigured(order.getSupplierId());

        Date now = new Date();
        order.setOrderStatus(TradeOrderRules.ORDER_STATUS_COMPLETED);
        order.setPayVoucherUrl(payRequest.getPayVoucherUrl());
        order.setPayVoucherPath(payRequest.getPayVoucherPath());
        order.setFinishTime(now);
        order.setUpdateBy(operator);
        order.setUpdateTime(now);
        int updated = bizTradeOrderMapper.updateOrderCompletePay(order);
        if (updated == 0)
        {
            throw new ServiceException(TradeOrderRules.MSG_NOT_PENDING);
        }

        BizSupplierSettlement settlement = settlementOnPayService.createFromOrder(order, supplier, operator);
        releaseMarketEntryEarTags(order);
        order.setSettlementId(settlement.getId());
        order.setSettlementNo(settlement.getSettlementNo());
        order.setOrderStatusName(TradeOrderRules.orderStatusName(order.getOrderStatus()));
        return order;
    }

    /**
     * 完成支付后，从进栏耳标池删除本单已成交耳标（supplier_id + ear_tag）。
     */
    private void releaseMarketEntryEarTags(BizTradeOrder order)
    {
        List<BizTradeOrderLine> lines = order.getLineList();
        if (lines == null || lines.isEmpty())
        {
            lines = bizTradeOrderLineMapper.selectLineListByOrderId(order.getId());
        }
        if (lines == null || lines.isEmpty())
        {
            return;
        }
        Long defaultSupplierId = order.getSupplierId();
        for (BizTradeOrderLine line : lines)
        {
            if (line == null || StringUtils.isEmpty(line.getEarTag()))
            {
                continue;
            }
            Long supplierId = line.getSupplierId() != null ? line.getSupplierId() : defaultSupplierId;
            if (supplierId == null)
            {
                continue;
            }
            bizMarketEntryEarTagMapper.deleteBySupplierIdAndEarTag(supplierId, line.getEarTag().trim());
        }
    }

    private void saveLines(BizTradeOrder row)
    {
        List<BizTradeOrderLine> lines = row.getLineList();
        if (lines == null || lines.isEmpty())
        {
            return;
        }
        for (BizTradeOrderLine line : lines)
        {
            line.setOrderId(row.getId());
            line.setSupplierId(row.getSupplierId());
        }
        bizTradeOrderLineMapper.batchInsertLine(lines);
    }

    private void enrichOrder(BizTradeOrder row)
    {
        if (row == null)
        {
            return;
        }
        row.setOrderStatusName(TradeOrderRules.orderStatusName(row.getOrderStatus()));
        List<BizTradeOrderLine> lines = bizTradeOrderLineMapper.selectLineListByOrderId(row.getId());
        row.setLineList(lines == null ? new ArrayList<>() : lines);
        enrichLineSummary(row);
    }

    private void enrichLineSummary(BizTradeOrder row)
    {
        if (row == null || row.getId() == null)
        {
            return;
        }
        List<BizTradeOrderLine> lines = row.getLineList();
        if (lines == null || lines.isEmpty())
        {
            lines = bizTradeOrderLineMapper.selectLineListByOrderId(row.getId());
            row.setLineList(lines == null ? new ArrayList<>() : lines);
        }
        if (lines.isEmpty())
        {
            return;
        }
        String first = lines.get(0).getEarTag();
        if (StringUtils.isEmpty(first))
        {
            return;
        }
        int n = lines.size();
        if (n <= 1)
        {
            row.setLineSummary(first);
        }
        else
        {
            row.setLineSummary(first + " 等" + n + "头");
        }
    }
}
