package org.jeecg.modules.stm.essearch.stlib.controller;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import org.apache.commons.lang3.StringUtils;
import org.jeecg.common.api.vo.Result;
import org.jeecg.modules.stm.common.service.IStCommonService;
import org.jeecg.modules.stm.common.vo.QueryVo;
import org.jeecg.modules.stm.essearch.stlib.service.IStlibService;
import org.jeecg.modules.stm.problem.service.IStProblemService;
import org.jeecg.modules.stm.stlib.constant.StLibbIndexs;
import org.jeecg.modules.stm.stlib.pojo.EsQueryVo;
import org.jeecg.modules.stm.stlib.pojo.PageResult;

import org.jeecg.modules.stm.risk.event.service.IStRiskEventService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import jakarta.servlet.http.HttpServletRequest;
import org.jeecg.common.es.JeecgElasticsearchTemplate;

import java.util.ArrayList;
import java.util.List;

@RestController
@RequestMapping("/stm/es/common")
public class StLibController {
    @Autowired
    private IStCommonService iStCommonService;
    @Autowired
    private JeecgElasticsearchTemplate esTpl;
    @Autowired
    private IStlibService iStlibService;
    @Autowired
    private IStRiskEventService stRiskEventService;
    @Autowired
    private IStProblemService stProblemService;
    @GetMapping(value = "/list")
    public Result<PageResult> searchPageList(EsQueryVo params,
             @RequestParam(name="pageNo", defaultValue="1") Integer pageNo,
             @RequestParam(name="pageSize", defaultValue="10") Integer pageSize,
             HttpServletRequest req) {

        int from = (pageNo-1)*pageSize;
        String name = params.getName();
        JSONArray objAryMust = new JSONArray();
        JSONObject highlightObj = null;
        highlightObj = getJSONHighlight();

        if(!StringUtils.isEmpty(name)){
            JSONObject objMatch = new JSONObject();
            JSONArray objFields = new JSONArray();
            objFields.add("lableNames^2");
            objFields.add("name^2");
            objFields.add("scdesc");
            objFields.add("tag");
            objMatch.put("fields",objFields);
            objMatch.put("query",name);
            JSONObject objMatchMulti = new JSONObject();
            objMatchMulti.put("multi_match", objMatch);
            objAryMust.add(objMatchMulti);
        }

        if(!StringUtils.isEmpty(params.getSctype())){
            JSONObject objTerm = new JSONObject();
            JSONObject objType = new JSONObject();
            objType.put("sctype", params.getSctype());
            objTerm.put("term", objType);
            objAryMust.add(objTerm);
        }

        String paramLableNames = params.getLableNames();
        if(!StringUtils.isEmpty(paramLableNames)){
            String strTmp = paramLableNames.replaceAll(","," ");
            JSONObject objTerm = new JSONObject();
            JSONObject objLabels = new JSONObject();
            objLabels.put("lableNames",strTmp);
            objTerm.put("match_phrase", objLabels);
            objAryMust.add(objTerm);
        }

        JSONObject objMust = new JSONObject();
        objMust.put("must",objAryMust);
        JSONObject objBool = new JSONObject();
        objBool.put("bool",objMust);
        JSONArray orderJSONObject = null;
        JSONObject buildQuery = esTpl.buildQuery(null, objBool, from, pageSize, highlightObj, orderJSONObject);

        JSONObject ret = null;
        try {
            ret = esTpl.search(StLibbIndexs.index_name, buildQuery);
        } catch (Exception e){
            boolean isExist = esTpl.indexExists(StLibbIndexs.index_name);
            if(!isExist){
                QueryVo queryVo = new QueryVo();
                createDocLib(queryVo);
                ret = esTpl.search(StLibbIndexs.index_name, buildQuery);
            }
        }

        JSONObject retObj = ret != null ? ret.getJSONObject("hits") : null;
        PageResult pageResult = null;
        if (retObj != null) {
            JSONObject totalObj = retObj.getJSONObject("total");
            int total = totalObj != null ? totalObj.getInteger("value") : 0;
            JSONArray list = retObj.getJSONArray("hits");
            List<EsQueryVo> retList = new ArrayList<>();

            if(list != null) {
                for(int i = 0; i < list.size(); i++) {
                    JSONObject ojb = list.getJSONObject(i).getJSONObject("_source");
                    JSONObject ojbHighlight = list.getJSONObject(i).getJSONObject("highlight");
                    EsQueryVo queryVo = new EsQueryVo();

                    if(ojb != null) {
                        String rname = ojb.getString("name");
                        queryVo.setId(ojb.getInteger("id"));
                        queryVo.setFileId(ojb.getInteger("fileId"));
                        String rtag = ojb.getString("tag");
                        String rscdesc = ojb.getString("scdesc");
                        String lableNames = ojb.getString("lableNames");
                        String fileName = ojb.getString("fileName");
                        String filePath = ojb.getString("filePath");

                        if(ojbHighlight != null) {
                            if (ojbHighlight.getJSONArray("name") != null) {
                                rname = ojbHighlight.getJSONArray("name").get(0).toString();
                            }
                            if (ojbHighlight.getJSONArray("scdesc") != null) {
                                rscdesc = ojbHighlight.getJSONArray("scdesc").get(0).toString();
                            }
                            if (ojbHighlight.getJSONArray("lableNames") != null) {
                                lableNames = ojbHighlight.getJSONArray("lableNames").get(0).toString();
                            }
                            if (ojbHighlight.getJSONArray("tag") != null) {
                                rtag = ojbHighlight.getJSONArray("tag").get(0).toString();
                            }
                        }

                        queryVo.setName(rname);
                        queryVo.setSctype(ojb.getString("sctype"));
                        queryVo.setTag(rtag);
                        queryVo.setLableNames(lableNames);
                        queryVo.setScdesc(rscdesc);
                        queryVo.setBizNo(ojb.getString("bizNo"));
                        queryVo.setFileName(fileName);
                        queryVo.setFilePath(filePath);
                        retList.add(queryVo);
                    }
                }
            }

            pageResult = new PageResult(total, retList);
            return Result.OK(pageResult);
        } else {
            return Result.OK("未查询到数据");
        }
    }

    @PostMapping("/createDocLib")
    public Result<String> createDocLib(QueryVo queryVo) {
        try {
            createIndex();
            List<QueryVo> list = iStCommonService.queryAllLibData(queryVo);
            if(list != null && !list.isEmpty()) {
                JSONArray ary = JSONArray.parseArray(JSON.toJSONString(list));
                boolean ret = esTpl.saveBatch(StLibbIndexs.index_name, ary);
                return ret ? Result.OK("数据创建成功") : Result.error("数据保存失败");
            } else {
                return Result.OK("未查到数据库数据");
            }
        } catch (Exception e) {
            e.printStackTrace();
            return Result.error("数据创建失败: " + e.getMessage());
        }
    }

    @PostMapping("/createIndex")
    public Result<String> createIndex() {
        try {
            if (esTpl.indexExists(StLibbIndexs.index_name)) {
                esTpl.deleteAll(StLibbIndexs.index_name);
                esTpl.removeIndex(StLibbIndexs.index_name);
            }

            JSONObject obj = JSONObject.parseObject(StLibbIndexs.mapping_common);
            boolean success = esTpl.createIndex(StLibbIndexs.index_name, obj);
            if (success) {
                esTpl.setIndexReplicasToZero(StLibbIndexs.index_name);
                esTpl.disableIndexTemplateILM(StLibbIndexs.index_name);
                return Result.OK("索引创建成功");
            } else {
                return Result.error("索引创建失败");
            }
        } catch (Exception e) {
            e.printStackTrace();
            return Result.error("索引创建失败: " + e.getMessage());
        }
    }

    private JSONObject getJSONHighlight() {
        JSONObject obj = JSONObject.parseObject(StLibbIndexs.mapping_common_highlight);
        return obj;
    }

    private JSONArray getJSONOrder() {
        JSONArray obj = JSONArray.parseArray(StLibbIndexs.mapping_common_query_sort);
        return obj;
    }
}