package org.diagbot.push.controller;

import io.swagger.models.auth.In;
import org.diagbot.common.work.*;
import org.diagbot.pub.api.Response;
import org.diagbot.pub.utils.PropertiesUtil;
import org.diagbot.pub.utils.http.HttpApi;
import org.diagbot.pub.web.BaseController;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;

import javax.servlet.http.HttpServletRequest;
import java.util.*;

/**
 * @ClassName org.diagbot.push.controller.AlgorithmController
 * @Description TODO
 * @Author fyeman
 * @Date 2019/1/16/016 19:00
 * @Version 1.0
 **/
@Controller
@RequestMapping("/algorithm")
public class AlgorithmController extends BaseController {
    {
        listView = "/pages/algorithm/list.html";
    }

    @RequestMapping({"/index"})
    public String index() {
        return listView;
    }

    @RequestMapping(value = "/page_neural")
    @ResponseBody
    public Response<ResponseData> neuralData(HttpServletRequest request, SearchData searchData) throws Exception {
        return algorithm(request, searchData);
    }

    @RequestMapping(value = "/neural", method = RequestMethod.POST)
    @ResponseBody
    public Response<ResponseData> bayesPageData(HttpServletRequest request, @RequestBody SearchData searchData) throws Exception {
        return algorithm(request, searchData);
    }

    public Response<ResponseData> algorithm(HttpServletRequest request, SearchData searchData) throws Exception {
        Response<ResponseData> response = new Response();

        PropertiesUtil propertiesUtil = new PropertiesUtil("push.properties");
        //大数据推送
        HttpApi<Response> api = new HttpApi<Response>();
        // 根据hospitalCode从his获取所有疾病库信息
        Response bigDataResponse = api.doPost(propertiesUtil.getProperty("bigdata.http.url"), searchData,
                Response.class);
        LinkedHashMap bigDataLinkedHashMap = (LinkedHashMap) bigDataResponse.getData();
        //转FeatureRate对象
        ResponseData bigDataResponseData = map2ResponseData(bigDataLinkedHashMap);
        //入参信息
        bigDataResponseData = addInputs(bigDataResponseData, bigDataLinkedHashMap);
        //知识图谱推送
        Response graphResponse = api.doPost(propertiesUtil.getProperty("graph.http.url"), searchData,
                Response.class);
        LinkedHashMap graphLinkedHashMap = (LinkedHashMap) graphResponse.getData();
        //转FeatureRate对象
        ResponseData graphResponseData = map2ResponseData(graphLinkedHashMap);
        //添加治疗信息
        graphResponseData = addTreat(graphResponseData, graphLinkedHashMap);
        if (graphResponseData.getDis().size() > 0) {
            List<FeatureRate> disFeatureRates = new ArrayList<>();
            boolean isFind = false;
            for (int i = 0; i < bigDataResponseData.getDis().size(); i++) {
                FeatureRate bigdata_fr = bigDataResponseData.getDis().get(i);
                isFind = false;
                for (FeatureRate graph_fr : graphResponseData.getDis()) {
                    if (bigdata_fr.getFeatureName().equals(graph_fr.getFeatureName())) {
                        isFind = true;
                    }
                }
                if (!isFind) {
                    disFeatureRates.add(bigdata_fr);
                }
            }
            List<FeatureRate> graphFeatureRates = graphResponseData.getDis();
            graphFeatureRates.addAll(disFeatureRates);
            //大数据推送疾病数据用知识图谱替换
            bigDataResponseData.setDis(graphFeatureRates);
        }
        bigDataResponseData.setTreat(graphResponseData.getTreat());
        response.setData(bigDataResponseData);
        return response;
    }

    private ResponseData map2ResponseData(LinkedHashMap linkedHashMap) {
        ResponseData responseData = new ResponseData();
        if (linkedHashMap.get("dis") != null) {
            responseData.setDis(map2FeatureRates((List<LinkedHashMap<String, String>>)linkedHashMap.get("dis")));
        }
        if (linkedHashMap.get("symptom") != null) {
            responseData.setSymptom(map2FeatureRates((List<LinkedHashMap<String, String>>)linkedHashMap.get("symptom")));
        }
        if (linkedHashMap.get("vitals") != null) {
            responseData.setVitals(map2FeatureRates((List<LinkedHashMap<String, String>>)linkedHashMap.get("vitals")));
        }
        if (linkedHashMap.get("labs") != null) {
            responseData.setLabs(map2FeatureRates((List<LinkedHashMap<String, String>>)linkedHashMap.get("labs")));
        }
        if (linkedHashMap.get("pacs") != null) {
            responseData.setPacs(map2FeatureRates((List<LinkedHashMap<String, String>>)linkedHashMap.get("pacs")));
        }
        return responseData;
    }

    private List<FeatureRate> map2FeatureRates(List<LinkedHashMap<String, String>> data) {
        List<FeatureRate> featureRates = new ArrayList<>();
        for (LinkedHashMap<String, String> map : data) {
            FeatureRate fr = new FeatureRate();
            fr.setFeatureName(map.get("featureName"));
            fr.setRate(map.get("rate"));
            fr.setExtraProperty(map.get("extraProperty"));
            featureRates.add(fr);
        }
        return featureRates;
    }

    private ResponseData addInputs(ResponseData bigDataResponseData, LinkedHashMap linkedHashMap) {
        if (linkedHashMap.get("inputs") != null) {
            bigDataResponseData.setInputs((Map<String, Map<String, String>>)linkedHashMap.get("inputs"));
        }
        return bigDataResponseData;
    }

    private ResponseData addTreat(ResponseData graphResponseData, LinkedHashMap linkedHashMap) {
        Map<String,Filnlly> treatResult = new HashMap<String,Filnlly>();
        if(linkedHashMap.get("treat")!=null){
            LinkedHashMap<String, LinkedHashMap<String,ArrayList<LinkedHashMap>>> data= (LinkedHashMap<String, LinkedHashMap<String,ArrayList<LinkedHashMap>>>)linkedHashMap.get("treat");
            for (Map.Entry<String, LinkedHashMap<String,ArrayList<LinkedHashMap>>> fd:data.entrySet()) {
                String diseaseName = fd.getKey();
                LinkedHashMap<String, ArrayList<LinkedHashMap>> value = fd.getValue();
                ArrayList<LinkedHashMap> treament = value.get("treatment");
                ArrayList<Drugs> drugsList = new ArrayList<Drugs>();
                for (LinkedHashMap sd: treament) {
                    //创建药类对象,对药类对象进行封装
                    Drugs drugs = new Drugs();

                    String bigdrugsName = String.valueOf(sd.get("bigdrugsName"));
                    String subdrugsName = String.valueOf(sd.get("subdrugsName"));
                    int drugsForbidden = Integer.parseInt(sd.get("drugsForbidden").toString());
                    ArrayList<LinkedHashMap<String, Object>> medicitionsList = (ArrayList<LinkedHashMap<String, Object>>) sd.get("medicitionsList");
                    LinkedList<Medicition> medicitionObjectList=new LinkedList<>();
                    for (LinkedHashMap<String, Object> ds: medicitionsList) {
                        //创建药对象,进行封装
                        Medicition medicitionObject = new Medicition();

                        String medicitionName = String.valueOf(ds.get("medicitionName"));
                        String rate = String.valueOf(ds.get("rate"));
                        Integer isShow = Integer.parseInt(ds.get("isShow").toString());
                        Integer forbidden =Integer.parseInt(ds.get("forbidden").toString());
                        medicitionObject.setMedicitionName(medicitionName);//设置药名
                        medicitionObject.setRate(rate);//设置药的使用率
                        medicitionObject.setIsShow(isShow);//设置这个药是否展示
                        medicitionObject.setForbidden(forbidden);//设置这个药是否为禁忌药
                        medicitionObjectList.add(medicitionObject);
                    }
                    drugs.setBigdrugsName(bigdrugsName);//药的大类
                    drugs.setSubdrugsName(subdrugsName);//药的子类
                    drugs.setDrugsForbidden(drugsForbidden);
                    drugs.setMedicitionsList(medicitionObjectList);//这个类所包含的药物列表
                    drugsList.add(drugs);//药类列表
                }
                Filnlly filnlly = new Filnlly();
                filnlly.setTreatment(drugsList);
                treatResult.put(diseaseName,filnlly);
            }
        }
        graphResponseData.setTreat(treatResult);
        return graphResponseData;
    }
}
