package com.ruoyi.job.service.impl;

import com.ruoyi.common.core.utils.DateUtils;
import com.ruoyi.common.core.utils.IdWorker;
import com.ruoyi.common.core.utils.StringUtils;
import com.ruoyi.common.security.utils.SecurityUtils;
import com.ruoyi.invest.domain.AccountsDealRecord;
import com.ruoyi.invest.domain.CreditCardBill;
import com.ruoyi.invest.domain.InstallmentHistory;
import com.ruoyi.invest.domain.InstallmentHistoryDetail;
import com.ruoyi.invest.domain.dto.AccountsDealRecordDto;
import com.ruoyi.invest.domain.dto.BankCardLendDto;
import com.ruoyi.invest.domain.dto.CreditCardBillDto;
import com.ruoyi.invest.domain.dto.InstallmentHistoryDetailDto;
import com.ruoyi.invest.domain.vo.*;
import com.ruoyi.invest.mapper.*;
import com.ruoyi.job.service.IInvestJobService;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.util.*;
import java.util.concurrent.TimeUnit;

/**
 * 生成数据
 *
 * @author tianyongbao
 * @date 2023-12-11
 */
@Service
public class InvestJobImpl implements IInvestJobService
{
    @Resource
    private BankCardLendMapper bankCardLendMapper;
    @Resource
    private AccountsMapper accountsMapper;

    @Resource
    private AccountsDealRecordMapper accountsDealRecordMapper;

    @Resource
    private CreditCardBillMapper creditCardBillMapper;

    @Resource
    private InstallmentHistoryDetailMapper installmentHistoryDetailMapper;
    @Resource
    private InstallmentHistoryMapper installmentHistoryMapper;

    /**
     * 生成数据
     *
     * @author tianyongbao
     * @date 2023-12-11
     */
    @Override
    public void generateUnpaidCreditBill() {
    //未出账单生成，定时任务，每3个小时同步计算一次，作为未出账单，根据信用卡基础信息，包括账单日及账单日消费信息，遍历信用卡记录信息表和交易记录表即可
        BankCardLendDto bankCardLendDto=new BankCardLendDto();
        bankCardLendDto.setType("2");
        List<BankCardLendVo> bankCardVoList=bankCardLendMapper.selectBankCardLendList(bankCardLendDto);
        // 获取当前日期
        LocalDate currentDate = LocalDate.now();
        int month = currentDate.getMonthValue();
        int year = currentDate.getYear();
        int dayOfMonth = currentDate.getDayOfMonth();
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy年MM月账单");
        SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd");
        SimpleDateFormat formatterTime = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date billDate= new Date();
        //遍历数据，获取信用卡账单日及数据
        for (BankCardLendVo bankCard : bankCardVoList) {
            //0表示当期，1表示下期
          String isNextBillDate  = bankCard.getIsNextBillDate();
            String billDateStr=year+"-"+String.format("%02d", month)+"-"+String.format("%02d", bankCard.getBillDate());
            //如果当前日期大于账单日，进入下个账单周期
            if(dayOfMonth>bankCard.getBillDate()){
                 billDateStr=year+"-"+String.format("%02d", month+1)+"-"+String.format("%02d", bankCard.getBillDate());
            }
            try {
                 billDate=formatter.parse(billDateStr);
            } catch (ParseException e) {
                throw new RuntimeException(e);
            }

            Calendar calendarStart = Calendar.getInstance();
            calendarStart.setTime(billDate);
            calendarStart.add(Calendar.MONTH, -1);
            if(isNextBillDate.equals("0")){
                calendarStart.add(Calendar.DATE, 1);
            }
            Date startDate = calendarStart.getTime();
            String periodStart = formatter.format(startDate);

            Calendar calendarEnd = Calendar.getInstance();
            calendarEnd.setTime(billDate);
            if(isNextBillDate.equals("1")){
                calendarEnd.add(Calendar.DATE, -1);
            }
            Date endDate = calendarEnd.getTime();
            String periodEnd= formatter.format(endDate);

            double billAmount=0;
            AccountsDealRecordDto accountsDealRecordDto=new AccountsDealRecordDto();
            accountsDealRecordDto.setAccountId(bankCard.getId());
            try {
                accountsDealRecordDto.setStartDateTime(formatterTime.parse(periodStart+" 00:00:00"));
                accountsDealRecordDto.setEndDateTime(formatterTime.parse(periodEnd+" 23:59:59"));
            } catch (ParseException e) {
                throw new RuntimeException(e);
            }

            accountsDealRecordDto.setCreditBill("6");

            //获取所有交易记录
            List<AccountsDealRecordVo> accountsDealRecordVoList=accountsDealRecordMapper.selectAccountsDealRecordList(accountsDealRecordDto);
            //收入转为负数
            for (AccountsDealRecordVo vo:accountsDealRecordVoList
            ) {
                if(vo.getDealType().equals("1")){
                    vo.setAmount(vo.getAmount()*(-1));
                }
            }
            if(accountsDealRecordVoList.size()>0){
                billAmount=accountsDealRecordVoList.stream().mapToDouble(AccountsDealRecordVo::getAmount).sum();
            }
            CreditCardBillDto creditCardBillDto=new CreditCardBillDto();
            creditCardBillDto.setCreditCardId(bankCard.getId());
            creditCardBillDto.setBillDate(billDateStr);
            creditCardBillDto.setBillState("0");
            List<CreditCardBillVo> creditCardBillList=creditCardBillMapper.selectCreditCardBillList(creditCardBillDto);
            if(creditCardBillList.size()>0){
                CreditCardBillVo creditCardBillVo=creditCardBillList.get(0);
                CreditCardBill creditCardBill=new CreditCardBill();
                creditCardBill.setUpdateBy(SecurityUtils.getUsername());
                creditCardBill.setUpdateTime(DateUtils.getNowDate());
                creditCardBill.setId(creditCardBillVo.getId());
                creditCardBill.setBillAmount(billAmount);
                //如果账单日与当前日期相同,将账单修改为已出账
                if(billDateStr.equals(formatter.format(new Date()))){
                    creditCardBill.setBillState("1");
                }
                //更新未出账单
                creditCardBillMapper.updateCreditCardBill(creditCardBill);
            }else {
                //如果账单日大于当前日期，未出账，进行插入操作
                if(billDateStr.compareTo(formatter.format(new Date()))==1){
                    CreditCardBill creditCardBill=new CreditCardBill();
                    try {
                        creditCardBill.setBillDate(formatter.parse(billDateStr));
                    } catch (ParseException e) {
                        throw new RuntimeException(e);
                    }
                    creditCardBill.setName(simpleDateFormat.format(creditCardBill.getBillDate()));
                    creditCardBill.setBillDatePeriod(periodStart+"~"+periodEnd);
                    creditCardBill.setCreateBy(SecurityUtils.getUsername());
                    creditCardBill.setCreateTime(DateUtils.getNowDate());
                    creditCardBill.setId(IdWorker.getId());
                    creditCardBill.setCreditCardId(bankCard.getId());
                    creditCardBill.setBillAmount(billAmount);
                    creditCardBill.setBillState("0");
                    //插入未出账单
                    creditCardBillMapper.insertCreditCardBill(creditCardBill);
                }
            }

        }
    }

    @Override
    public void  updateUnpaidInstallmentData(){
   //信用卡分期入账信息自动入账，同时更新信用卡额度相关信息
        // 获取当前日期
        Date currentDate = new Date();
        // 创建SimpleDateFormat实例，指定日期格式
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        // 格式化日期为字符串
        String formattedDate = sdf.format(currentDate);
        InstallmentHistoryDetailDto installmentHistoryDetailDto=new InstallmentHistoryDetailDto();
        installmentHistoryDetailDto.setRepaymentEqualDate(formattedDate);
        installmentHistoryDetailDto.setState("0");
        installmentHistoryDetailDto.setType("2");
        List<InstallmentHistoryDetailVo> historyDetailList=installmentHistoryDetailMapper.selectInstallmentHistoryDetailList(installmentHistoryDetailDto);
        //修改名称加卡号
        for (InstallmentHistoryDetailVo installmentHistoryDetail : historyDetailList) {
            installmentHistoryDetail.setPostingState("1");
            InstallmentHistoryDetail detail=new InstallmentHistoryDetail();
            detail.setUpdateBy(SecurityUtils.getUsername());
            detail.setUpdateTime(DateUtils.getNowDate());
            detail.setId(installmentHistoryDetail.getId());
            detail.setPostingState(installmentHistoryDetail.getPostingState());
            installmentHistoryDetailMapper.updateInstallmentHistoryDetail(detail);
                //已入账
                Calendar cal1 = Calendar.getInstance();
                cal1.setTime(installmentHistoryDetail.getRepaymentDate());
                Calendar cal2 = Calendar.getInstance();
                cal2.setTime(new Date());
                long diffInMillis = cal2.getTimeInMillis() - cal1.getTimeInMillis();
                int daysDiff = Long.valueOf(TimeUnit.MILLISECONDS.toDays(diffInMillis)).intValue();
                //入账日期小于一个月的
                if("1".equals(installmentHistoryDetail.getPostingState())&&daysDiff<31){
                    //更新主表已还期数
                    InstallmentHistoryVo historyVo=installmentHistoryMapper.selectInstallmentHistoryById(installmentHistoryDetail.getInstallmentHistoryId());
                    InstallmentHistory his=new InstallmentHistory();
                    his.setRepaidPeriod(historyVo.getRepaidPeriod()+1);
                    his.setId(historyVo.getId());
                    his.setUpdateTime(new Date());
                    installmentHistoryMapper.updateInstallmentHistory(his);
                    //信用卡账户余额计算
                    AccountsVo creditAccount=accountsMapper.selectAccountsById(installmentHistoryDetail.getBankCardLendId());
                    creditAccount.setBalance(creditAccount.getBalance()-installmentHistoryDetail.getInterest());
                    creditAccount.setAvailableLimit(creditAccount.getBalance()+creditAccount.getCreditLimit());
                    creditAccount.setUpdateTime(installmentHistoryDetail.getUpdateTime());
                    accountsMapper.updateAccounts(creditAccount);
                    //工行提前将利息额度占用，不再生成利息支出，一次性生成利息支出即可。
                      if(!creditAccount.getName().contains("工商银行")){
                    //信用卡消费记录明细
                    AccountsDealRecord creditDeal=new AccountsDealRecord();
                    creditDeal.setTransferRecordId(installmentHistoryDetail.getId());
                    creditDeal.setAccountId(creditAccount.getAccountId());
                    creditDeal.setId(IdWorker.getId());
                    //支出金额
                    creditDeal.setAmount(installmentHistoryDetail.getInterest());
                    //实时余额
                    creditDeal.setCurrentBalance(creditAccount.getBalance());
                    //1储蓄卡，2 信用卡，3 网贷，4 人情，5 投资账户
                    creditDeal.setType("2");
                    //1 收入，2 支出，3 转账，4 借贷
                    creditDeal.setDealType("2");
                    //分期利息支出
                    creditDeal.setDealCategory("10");
                    creditDeal.setName(creditAccount.getName()+"（"+ StringUtils.getLastNumberChars(4,creditAccount.getCode()+"）"));
                    creditDeal.setRemark("分期利息");
                    creditDeal.setCreateBy(SecurityUtils.getUsername());
                    creditDeal.setCreateTime(new Date());
//                    accountsDealRecordMapper.insertAccountsDealRecord(creditDeal);
                          insertAccountsDealRecord(creditDeal);
                      }
                    //信用卡消费记录明细，应还本金
                    AccountsDealRecord creditDealPrinciple=new AccountsDealRecord();
                    creditDealPrinciple.setTransferRecordId(installmentHistoryDetail.getId());
                    creditDealPrinciple.setAccountId(creditAccount.getAccountId());
                    creditDealPrinciple.setId(IdWorker.getId());
                    //支出金额
                    creditDealPrinciple.setAmount(installmentHistoryDetail.getPrincipal());
                    //实时余额
                    creditDealPrinciple.setCurrentBalance(creditAccount.getBalance());
                    //1储蓄卡，2 信用卡，3 网贷，4 人情，5 投资账户
                    creditDealPrinciple.setType("2");
                    //1 收入，2 支出，3 转账，4 借贷
                    creditDealPrinciple.setDealType("2");
                    //分期利息支出
                    creditDealPrinciple.setDealCategory("10");
                    creditDealPrinciple.setName(creditAccount.getName()+"（"+ StringUtils.getLastNumberChars(4,creditAccount.getCode()+"）"));
                    creditDealPrinciple.setRemark("应还本金");
                    creditDealPrinciple.setCreateBy(SecurityUtils.getUsername());
                    creditDealPrinciple.setCreateTime(new Date());
//                    accountsDealRecordMapper.insertAccountsDealRecord(creditDealPrinciple);
                    insertAccountsDealRecord(creditDealPrinciple);
                }


        }


    }

    public int insertAccountsDealRecord(AccountsDealRecord accountsDealRecord)
    {
        accountsDealRecord.setCreateBy(SecurityUtils.getUsername());
        accountsDealRecord.setId(IdWorker.getId());

        //获取最新一条记录的数据，计算余额
        Map<String, Object> lastMap = new HashMap<>();
        lastMap.put("startDateTime", accountsDealRecord.getCreateTime());
        lastMap.put("accountId", accountsDealRecord.getAccountId());
        AccountsDealRecord lastOneAccountsDealRecord=accountsDealRecordMapper.getLastOneAccountsDealRecordByMap(lastMap);
        if(lastOneAccountsDealRecord==null){
            lastOneAccountsDealRecord=new AccountsDealRecord();
            lastOneAccountsDealRecord.setCurrentBalance(0d);
        }
        //收入
        if(accountsDealRecord.getDealType().equals("1")){
            Map<String, Object> map = new HashMap<>();
            map.put("startDateTime", accountsDealRecord.getCreateTime());
            map.put("accountId", accountsDealRecord.getAccountId());
            map.put("currentBalance", accountsDealRecord.getAmount());
            accountsDealRecordMapper.batchPlusCurrentBalance(map);
        }
        //支出
        if(accountsDealRecord.getDealType().equals("2")){
            Map<String, Object> map = new HashMap<>();
            map.put("startDateTime", accountsDealRecord.getCreateTime());
            map.put("accountId", accountsDealRecord.getAccountId());
            map.put("currentBalance", accountsDealRecord.getAmount());
            accountsDealRecordMapper.batchMinusCurrentBalance(map);
        }

        return accountsDealRecordMapper.insertAccountsDealRecord(accountsDealRecord);
    }

}
