package com.mvc.service.iotcard;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.TypeReference;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.mvc.dao.TIotcardInfoMapper;
import com.mvc.entity.TIotcardInfo;
import com.mvc.entity.TIotcardInfoExample;
import com.mvc.model.ResPageModel;
import com.mvc.model.TAireadModel;
import com.mvc.model.iotcard.*;
import com.mvc.service.copy.TAireadService;
import com.mvc.service.taizhang.StationAccService;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.http.*;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

import javax.annotation.Resource;
import java.util.*;

/**
 * 物联网卡服务
 */
@Service
public class IotCardService {
    private static Logger log = LoggerFactory.getLogger(IotCardService.class);

    //分页获取账户下所有卡信息
    private static final String API_QUERYCARDINFOALL = "https://icmp.shingsou.com/open/queryCardInfoAll";

    //通过接入号/ICCID获取单卡信息
    private static final String API_QUERYOPENCARDINFOSINGLE = "https://icmp.shingsou.com/open/queryOpenCardInfoSingle";

    //通过接入号/ICCID批量获取卡信息
    private static final String API_QUERYOPENCARDINFOBULK = "https://icmp.shingsou.com/open/queryOpenCardInfoBulk";

    //通过接入号/ICCID单卡停复机
    private static final String API_UPDATECARDSTATUSSINGLE = "https://icmp.shingsou.com/open/updateCardStatusSingle";

    //通过接入号/ICCID查询停机原因
    private static final String API_QUERYSTOPREASON = "https://icmp.shingsou.com/open/queryStopReason";

    //下面两项从其平台(物联网卡管理平台)中获取
    private static final String AUTH_AGENCYCODE = "wIxOJ069fB8vMZJ3";
    private static final String AUTH_KEY = "LvdBJmiip";
    private static final Integer PAGE_SIZE = 1000;//获取列表时每页的条数(不可改的)
    private static boolean mIsUpdating = false;//防止更新中又调用更新

    @Resource
    private RestTemplate restTemplate;

    @Resource
    private TIotcardInfoMapper iotcardInfoMapper;

    @Resource
    private TAireadService aireadService;

    @Resource
    private StationAccService stationAccService;

    @Resource
    private IotCardShzyService iotCardShzyService;//上海秩易接口处理  2024-09-03 guozhao

    public ResPageModel findAllTIotcardInfo(TIotcardInfoModel queryModel) {
        TIotcardInfoExample example = new TIotcardInfoExample();
        TIotcardInfoExample.Criteria criteria = example.createCriteria();
        if (StringUtils.isNotEmpty(queryModel.getDeviceSn())) {
            criteria.andDeviceSnEqualTo(queryModel.getDeviceSn());
            /*TAireadModel aireadModel = aireadService.findLatestTAireadByDeviceSn(queryModel.getDeviceSn());
            if (aireadModel != null && StringUtils.isNotEmpty(aireadModel.getCcid())) {
                criteria.andIccidEqualTo(aireadModel.getCcid());
            } else {
                criteria.andIdEqualTo(0);
            }*/
        } else if (StringUtils.isNotEmpty(queryModel.getStationCode())) {
            TAireadModel aireadModel = aireadService.findLatesTAireadByStationCode(queryModel.getStationCode());
            if (aireadModel != null && StringUtils.isNotEmpty(aireadModel.getCcid())) {
                criteria.andIccidEqualTo(aireadModel.getCcid());
            } else {
                criteria.andIdEqualTo(0);
            }
        }
        if (queryModel.getAireadId() != null) {
            criteria.andAireadIdEqualTo(queryModel.getAireadId());
        }
        if (StringUtils.isNotEmpty(queryModel.getMsisdn())) {
            criteria.andMsisdnEqualTo(queryModel.getMsisdn());
        }
        if (StringUtils.isNotEmpty(queryModel.getIccid())) {
            criteria.andIccidEqualTo(queryModel.getIccid());
        }
        if (StringUtils.isNotEmpty(queryModel.getImsi())) {
            criteria.andImsiEqualTo(queryModel.getImsi());
        }
        if (StringUtils.isNotEmpty(queryModel.getOperator())) {
            criteria.andOperatorEqualTo(queryModel.getOperator());
        }
        if (StringUtils.isNotEmpty(queryModel.getWorkingcondition())) {
            criteria.andWorkingconditionEqualTo(queryModel.getWorkingcondition());
        }
        if (queryModel.getRemaingprs() != null) {
            criteria.andRemaingprsLessThanOrEqualTo(queryModel.getRemaingprs());
        }
        if (StringUtils.isNotEmpty(queryModel.getDuedate())) {
            criteria.andDuedateLessThanOrEqualTo(queryModel.getDuedate());
        }
        if (queryModel.getArrearage() != null) {
            criteria.andArrearageEqualTo(queryModel.getArrearage());
        }

        example.setOrderByClause("CREATE_TIME desc");

        Page<Object> pageObject = PageHelper.startPage(queryModel.getPageNum(), queryModel.getPageSize());
        List<TIotcardInfoModel> resList = selectByExample(example);
        ResPageModel pageModel = new ResPageModel(resList, pageObject);
        return pageModel;
    }

    /**
     * 根据Example查询数据列表
     *
     * @param example
     * @return
     */
    private List<TIotcardInfoModel> selectByExample(TIotcardInfoExample example) {
        List<TIotcardInfo> iotcardInfos = iotcardInfoMapper.selectByExample(example);
        List<TIotcardInfoModel> resList = new ArrayList<>();
        for (TIotcardInfo TMaintenanceRecords : iotcardInfos) {
            TIotcardInfoModel model = new TIotcardInfoModel();
            BeanUtils.copyProperties(TMaintenanceRecords, model);
            resList.add(model);
        }
        return resList;
    }

    /**
     * 根据CCID获取单卡信息(从第三方API)
     *
     * @param ccid
     * @return
     */
    public TIotcardInfoModel queryCardInfoByCCID(String ccid) {
        QuerySingleParamModel paramModel = new QuerySingleParamModel(ccid, AUTH_AGENCYCODE, AUTH_KEY);
        String json = postInParam(API_QUERYOPENCARDINFOSINGLE, paramModel);
        if (StringUtils.isNotEmpty(json)) {
            IotCardResult<TIotcardInfoModel> result = JSON.parseObject(json, new TypeReference<>() {
            });
            return result.getInfo();
        }

        return null;
    }

    /**
     * 根据CCID获取单卡信息(本地数据库)
     *
     * @param ccid
     * @return
     */
    public TIotcardInfoModel queryLocalCardInfoByCCID(String ccid) {
        if (StringUtils.isEmpty(ccid)) return null;
        TIotcardInfoExample example = new TIotcardInfoExample();
        TIotcardInfoExample.Criteria criteria = example.createCriteria();
        criteria.andIccidEqualTo(ccid);
        List<TIotcardInfoModel> list = selectByExample(example);
        return list == null || list.size() == 0 ? null : list.get(0);
    }

    /**
     * 根据CCID的采样时间获取数据
     *
     * @param ccid
     * @param sampleTime
     * @return
     */
    public Map<Integer, TIotcardInfoModel> findIotcardInfoModelsByCcid(String ccid, Date sampleTime) {
        TIotcardInfoExample example = new TIotcardInfoExample();
        TIotcardInfoExample.Criteria criteria = example.createCriteria();
        criteria.andIccidEqualTo(ccid);
        if (sampleTime != null) {
            criteria.andCreateTimeGreaterThanOrEqualTo(sampleTime);
        }

        return getIotcardInfoModelMapByExample(example);
    }

    /**
     * 根据TAiread表主键获取TIotcardInfoModel Map
     *
     * @param aiReadKeys
     * @return
     */
    public Map<Integer, TIotcardInfoModel> findIotcardInfoModelMapByAiReadKeys(List<Integer> aiReadKeys) {
        if (aiReadKeys == null || aiReadKeys.size() == 0) return null;
        TIotcardInfoExample example = new TIotcardInfoExample();
        TIotcardInfoExample.Criteria criteria = example.createCriteria();
        criteria.andAireadIdIn(aiReadKeys);

        return getIotcardInfoModelMapByExample(example);
    }


    private Map<Integer, TIotcardInfoModel> getIotcardInfoModelMapByExample(TIotcardInfoExample example) {
        Map<Integer, TIotcardInfoModel> map = new HashMap<>();
        List<TIotcardInfo> iotcardInfos = iotcardInfoMapper.selectByExample(example);

        for (TIotcardInfo TMaintenanceRecords : iotcardInfos) {
            TIotcardInfoModel model = new TIotcardInfoModel();
            BeanUtils.copyProperties(TMaintenanceRecords, model);
            if(!map.containsKey(model.getAireadId())){
                map.put(model.getAireadId(), model);
            }
        }

        return map;
    }

    /**
     * 根据AireadId获取对应卡信息
     *
     * @param aireadId
     * @return
     */
    public TIotcardInfoModel queryLocalCardInfoByAiReadId(int aireadId) {
        TIotcardInfoExample example = new TIotcardInfoExample();
        TIotcardInfoExample.Criteria criteria = example.createCriteria();
        criteria.andAireadIdEqualTo(aireadId);
        List<TIotcardInfoModel> list = selectByExample(example);
        return list == null || list.size() == 0 ? null : list.get(0);
    }

    /**
     * 根据TAiread获取流量信息,并保存记录
     *
     * @param aireadModel
     * @return
     */
    @Async
    public TIotcardInfoModel saveCardInfoByAiReadModel(TAireadModel aireadModel) {
        if (aireadModel == null || StringUtils.isEmpty(aireadModel.getCcid())) return null;
        TIotcardInfoModel model = queryCardInfoByCCID(aireadModel.getCcid());
        if(model == null){//如果第一批卡的接口没有数据，则从上海秩易尝试获取一次 2024-09-03 guozhao
            model = iotCardShzyService.queryCardInfoByCCID(aireadModel.getCcid());
        }
        if (model != null) {
            model.setSampleTime(aireadModel.getSampleTime());
            model.setDeviceSn(aireadModel.getDeviceSn());
            model.setAireadId(aireadModel.getId());
            stationAccService.updateIotCardInfo(aireadModel.getStationCode(), model);
            return saveTIotcardInfo(model);
        }

        return null;
    }

    /**
     * 从卡平台获取所有卡的信息
     *
     * @return
     */
    @Async
    public void updateAllCardInfo() {
        System.out.println(new Date());

        if (mIsUpdating) {
            System.out.println("当前已经有更新任务正在执行中...");
            return;
        }
        mIsUpdating = true;
        deleteAllTIotcardInfo();
        QueryAllParamModel paramModel = new QueryAllParamModel(1, AUTH_AGENCYCODE, AUTH_KEY, 0);//欠费的第一页

        int pages = 100;//未查询前不知道多少页
        //1.获取已欠费的卡
        List<TIotcardInfo> list = new ArrayList<>();
        for (int i = 1; i <= pages; i++) {
            paramModel.setPage(String.valueOf(i));
            String json = postInParam(API_QUERYCARDINFOALL, paramModel);
            if (StringUtils.isNotEmpty(json)) {
                //TIotcardInfo与返回值json的大小写并不匹配,但不影响转换
                IotCardListResult<TIotcardInfo> result = JSON.parseObject(json, new TypeReference<>() {
                });
                if (i == 1) {//重新计算总页数
                    pages = getActualPages(result.getCount());
                }
                if (result.getInfoList() != null && result.getInfoList().size() > 0) {
                    list.addAll(result.getInfoList());
                }
            } else {
                break;
            }
        }

        //已停机的入库
        for (TIotcardInfo iotcardInfo : list) {
            iotcardInfo.setArrearage(0);
            saveTIotcardInfo(iotcardInfo);
        }

        list.clear();
        //2.获取未欠费的卡
        pages = 100;
        paramModel.setIsArrearage(1);
        for (int i = 1; i <= pages; i++) {
            paramModel.setPage(String.valueOf(i));
            String json = postInParam(API_QUERYCARDINFOALL, paramModel);
            if (StringUtils.isNotEmpty(json)) {
                IotCardListResult<TIotcardInfo> result = JSON.parseObject(json, new TypeReference<>() {
                });
                if (i == 1) {
                    pages = getActualPages(result.getCount());
                }
                if (result.getInfoList() != null && result.getInfoList().size() > 0) {
                    list.addAll(result.getInfoList());
                }
            } else {
                break;
            }
        }

        //未停机的入库
        for (TIotcardInfo iotcardInfo : list) {
            iotcardInfo.setArrearage(1);
            saveTIotcardInfo(iotcardInfo);
        }

        //刷新一下站点台账表中记录的信息
        stationAccService.updateIotCardInfo();
        mIsUpdating = false;
        System.out.println(new Date());
    }

    //获取实际页数
    private int getActualPages(int count) {
        int pages = count / PAGE_SIZE;
        if (count % PAGE_SIZE != 0) {
            pages++;
        }
        return pages;
    }

    //保存记录到数据库
    public TIotcardInfo saveTIotcardInfo(TIotcardInfo iotcardInfo) {
        iotcardInfo.setCreateTime(new Date());
        iotcardInfoMapper.insert(iotcardInfo);
        return iotcardInfo;
    }

    //保存记录到数据库
    public TIotcardInfoModel saveTIotcardInfo(TIotcardInfoModel model) {
        model.setCreateTime(new Date());
        TIotcardInfo iotcardInfo = new TIotcardInfo();
        BeanUtils.copyProperties(model, iotcardInfo);
        iotcardInfoMapper.insert(iotcardInfo);
        model.setId(iotcardInfo.getId());
        return model;
    }

    /**
     * 清空所有记录
     */
    public void deleteAllTIotcardInfo() {
        TIotcardInfoExample example = new TIotcardInfoExample();
        TIotcardInfoExample.Criteria criteria = example.createCriteria();
        criteria.andIdGreaterThan(0);
        iotcardInfoMapper.deleteByExample(example);
    }

    private String postInParam(String url, Object model) {
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        String json = JSON.toJSONString(model);
        try {
            HttpEntity<String> entity = new HttpEntity<>(json, headers);
            ResponseEntity<String> response = restTemplate.postForEntity(url, entity, String.class);

            if (response.getStatusCode() == HttpStatus.OK) {
                return response.getBody();
            } else {
                log.error("获取物联网卡信息异常1");
                log.error(response.getBody());
            }
        } catch (Exception ex) {
            log.error("获取物联网卡信息异常2");
            log.error(ex.getMessage());
            ex.printStackTrace();
        }
        return null;
    }
}
