package org.jeecg.modules.adweb.workflow.controller;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.jeecg.common.api.vo.Result;
import org.jeecg.common.aspect.annotation.AutoLog;
import org.jeecg.common.system.base.controller.JeecgController;
import org.jeecg.common.system.query.QueryGenerator;
import org.jeecg.common.system.vo.LoginUser;
import org.jeecg.modules.adweb.common.constant.NumConstant;
import org.jeecg.modules.adweb.enquiry.entity.AdwebEnquiry;
import org.jeecg.modules.adweb.enquiry.service.IAdwebEnquiryService;
import org.jeecg.modules.adweb.site.entity.AdwebSite;
import org.jeecg.modules.adweb.site.service.IAdwebSiteService;
import org.jeecg.modules.adweb.workflow.entity.ExecuteNode;
import org.jeecg.modules.adweb.workflow.service.IExecuteNodeService;
import org.jeecg.modules.system.entity.SysUser;
import org.jeecg.modules.system.service.ISysUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.servlet.ModelAndView;

/**
 * @Description: adweb_execute_node @Author: jeecg-boot @Date: 2025-03-21 @Version: V1.0
 */
@Tag(name = "adweb_execute_node")
@RestController
@RequestMapping("/adweb/executeNode")
@Slf4j
public class ExecuteNodeController extends JeecgController<ExecuteNode, IExecuteNodeService> {

  @Autowired private IExecuteNodeService executeNodeService;

  @Autowired private IAdwebSiteService siteService;

  @Autowired private IAdwebEnquiryService adwebEnquiryService;

  @Autowired private ISysUserService sysUserService;

  /**
   * 分页列表查询
   *
   * @param executeNode
   * @param pageNo
   * @param pageSize
   * @param req
   * @return
   */
  @AutoLog(value = "adweb_execute_node-分页列表查询")
  @Operation(summary = "adweb_execute_node-分页列表查询")
  @GetMapping(value = "/list")
  public Result<?> queryPageList(
      ExecuteNode executeNode,
      @RequestParam(name = "pageNo", defaultValue = "1") Integer pageNo,
      @RequestParam(name = "pageSize", defaultValue = "10") Integer pageSize,
      HttpServletRequest req) {
    QueryWrapper<ExecuteNode> queryWrapper =
        QueryGenerator.initQueryWrapper(executeNode, req.getParameterMap());
    Page<ExecuteNode> page = new Page<ExecuteNode>(pageNo, pageSize);
    IPage<ExecuteNode> pageList = executeNodeService.page(page, queryWrapper);
    return Result.OK(pageList);
  }

  /**
   * 添加
   *
   * @param executeNode
   * @return
   */
  @AutoLog(value = "adweb_execute_node-添加")
  @Operation(summary = "adweb_execute_node-添加")
  @PostMapping(value = "/add")
  public Result<?> add(@RequestBody ExecuteNode executeNode) {
    executeNodeService.save(executeNode);
    return Result.OK("添加成功！");
  }

  /**
   * 编辑
   *
   * @param executeNode
   * @return
   */
  @AutoLog(value = "adweb_execute_node-编辑")
  @Operation(summary = "adweb_execute_node-编辑")
  @PutMapping(value = "/edit")
  public Result<?> edit(@RequestBody ExecuteNode executeNode) {
    executeNodeService.updateById(executeNode);
    return Result.OK("编辑成功!");
  }

  /**
   * 通过id删除
   *
   * @param id
   * @return
   */
  @AutoLog(value = "adweb_execute_node-通过id删除")
  @Operation(summary = "adweb_execute_node-通过id删除")
  @DeleteMapping(value = "/delete")
  public Result<?> delete(@RequestParam(name = "id", required = true) String id) {
    executeNodeService.removeById(id);
    return Result.OK("删除成功!");
  }

  /**
   * 批量删除
   *
   * @param ids
   * @return
   */
  @AutoLog(value = "adweb_execute_node-批量删除")
  @Operation(summary = "adweb_execute_node-批量删除")
  @DeleteMapping(value = "/deleteBatch")
  public Result<?> deleteBatch(@RequestParam(name = "ids", required = true) String ids) {
    this.executeNodeService.removeByIds(Arrays.asList(ids.split(",")));
    return Result.OK("批量删除成功!");
  }

  /**
   * 通过id查询
   *
   * @param id
   * @return
   */
  @AutoLog(value = "adweb_execute_node-通过id查询")
  @Operation(summary = "adweb_execute_node-通过id查询")
  @GetMapping(value = "/queryById")
  public Result<?> queryById(@RequestParam(name = "id", required = true) String id) {
    ExecuteNode executeNode = executeNodeService.getById(id);
    if (executeNode == null) {
      return Result.error("未找到对应数据");
    }
    return Result.OK(executeNode);
  }

  /**
   * 导出excel
   *
   * @param request
   * @param executeNode
   */
  @RequestMapping(value = "/exportXls")
  public ModelAndView exportXls(HttpServletRequest request, ExecuteNode executeNode) {
    return super.exportXls(request, executeNode, ExecuteNode.class, "adweb_execute_node");
  }

  /**
   * 通过excel导入数据
   *
   * @param request
   * @param response
   * @return
   */
  @RequestMapping(value = "/importExcel", method = RequestMethod.POST)
  public Result<?> importExcel(HttpServletRequest request, HttpServletResponse response) {
    return super.importExcel(request, response, ExecuteNode.class);
  }

  /**
   * 通过siteCode查询建站执行流程
   *
   * @param siteCode 站点code @Author: luxiaoxiao @Date: 2021/10/28
   */
  @GetMapping(value = "/querySiteBuildFlow")
  @Operation(summary = "通过siteCode查询建站执行流程")
  public Result<?> querySiteBuildFlow(
      @RequestParam(name = "siteCode", required = true) String siteCode) {
    List<ExecuteNode> list = executeNodeService.getSiteBuildFlow(siteCode);
    if (CollectionUtils.isEmpty(list)) {
      return Result.error("未找到对应数据");
    }
    return Result.OK(list);
  }

  /**
   * 通过询盘ID查出审核流程
   *
   * @param enquiryId 询盘ID @Author: chenpeiqing @Date: 2025/03/24
   */
  @GetMapping(value = "/queryEnquiryVerifyFlow")
  @Operation(summary = "通过询盘ID查出审核流程")
  public Result<?> queryEnquiryVerifyFlow(
      @RequestParam(name = "enquiryId", required = true) String enquiryId) {
    List<ExecuteNode> list = executeNodeService.getEnquiryVerifyFlow(enquiryId);
    if (CollectionUtils.isEmpty(list)) {

      // 如果询盘审核流程不存在创建审核流程，该逻辑为了兼容旧询盘数据，正常情况下，凡是查询盘的审核流程都已经有，所以这里就不做处理了
      // 询盘审核流程，在MQ消费插入询盘时自动创建
      executeNodeService.copyEnquiryVerifyFlow(enquiryId);
      list = executeNodeService.getEnquiryVerifyFlow(enquiryId);
    }

    // 设置审核人
    for (ExecuteNode executeNode : list) {
      if (StringUtils.isNotBlank(executeNode.getFinUid())) {
        SysUser user = sysUserService.getById(executeNode.getFinUid());
        if (user != null) {
          executeNode.setFinName(user.getRealname());
        }
      }
    }

    return Result.OK(list);
  }

  /** 查询建站模板流程 @Author: luxiaoxiao @Date: 2021/10/28 */
  @GetMapping(value = "/querySiteBuildTemplateFlow")
  @Operation(summary = "查询建站模板流程")
  public Result<?> querySiteBuildTemplateFlow() {
    List<ExecuteNode> list = executeNodeService.getSiteBuildTemplateFlow();
    if (CollectionUtils.isEmpty(list)) {
      return Result.error("未找到对应数据");
    }
    return Result.OK(list);
  }

  /** 查询建站模板流程 @Author: luxiaoxiao @Date: 2021/10/28 */
  @GetMapping(value = "/queryEnquiryVerifyTemplateFlow")
  @Operation(summary = "查询询盘蛇和模板流程")
  public Result<?> queryEnquiryVerifyTemplateFlow() {
    List<ExecuteNode> list = executeNodeService.getEnquiryVerifyTemplateFlow();
    if (CollectionUtils.isEmpty(list)) {
      return Result.error("未找到对应数据");
    }
    return Result.OK(list);
  }

  /** 通过planId查询SEO优化模板流程 @Author: luxiaoxiao @Date: 2021/10/28 */
  @GetMapping(value = "/querySEOTemplateFlow")
  @Operation(summary = "查询SEO优化模板流程")
  public Result<?> querySEOTemplateFlow() {
    List<ExecuteNode> list = executeNodeService.getSEOTemplateFlow();
    if (CollectionUtils.isEmpty(list)) {
      return Result.error("未找到对应数据");
    }
    return Result.OK(list);
  }

  /** 保存流程，hostId不能为空 @Author: luxiaoxiao @Date: 2021/10/28 */
  @PostMapping(value = "/saveFlowTemplate")
  @Operation(summary = "保存流程模板")
  public Result<?> saveTemplate(@RequestBody List<ExecuteNode> nodeList) {
    boolean result = executeNodeService.saveTemplate(nodeList);
    return result ? Result.OK() : Result.error("操作失败");
  }

  /**
   * 流程完成与撤销，同时更新site表现阶段
   *
   * @param executeNode @Author: jerry @Date: 2021/12/03
   */
  @RequestMapping(value = "/finishOrRollbackStep")
  public Result<?> finishOrRollbackStep(@RequestBody ExecuteNode executeNode) {
    // 更新节点数据
    LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
    UpdateWrapper<ExecuteNode> updateWrapper = new UpdateWrapper<>();
    updateWrapper.eq("id", executeNode.getId());
    updateWrapper.set("status", executeNode.getStatus());
    if (executeNode.getStatus() == 0) {
      updateWrapper.set("fin_time", null);
      updateWrapper.set("fin_uid", null);
    }
    if (executeNode.getStatus() == 1) {
      updateWrapper.set(
          "fin_time", executeNode.getFinTime() == null ? new Date() : executeNode.getFinTime());
      updateWrapper.set("fin_uid", sysUser.getId());
    }
    boolean res = executeNodeService.update(updateWrapper);
    if (!res) {
      return Result.error("操作失败！");
    }

    executeNode = executeNodeService.getById(executeNode.getId());

    // 更新流程步骤和状态
    UpdateWrapper<AdwebSite> siteUpdateWrapper = new UpdateWrapper<>();
    siteUpdateWrapper.eq("code", executeNode.getHostId());
    // SEO流程
    if (executeNode.getNodeType().equals(NumConstant.TWO)) {
      List<ExecuteNode> unfinishedList =
          executeNodeService.getSeoUnfinishedNode(executeNode.getHistoryId());
      if (CollectionUtils.isNotEmpty(unfinishedList)) {
        siteUpdateWrapper
            .set("seo_flow_status", 0)
            .set("seo_current_step", unfinishedList.get(0).getName());
      } else {
        siteUpdateWrapper.set("seo_flow_status", 1).set("seo_current_step", "已完成");
      }
    }
    // 建站流程
    if (executeNode.getNodeType().equals(NumConstant.ONE)) {
      List<ExecuteNode> unfinishedList =
          executeNodeService.getSiteUnfinishedNode(executeNode.getHostId());
      if (CollectionUtils.isNotEmpty(unfinishedList)) {
        siteUpdateWrapper
            .set("site_flow_status", 0)
            .set("site_current_step", unfinishedList.get(0).getName());
      } else {
        siteUpdateWrapper.set("site_flow_status", 1).set("site_current_step", "已完成");
      }
    }
    siteService.update(siteUpdateWrapper);
    return Result.OK();
  }

  /**
   * 流程完成与撤销，同时更新询盘表现阶段
   *
   * @param executeNode @Author: jerry @Date: 2021/12/03
   */
  @RequestMapping(value = "/finishOrRollbackEnquiryVerifyStep")
  public Result<?> finishOrRollbackEnquiryVerifyStep(@RequestBody ExecuteNode executeNode) {

    if (executeNode.getStepCount() == null) {
      return Result.error("当前审核步骤长度为空！");
    }

    Integer stepCount = executeNode.getStepCount();

    // 更新节点数据
    LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
    UpdateWrapper<ExecuteNode> updateWrapper = new UpdateWrapper<>();
    updateWrapper.eq("id", executeNode.getId());
    updateWrapper.set("status", executeNode.getStatus());
    updateWrapper.set("description", executeNode.getDescription());
    if (executeNode.getStatus() == 0) {
      updateWrapper.set("fin_time", null);
      updateWrapper.set("fin_uid", null);
    }
    if (executeNode.getStatus() == 1) {
      updateWrapper.set(
          "fin_time", executeNode.getFinTime() == null ? new Date() : executeNode.getFinTime());
      updateWrapper.set("fin_uid", sysUser.getId());
    }
    boolean res = executeNodeService.update(updateWrapper);
    if (!res) {
      return Result.error("操作失败！");
    }

    executeNode = executeNodeService.getById(executeNode.getId());

    // 更新流程步骤和状态
    UpdateWrapper<AdwebEnquiry> enquiryUpdateWrapper = new UpdateWrapper<>();
    enquiryUpdateWrapper.eq("id", executeNode.getHostId());
    // 询盘审核流程
    if (executeNode.getNodeType().equals(NumConstant.FOUR)) {
      List<ExecuteNode> unfinishedList =
          executeNodeService.getEnquiryVerifyUnfinishedNode(executeNode.getHostId());
      if (CollectionUtils.isNotEmpty(unfinishedList)) {
        enquiryUpdateWrapper.set("verify_num", stepCount - unfinishedList.size());
      } else {
        enquiryUpdateWrapper.set("verify_num", stepCount); // 设置审核步骤完成
        enquiryUpdateWrapper.set("user_Effective", 1); // 设置为有效询盘
      }
    }

    adwebEnquiryService.update(enquiryUpdateWrapper);
    return Result.OK();
  }
}
