package com.jy.flow.controller;

import com.jy.flow.dto.FlowDefinitionDto;
import com.warm.flow.core.entity.Definition;
import com.warm.flow.core.service.DefService;
import com.warm.flow.core.utils.page.Page;
import com.warm.flow.orm.entity.FlowDefinition;
import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletResponse;
import org.dom4j.Document;
import org.dom4j.io.OutputFormat;
import org.dom4j.io.XMLWriter;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.util.Collections;

@RestController
@RequestMapping("/flow/definition")
public class DefController {

    @Resource
    private DefService defService;

    /**
     * 分页查询流程定义列表
     */
    @GetMapping("/list")
    public Page<Definition> list(FlowDefinitionDto flowDefinition) {
        return defService.orderByCreateTime().desc()
                .page(flowDefinition, Page.pageOf(flowDefinition.getPageNum(), flowDefinition.getPageSize()));
    }

    /**
     * 获取流程定义详细信息
     */
    @GetMapping(value = "/{id}")
    public Definition getInfo(@PathVariable("id") Long id) {
        return defService.getById(id);
    }

    /**
     * 新增流程定义
     */
    @PostMapping
    @Transactional(rollbackFor = Exception.class)
    public Boolean add(@RequestBody FlowDefinition flowDefinition) {
        flowDefinition.setActivityStatus(0);
        return defService.checkAndSave(flowDefinition);
    }

    /**
     * 修改流程定义
     */
    @PutMapping
    @Transactional(rollbackFor = Exception.class)
    public Boolean edit(@RequestBody FlowDefinition flowDefinition) {
        return defService.updateById(flowDefinition);
    }

    /**
     * 删除流程定义
     */
    @DeleteMapping("/{id}")
    @Transactional(rollbackFor = Exception.class)
    public boolean remove(@PathVariable(name = "id", required = true) Long id) {
        return defService.removeDef(Collections.singletonList(id));
    }

    /**
     * 发布流程定义
     */
    @GetMapping("/publish/{id}")
    @Transactional(rollbackFor = Exception.class)
    public Boolean publish(@PathVariable("id") Long id) {
        return defService.publish(id);
    }

    /**
     * 取消发布流程定义
     */
    @GetMapping("/unPublish/{id}")
    @Transactional(rollbackFor = Exception.class)
    public void unPublish(@PathVariable("id") Long id) {
        defService.unPublish(id);
    }

    /**
     * 保存流程定义
     */
    @PostMapping("/saveXml")
    @Transactional(rollbackFor = Exception.class)
    public void saveXml(@RequestBody FlowDefinition def) throws Exception {
        defService.saveXml(def);
    }

    /**
     * 复制流程定义
     */
    @GetMapping("/copyDef/{id}")
    @Transactional(rollbackFor = Exception.class)
    public Boolean copyDef(@PathVariable("id") Long id) {
        return defService.copyDef(id);
    }

    @PostMapping("/importDefinition")
    @Transactional(rollbackFor = Exception.class)
    public void importDefinition(MultipartFile file) throws Exception {
        defService.importXml(file.getInputStream());
    }

    @PostMapping("/exportDefinition/{id}")
    public void exportDefinition(@PathVariable("id") Long id, HttpServletResponse response) throws Exception {
        Document document = defService.exportXml(id);
        // 设置生成xml的格式
        OutputFormat of = OutputFormat.createPrettyPrint();
        // 设置编码格式
        of.setEncoding("UTF-8");
        of.setIndent(true);
        of.setIndent("    ");
        of.setNewlines(true);

        // 创建一个xml文档编辑器
        XMLWriter writer = new XMLWriter(response.getOutputStream(), of);
        writer.setEscapeText(false);
        response.reset();
        response.setCharacterEncoding("UTF-8");
        response.setContentType("application/x-msdownload");
        response.setHeader("Content-Disposition", "attachment;");
        writer.write(document);
        writer.close();
    }

    @GetMapping("/xmlString/{id}")
    public String xmlString(@PathVariable("id") Long id) {
        return defService.xmlString(id);
    }

    /**
     * 查询流程图
     */
    @GetMapping("/flowChartNoColor/{definitionId}")
    public String flowChartNoColor(@PathVariable("definitionId") Long definitionId) throws IOException {
        return defService.flowChartNoColor(definitionId);
    }

    /**
     * 查询流程图
     */
    @GetMapping("/flowChart/{instanceId}")
    public String flowChart(@PathVariable("instanceId") Long instanceId) throws IOException {
        return defService.flowChart(instanceId);
    }

    /**
     * 激活流程
     */
    @GetMapping("/active/{definitionId}")
    public Boolean active(@PathVariable("definitionId") Long definitionId) {
        return defService.active(definitionId);
    }

    /**
     * 挂起流程
     */
    @GetMapping("/unActive/{definitionId}")
    public Boolean unActive(@PathVariable("definitionId") Long definitionId) {
        return defService.unActive(definitionId);
    }

}
