package com.lantone.structure.ai;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.google.common.collect.Lists;
import com.lantone.structure.ai.process.EntityOperationRecord;
import com.lantone.structure.ai.process.EntityProcessOperation;
import com.lantone.structure.client.CRFServiceClient;
import com.lantone.structure.ai.process.EntityProcessDrug;
import com.lantone.structure.ai.process.EntityProcessOperationDiscussion;
import com.lantone.common.util.CatalogueUtil;
import com.lantone.structure.model.Content;
import com.lantone.structure.model.InputInfo;
import com.lantone.structure.model.doc.operation.OperationDiscussionDoc;
import com.lantone.structure.model.doc.operation.OperationDoc;
import com.lantone.structure.model.doc.operation.OperationRecordDoc;
import com.lantone.structure.model.doc.operation.PreoperativeDiscussionDoc;
import com.lantone.structure.model.entity.Drug;
import com.lantone.structure.model.label.OperationDiscussionLabel;
import com.lantone.structure.model.label.OperationRecordLabel;
import com.lantone.common.util.StringUtil;
import com.lantone.structure.model.label.PreoperativeDiscussionLabel;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;

/**
 * @ClassName : OperationAI
 * @Description :
 * @Author : 胡敬
 * @Date: 2020-03-24 09:52
 */
public class OperationAI extends ModelAI {
    /**
     *
     */
    public static List<String> medicalTextType = Arrays.asList("CourseAfterOperation_cx", "CourseRecordSRR", "Taizhou_before_surgery", "Taizhou_operation");
    public static String entityRelationObject = "entity_relation_object";
    public static String outputs = "outputs";
    public static String content = "content";
    public static List<String> discussionKey = Lists.newArrayList("术前诊断", "术中后诊断", "手术名称", "麻醉方式"
            , "手术简要经过", "目前情况", "术后注意事项");

    public void medrec(InputInfo inputInfo, CRFServiceClient crfServiceClient) {
        JSONArray crfContent = new JSONArray();
        List<OperationDoc> operationDocs = inputInfo.getOperationDocs();
        for (int i = 0; i < operationDocs.size(); i++) {
            if (operationDocs.get(i).getPreoperativeDiscussionDoc() != null) {
                PreoperativeDiscussionDoc preoperativeDiscussionDoc = operationDocs.get(i).getPreoperativeDiscussionDoc();
                Map<String, String> structureMap = preoperativeDiscussionDoc.getStructureMap();
                String text = preoperativeDiscussionDoc.getText();
                //部位

                StringBuffer sb = new StringBuffer();
                if (StringUtil.isNotEmpty(structureMap.get("拟实施手术及操作名称"))) {
                    String opName = "拟实施手术及操作名称：" + structureMap.get("拟实施手术及操作名称");
                    putContent(crfContent, medicalTextType.get(2), opName, Content.surgicalSite);
                }
                //手术禁忌 = 手术指征 || 术前准备
                //手术禁忌 = 诊断依据 || 术前准备 || "药物、食物过敏史
                String opFlag = structureMap.get("手术指征");
                if (StringUtil.isNotEmpty(opFlag)) {
                    sb.append("手术指征：" + opFlag + "\n");
                }

                String preCase = structureMap.get("术前准备");
                if (StringUtil.isNotEmpty(preCase)) {
                    sb.append("术前准备：" + preCase + "\n");
                }

                String simCase = structureMap.get("诊断依据");
                if (StringUtil.isNotEmpty(simCase)) {
                    sb.append("简要病情：" + simCase + "\n");
                }

                String pillCase = structureMap.get("药物、食物过敏史");
                if (StringUtil.isNotEmpty(pillCase) && StringUtil.isEmpty(simCase)) {
                    sb.append("药物、食物过敏史：" + pillCase + "\n");
                }

                if (StringUtil.isNotEmpty(sb.toString())) {
                    text = sb.toString();
                    putContent(crfContent, medicalTextType.get(2), text, Content.preoperativeDiscussion);
                }
            }
            if (operationDocs.get(i).getOperationRecordDoc() != null) {
                OperationRecordDoc operationRecordDoc = operationDocs.get(i).getOperationRecordDoc();
                Map<String, String> structureMap = operationRecordDoc.getStructureMap();
                //存放抓取的药品
                String content = CatalogueUtil.structureMapJoin(structureMap, Lists.newArrayList("手术经过及处理", "手术中用药（化疗等药物）"));
                putContent(crfContent, medicalTextType.get(1), content, "手术记录" + i + "药物");

                /***************************** 后结构化数据处理（一般手术记录）****************************************/
                if (operationRecordDoc.getStructureMap() != null) {
                    putContent(crfContent, medicalTextType.get(3), operationRecordDoc.getStructureMap().get("手术过程描述"), Content.operationRecord);
                }
            }
            if (operationDocs.get(i).getOperationDiscussionDoc() != null) {
                OperationDiscussionDoc operationDiscussionDoc = operationDocs.get(i).getOperationDiscussionDoc();
                Map<String, String> structureMap = operationDiscussionDoc.getStructureMap();
                String discussionText = CatalogueUtil.structureMapJoin(structureMap, discussionKey);
                putContent(crfContent, medicalTextType.get(0), discussionText, Content.operation_Discussion + i);
                //存放抓取的药品
                String content = CatalogueUtil.structureMapJoin(structureMap, Lists.newArrayList("治疗计划和措施", "术后处理措施"));
                putContent(crfContent, medicalTextType.get(1), content, Content.operation_Discussion + i + "药物");
            }
        }

        JSONObject midData = loadAI(crfContent, crfServiceClient);//crf返回数据

        for (int i = 0; i < operationDocs.size(); i++) {
            if (midData.get(Content.preoperativeDiscussion) == null) {
                continue;
            }
            if (midData.get(Content.surgicalSite) == null) {
                continue;
            }
            putPreoperativeDiscussionCrfData(midData.getJSONObject(Content.preoperativeDiscussion), inputInfo);
            PreoperativeDiscussionLabel preoperativeDiscussionLabel = inputInfo.getOperationDocs().get(0).getPreoperativeDiscussionDoc().getPreoperativeDiscussionLabel();
            putPreoperativeDiscussionCrfData(midData.getJSONObject(Content.surgicalSite), inputInfo);
            PreoperativeDiscussionLabel preoperativeDiscussionLabelRe = inputInfo.getOperationDocs().get(0).getPreoperativeDiscussionDoc().getPreoperativeDiscussionLabel();
            preoperativeDiscussionLabel.setOpBottomName(preoperativeDiscussionLabelRe.getOpBottomName());
            inputInfo.getOperationDocs().get(0).getPreoperativeDiscussionDoc().setPreoperativeDiscussionLabel(preoperativeDiscussionLabel);
        }

        for (int i = 0; i < operationDocs.size(); i++) {
            if (midData.get("手术记录" + i + "药物") != null) {
                OperationRecordDoc operationRecordDoc = operationDocs.get(i).getOperationRecordDoc();
                //手术记录药品
                OperationRecordLabel operationRecordLabel = new OperationRecordLabel();
                operationRecordLabel.setDrugs(putDrugCrfData(midData.getJSONObject("手术记录" + i + "药物")));
            }
            if (midData.get(Content.operation_Discussion + i) != null) {
                OperationDiscussionDoc discussionDoc = operationDocs.get(i).getOperationDiscussionDoc();
                OperationDiscussionLabel discussionLabel = putOperationDiscussionCrfData(midData.getJSONObject(Content.operation_Discussion + i));
                if (discussionLabel != null) {
                    discussionDoc.setOperationDiscussionLabel(discussionLabel);
                }
                //术后首程药品
                if (midData.get(Content.operation_Discussion + i + "药物") != null) {
                    discussionLabel = operationDocs.get(i).getOperationDiscussionDoc().getOperationDiscussionLabel();
                    if (discussionLabel == null) {
                        discussionLabel = new OperationDiscussionLabel();
                    }
                    discussionLabel.setDrugs(putDrugCrfData(midData.getJSONObject(Content.operation_Discussion + i + "药物")));
                }
            }

            /***************************** 后结构化数据处理（一般手术记录）****************************************/
            if (midData.get(Content.operationRecord) != null) {
                OperationRecordDoc operationRecordDoc = operationDocs.get(i).getOperationRecordDoc();
                OperationRecordLabel operationRecordLabel = putOperationRecordCrfData(midData.getJSONObject(Content.operationRecord), inputInfo);
                if (operationRecordLabel != null) {
                    operationRecordDoc.setOperationRecordLabel(operationRecordLabel);
                }
            }
        }
    }

    /**
     * 处理后结构化一般手术记录
     *
     * @param jsonObject
     */
    public OperationRecordLabel putOperationRecordCrfData(JSONObject jsonObject, InputInfo inputInfo) {
        OperationRecordLabel operationRecordLabel = new OperationRecordLabel();
        if (jsonObject == null) {
            return operationRecordLabel;
        }
        JSONObject aiOut = jsonObject.getJSONObject(entityRelationObject).getJSONObject(BeHospitalizedAI.outputs);
        if (aiOut == null) {
            return operationRecordLabel;
        }
        EntityOperationRecord entityOperationRecord = new EntityOperationRecord();
        operationRecordLabel = entityOperationRecord.extractEntity(aiOut);
        return operationRecordLabel;
    }

    /**
     * 处理手术记录
     *
     * @param jsonObject
     */
    public OperationDiscussionLabel putOperationDiscussionCrfData(JSONObject jsonObject) {
        JSONObject aiOut = loadEntity(jsonObject, entityRelationObject, outputs, content);
        if (aiOut == null) {
            return null;
        }
        String originalText = jsonObject.getString("originalText");
        EntityProcessOperationDiscussion entityProcessOperationDiscussion = new EntityProcessOperationDiscussion();
        return entityProcessOperationDiscussion.extractEntity(aiOut);
    }

    /**
     * 存放抓取的药品
     *
     * @param jsonObject
     */
    public List<Drug> putDrugCrfData(JSONObject jsonObject) {
        JSONObject aiOut = loadEntity(jsonObject, entityRelationObject, outputs, content);
        if (aiOut == null) {
            return new ArrayList<>();
        }
        EntityProcessDrug entityProcessDrug = new EntityProcessDrug();
        List<Drug> drugs = entityProcessDrug.extractEntity(aiOut);
        return drugs;
    }

    /**
     * 处理术前小结
     *
     * @param jsonObject
     */
    public void putPreoperativeDiscussionCrfData(JSONObject jsonObject, InputInfo inputInfo) {
        if (jsonObject == null) {
            return;
        }
        JSONObject aiOut = jsonObject.getJSONObject(entityRelationObject).getJSONObject(BeHospitalizedAI.outputs);
        if (aiOut == null) {
            return;
        }
        EntityProcessOperation entityProcessOperation = new EntityProcessOperation();
        PreoperativeDiscussionLabel preoperativeDiscussionLabel = entityProcessOperation.extractEntity(aiOut);
        inputInfo.getOperationDocs().get(0).getPreoperativeDiscussionDoc().setPreoperativeDiscussionLabel(preoperativeDiscussionLabel);
    }

    protected void putContent(JSONArray crfContent, String medicalTextType, String text, String sign) {
        String move_text = CatalogueUtil.removeSpecialChar(text);
        if (StringUtil.isEmpty(move_text)) {
            return;
        }
        JSONObject detailContent = new JSONObject();
        detailContent.put("medical_text_type", medicalTextType);
        detailContent.put("content", move_text);
        detailContent.put("detail_title", sign);
        detailContent.put("originalText", text);
        crfContent.add(detailContent);
    }
}