package cn.cslg.report.service.business;

import cn.cslg.report.common.model.vo.PatentRightVo;
import cn.cslg.report.common.model.vo.PatentVO;
import cn.cslg.report.common.model.vo.PersonnelVO;
import cn.cslg.report.common.utils.CacheUtils;
import cn.cslg.report.common.utils.Response;
import cn.cslg.report.common.utils.SecurityUtils.LoginUtils;
import cn.cslg.report.entity.Features;
import cn.cslg.report.entity.PatentRight;
import cn.cslg.report.entity.Report;
import cn.cslg.report.mapper.FeatureMapper;
import cn.cslg.report.service.OutInterfaceService;
import cn.dev33.satoken.stp.StpUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.io.IOException;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

@Service
@Slf4j
@RequiredArgsConstructor(onConstructor_ = {@Lazy})
public class FeatureService extends ServiceImpl<FeatureMapper, Features> {

    private final OutInterfaceService outInterfaceService;
    private final CacheUtils cacheUtils;
    private final ReportService reportService;
    private final LoginUtils loginUtils;
    private final FeatureMapper featureMapper;

    //对权要进行合并操作
    private List<PatentRight> FormatPatentRights(List<PatentRight> patentRights) {
        List<PatentRight> retList = new ArrayList<>();
        for (int i = 0; i < patentRights.size(); i++) {
            String str = patentRights.get(i).getContent();
            str = str.replace(" ", "");
            Pattern p = Pattern.compile("^[0-9]+\\..*");
            Matcher m = p.matcher(str);
            if (m.matches()) {
                retList.add(patentRights.get(i));
            } else {
                if (retList.size() != 0) {
                    retList.get(retList.size() - 1).setContent(retList.get(retList.size() - 1).getContent() + patentRights.get(i).getContent());
                    retList.get(retList.size() - 1).setContentOut(retList.get(retList.size() - 1).getContentOut() + patentRights.get(i).getContentOut());
                }

            }

        }

        return retList;
    }

    //从PAS系统上获得权要并拆分
    public String splitPatentRight(String patentNo, Integer splitType, Integer splitBy, Integer reportId) throws IOException {
        PersonnelVO personnelVO = cacheUtils.getLoginUser(StpUtil.getLoginIdAsInt());
        LambdaQueryWrapper<Report> queryWrapper = new LambdaQueryWrapper();
        queryWrapper.eq(Report::getId, reportId);
        Report report = reportService.list(queryWrapper).get(0);
        Integer flag = 0;
        if(splitBy==null){
            splitBy=0;
        }
        if(splitType==null){
            splitType=0;
        }
        if (report.getSplitBy() == null || report.getSplitType() == null || report.getSplitBy() != splitBy || report.getSplitType() != splitType) {
            report.setSplitBy(splitBy);
            report.setSplitType(splitType);
            report.updateById();
            flag = 1;
        }
        //权要（带拆分的特征）列表
        List<PatentRightVo> patentRightVos = new ArrayList<>();
        //从pas获得权要信息
        String resBody = outInterfaceService.getPatentRightFromPAS(patentNo);
        JSONObject jsonObject = JSONObject.parseObject(resBody);
        //解析jason获得标的专利的权要
        List<PatentRight> patentRightsOrgin = JSON.parseArray(jsonObject.getString("data"), PatentRight.class);
        List<PatentRight> patentRights = FormatPatentRights(patentRightsOrgin);
        List<Integer> partRightIds = new ArrayList<>();
        List<String> flags = new ArrayList<>();
        // 当splitType=0仅拆解主权要
        if (splitType == 0) {
            partRightIds = patentRights.stream().filter(item -> item.getType() == 1).map(PatentRight::getId).collect(Collectors.toList());
        }// 当splitType=1拆解全部权要
        else if (splitType == 1) {
            partRightIds = patentRights.stream().map(PatentRight::getId).collect(Collectors.toList());
        }
        //当splitBy=0时仅仅根据“,”拆解
        if (splitBy == 0) {
            flags.add(",");
            flags.add("，");
        }
        //当splitBy=1时仅仅根据“;“拆解
        else if (splitBy == 1) {
            flags.add(";");
            flags.add("；");
        }//当splitBy=2时根据“;“和”,”拆解
        else if (splitBy == 2) {
            flags.add(";");
            flags.add("；");
            flags.add(",");
            flags.add("，");
        }
        Features featureTO = new Features();
        featureTO.setReportId(reportId);
        featureTO.setSignPatentNo(patentNo);
        //featureTO.setPartnerId();
        //查询数据库里是否有查询记录
        List<Features> featureFromDb = this.queryFeatures(featureTO);
        LambdaQueryWrapper<Features> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Features::getReportId, reportId)
                .eq(Features::getSignPatentNo, patentNo)
                .eq(Features::getPartnerId, personnelVO.getId())
                .ne(Features::getSplitBy,splitBy);
        if(splitType==1)
        {wrapper.ne(Features::getSplitBy,-1);}
        this.remove(wrapper);


        //将拆解的权要和特征装载到对象PatentRightVo
        for (int i = 0; i < patentRights.size(); i++) {
            //特征序号
            Integer order =1;
            List<Features> featuresList = new ArrayList<>();
            String[] tems= patentRights.get(i).getContent().split("\\.");
            String name ="权要"+tems[0].replace(" ","");
            int rightId = patentRights.get(i).getId();
            //对需要拆解的权要进行拆解
            Integer a=splitBy;
            if (partRightIds.contains(patentRights.get(i).getId())) {

                if (featureFromDb != null && featureFromDb.size() != 0) {
                    featuresList = featureFromDb.stream().filter(item -> item.getRightId() == rightId && item.getSplitBy() .equals(a)  &&item.getPartnerId()==personnelVO.getId()).collect(Collectors.toList());
                }
                //如果数据库里无拆解记录则手动插入一条
                if (featuresList == null || featuresList.size() == 0 || flag == 1) {
                    featuresList = new ArrayList<>();
                    //获得权要的译文并且拆解
                    List<String> contentOuts = this.splitStringByFlags(patentRights.get(i).getContentOut(), flags);
                    //获得权要的原文并且拆解
                    List<String> contents = this.splitStringByFlags(patentRights.get(i).getContent(), flags);
                    //遍历拆解出来的内容并装载到features最后存入列表
                    for (int t = 0; t < contents.size(); t++) {
                        Features features = new Features();
                        features.setRightId(patentRights.get(i).getId());
                        features.setIsFinal(0);
                        features.setSignPatentNo(patentNo);
                        features.setReportId(reportId);
                        String countOut = contentOuts.size() - 1 >= t ? contentOuts.get(t) : "";
                        features.setContentOut(countOut);
                        features.setContent(contents.get(t));
                        features.setSplitBy(splitBy);
                        features.setPartnerId(personnelVO.getId());
                        features.setRightName(name);
                        features.setFeaturesOrder(order);
                        features.setRightType(patentRights.get(i).getType());
                        featuresList.add(features);
                        order+=1;
                    }
                    this.saveBatch(featuresList);
                }
            }
            else{
                featuresList = featureFromDb.stream().filter(item -> item.getRightId() == rightId && item.getSplitBy() == -1 &&item.getPartnerId()==personnelVO.getId()).collect(Collectors.toList());
                if (featuresList == null || featuresList.size() == 0 || flag == 1) {
                        Features features = new Features();
                        features.setRightId(patentRights.get(i).getId());
                        features.setIsFinal(0);
                        features.setSignPatentNo(patentNo);
                        features.setReportId(reportId);
                        features.setContentOut(patentRights.get(i).getContentOut());
                        features.setContent(patentRights.get(i).getContent());
                        features.setSplitBy(-1);
                        features.setPartnerId(personnelVO.getId());
                        features.setRightName(name);
                        features.setFeaturesOrder(1);
                        features.insert();
                    featuresList.add(features);
                }
            }

            //装载到对象PatentRightVo
            PatentRightVo patentRightVo = new PatentRightVo();
            patentRightVo.setPatentId(patentRights.get(i).getPatentId());
            patentRightVo.setFeatures(featuresList);
            patentRightVo.setContent(patentRights.get(i).getContent());
            patentRightVo.setSort(patentRights.get(i).getSort());
            patentRightVo.setType(patentRights.get(i).getType());
            patentRightVo.setContentOut(patentRights.get(i).getContentOut());
            patentRightVo.setReportId(reportId);
            patentRightVo.setRightName(name);
            patentRightVo.setSignPatentNo(patentNo);
            patentRightVos.add(patentRightVo);
        }
        Map<String, Object> map = new HashMap<String, Object>();
        map.put("patentRightVos", patentRightVos);
        map.put("splitBy", report.getSplitBy());
        map.put("splitType", report.getSplitType());
        return Response.success(map);

    }

    public String getFeatures(String patentNo, Integer reportId) throws IOException {
        LambdaQueryWrapper<Report> queryWrapper = new LambdaQueryWrapper();
        queryWrapper.eq(Report::getId, reportId);
        Report report = reportService.list(queryWrapper).get(0);
        //权要（带拆分的特征）列表
        List<PatentRightVo> patentRightVos = new ArrayList<>();
        //从pas获得权要信息
        String resBody = outInterfaceService.getPatentRightFromPAS(patentNo);
        JSONObject jsonObject = JSONObject.parseObject(resBody);
        //解析jason获得标的专利的权要
        List<PatentRight> patentRightsOrgin = JSON.parseArray(jsonObject.getString("data"), PatentRight.class);
        //处理权要
        List<PatentRight> patentRights = FormatPatentRights(patentRightsOrgin);
     Features featureTO = new Features();
        featureTO.setReportId(reportId);
        featureTO.setSignPatentNo(patentNo);
        //查询数据库里是否有查询记录
        List<Features> featureFromDb = this.queryFeatures(featureTO);
        //将拆解的权要和特征装载到对象PatentRightVo
        for (int i = 0; i < patentRights.size(); i++) {

            List<Features> featuresList = new ArrayList<>();
            //对需要拆解的权要进行拆解
                if (featureFromDb != null && featureFromDb.size() != 0) {
                    int rightId = patentRights.get(i).getId();
                    featuresList = featureFromDb.stream().filter(item -> item.getRightId() == rightId &&item.getPartnerId()==report.getPersonId()).collect(Collectors.toList());
                }

            //装载到对象PatentRightVo
            PatentRightVo patentRightVo = new PatentRightVo();

            String name = "权要" + (i + 1);
            patentRightVo.setPatentId(patentRights.get(i).getPatentId());
            patentRightVo.setFeatures(featuresList);
            patentRightVo.setContent(patentRights.get(i).getContent());
            patentRightVo.setSort(patentRights.get(i).getSort());
            patentRightVo.setType(patentRights.get(i).getType());
            patentRightVo.setContentOut(patentRights.get(i).getContentOut());
            patentRightVo.setReportId(reportId);
            patentRightVo.setRightName(name);
            patentRightVo.setSignPatentNo(patentNo);
            patentRightVos.add(patentRightVo);
        }
        Map<String, Object> map = new HashMap<String, Object>();
        map.put("patentRightVos", patentRightVos);
        map.put("splitBy", report.getSplitBy());
        map.put("splitType", report.getSplitType());
        return Response.success(map);

    }

    //根据符号拆分字符串
    public List<String> splitStringByFlags(String sentence, List<String> flags) {
        List<String> sectences = new ArrayList<>();
//如果字符串为空则返回一个包含空字符串的list
        if (sentence == null) {
            sectences.add("");
            return sectences;
        }
        sectences.add(sentence);
        for (int i = 0; i < flags.size(); i++) {
            List<String> tem = new ArrayList<>();
            for (int t = 0; t < sectences.size(); t++) {
                tem.addAll(Arrays.asList(sectences.get(t).split(flags.get(i))));
            }
            sectences = tem;

        }
        return sectences;

    }

    /**
     * @author lrj
     * @deprecated 查询特征
     */
    public List<Features> queryFeatures(Features features) {
        List<Features> featureList = new ArrayList<>();
        LambdaQueryWrapper<Features> lambdaQueryWrapper = new LambdaQueryWrapper();
        if (features.getRightId() != null) {
            lambdaQueryWrapper.eq(Features::getRightId, features.getRightId());
        }
        if (features.getIsFinal() != null) {
            lambdaQueryWrapper.eq(Features::getIsFinal, features.getIsFinal());
        }
        if (features.getPartnerId() != null) {
            lambdaQueryWrapper.eq(Features::getPartnerId, features.getPartnerId());
        }
        if (features.getSignPatentNo() != null) {
            lambdaQueryWrapper.eq(Features::getSignPatentNo, features.getSignPatentNo());
        }
        if (features.getReportId() != null) {
            lambdaQueryWrapper.eq(Features::getReportId, features.getReportId());
        }
        featureList = this.list(lambdaQueryWrapper);
        return featureList;
    }

    /**
     * @author 沈永艺
     * @deprecated 保存特征
     */
    @Transactional(rollbackFor = Exception.class)
    public String addFeatures(List<PatentRightVo> patentRightVos) {
        PersonnelVO personnelVO = cacheUtils.getLoginUser(StpUtil.getLoginIdAsInt());
        LambdaQueryWrapper<Features> wrapper = new LambdaQueryWrapper<>();
        if (patentRightVos.get(0).getReportId() != null && patentRightVos.get(0).getSignPatentNo() != null) {

            wrapper.eq(Features::getReportId, patentRightVos.get(0).getReportId())
                    .eq(Features::getSignPatentNo, patentRightVos.get(0).getSignPatentNo())
                    .eq(Features::getPartnerId, personnelVO.getId());
            this.remove(wrapper);
        }
        List<Features> features = new ArrayList<>();
        for (int i = 0; i < patentRightVos.size(); i++) {
             int order=1;
            PatentRightVo patentRightVo = patentRightVos.get(i);
            if (patentRightVo.getFeatures() != null && patentRightVo.getFeatures().size() != 0) {
                List<Features> tem =patentRightVo.getFeatures();
                for (int t = 0; t < tem.size(); t++) {
                    tem.get(t).setPartnerId(personnelVO.getId());
                    tem.get(t).setFeaturesOrder(order);
                    order+=1;
                    features.add(tem.get(t));
                }
            }
        }

        this.saveBatch(features);
        return Response.success();
    }

    public String querySimFeaturePatent(PatentVO patentVO) throws IOException {
        //获得当前用户信息
       PersonnelVO personnelVO = cacheUtils.getLoginUser(loginUtils.getId());
        //根据报告Id,拆分人Id,标的专利号获得特征。
        LambdaQueryWrapper<Features> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(Features::getReportId, patentVO.getReportId())
             .eq(Features::getPartnerId, personnelVO.getId());
        List<Features> features = this.list(queryWrapper);
        LambdaQueryWrapper<Report> lambdaQueryWrapper =new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(Report::getId,patentVO.getReportId());
        List<Report> reports =reportService.list(lambdaQueryWrapper);
        List<String> signPatentNos =reports.stream().map(Report::getSignPatentNo).collect(Collectors.toList());
        //获得特征内容
        List<String> contents = features.stream().map(Features::getContent).collect(Collectors.toList());
        List<String> patentNos = featureMapper.getSignPatentNo(contents);
        patentNos.removeAll(signPatentNos);
        if(patentNos.size()==0)
        {return Response.success();}

        patentVO.setPatentNos(patentNos);
      String res=  outInterfaceService.getPatentFromPAS(patentVO,1);
        return res;


    }
    public Features select(int id){
        LambdaQueryWrapper<Features> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(Features::getId,id);
        if(this.list(queryWrapper).size()==0){
            return null;
        }
        return this.list(queryWrapper).get(0);
    }



}
