package cn.stylefeng.workflow.instance.modular.task.factory;

import cn.hutool.core.collection.ListUtil;
import cn.stylefeng.roses.kernel.auth.api.context.LoginContext;
import cn.stylefeng.roses.kernel.rule.enums.YesOrNotEnum;
import cn.stylefeng.workflow.api.entity.instance.RuntimeInstance;
import cn.stylefeng.workflow.api.entity.instance.RuntimeNode;
import cn.stylefeng.workflow.api.entity.task.RuTask;
import cn.stylefeng.workflow.api.enums.TaskConditionEnum;
import cn.stylefeng.workflow.api.enums.TaskStatusEnum;
import cn.stylefeng.workflow.api.enums.TaskTypeEnum;
import cn.stylefeng.workflow.api.pojo.InstanceContext;
import cn.stylefeng.workflow.api.util.WorkFlowStatusUtil;
import cn.stylefeng.workflow.instance.modular.task.pojo.TaskDetailVo;
import cn.stylefeng.workflow.instance.modular.task.pojo.request.TaskQueryRequest;
import com.baomidou.mybatisplus.core.toolkit.IdWorker;

import java.util.List;

public class RuTaskFactory {

    public static RuTask createBaseApproverTask(Long approverId, TaskTypeEnum taskTypeEnum, RuntimeNode runtimeNode,
                                                InstanceContext instanceContext) {

        RuTask ruTask = new RuTask();

        ruTask.setTaskId(IdWorker.getId());

        ruTask.setTaskType(taskTypeEnum.getCode());

        ruTask.setModelId(instanceContext.getModel().getModelId());
        ruTask.setDefinitionId(instanceContext.getDefinition().getDefinitionId());
        ruTask.setInstanceId(instanceContext.getRuntimeInstance().getInstanceId());

        ruTask.setReNodeId(runtimeNode.getNodeId());
        ruTask.setRuNodeId(runtimeNode.getRuNodeId());

        ruTask.setApprover(approverId);

        ruTask.setReadFlag(YesOrNotEnum.N.getCode());

        WorkFlowStatusUtil.initTaskStatus(ruTask, taskTypeEnum);

        return ruTask;
    }

    public static TaskQueryRequest createTaskStatusRequest(TaskConditionEnum taskCondition, Long taskId) {

        TaskQueryRequest taskQueryRequest = new TaskQueryRequest();

        taskQueryRequest.setTaskId(taskId);

        taskQueryRequest.setApprover(LoginContext.me().getLoginUser().getUserId());

        Integer taskType = null;
        List<Integer> taskStatusCollection = null;

        if (taskCondition.equals(TaskConditionEnum.WAIT_TO_DO)) {
            taskType = TaskTypeEnum.PROCESSING.getCode();
            taskStatusCollection = ListUtil.list(false, TaskStatusEnum.PROCESSING.getCode());
        }

        else if (taskCondition.equals(TaskConditionEnum.WAIT_TO_READ)) {
            taskType = TaskTypeEnum.COPY.getCode();
            taskQueryRequest.setReadFlag(YesOrNotEnum.N.getCode());
        }

        else if (taskCondition.equals(TaskConditionEnum.ALREADY_DO)) {
            taskType = TaskTypeEnum.PROCESSING.getCode();
            taskStatusCollection = ListUtil.list(false, TaskStatusEnum.PROCESSED.getCode(), TaskStatusEnum.REJECT.getCode(),
                    TaskStatusEnum.BACK.getCode(), TaskStatusEnum.CALL_BACK.getCode(), TaskStatusEnum.TRANSFERRED.getCode());
        }

        else if (taskCondition.equals(TaskConditionEnum.ALREADY_READ)) {
            taskType = TaskTypeEnum.COPY.getCode();
            taskQueryRequest.setReadFlag(YesOrNotEnum.Y.getCode());
        }

        taskQueryRequest.setTaskType(taskType);
        taskQueryRequest.setTaskStatusList(taskStatusCollection);

        return taskQueryRequest;
    }

    public static TaskDetailVo createTaskDetail(RuTask ruTask, RuntimeInstance runtimeInstance) {
        TaskDetailVo taskDetailVo = new TaskDetailVo();

        if (ruTask != null) {
            taskDetailVo.setTaskStatus(ruTask.getTaskStatus());
        }

        if (runtimeInstance != null) {
            taskDetailVo.setInstanceId(runtimeInstance.getInstanceId());
            taskDetailVo.setInstanceTitle(runtimeInstance.getInstanceTitle());
            taskDetailVo.setApplicant(runtimeInstance.getApplicant());
            taskDetailVo.setApplicantOrgId(runtimeInstance.getApplicantOrgId());
            taskDetailVo.setInstanceStatus(runtimeInstance.getInstanceStatus());
            taskDetailVo.setCreateTime(runtimeInstance.getCreateTime());
        }

        return taskDetailVo;
    }

}
