package cn.axzo.workflow.core.deletage;

import cn.axzo.workflow.common.model.request.bpmn.task.BpmnTaskDelegateAssigner;
import com.alibaba.fastjson.JSON;
import org.flowable.bpmn.model.FlowElement;
import org.flowable.engine.delegate.DelegateExecution;
import org.springframework.util.CollectionUtils;

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;

/**
 * 开发阶段的模拟审批人查询
 *
 * @author wangli
 * @since 2023/11/17 13:40
 */
public class MockTaskAssigneeSelector implements BpmnTaskAssigneeSelector {
    private final Map<String, List<BpmnTaskDelegateAssigner>> assigneeMap = new HashMap<>();
    private final String category;
    private final Boolean global;

    public MockTaskAssigneeSelector(Map<String, String> map, Boolean global, String category) {
        map.forEach((k, v) -> {
            List<BpmnTaskDelegateAssigner> assigners = new ArrayList<>();
            JSON.parseArray(v, String.class).forEach(i -> assigners.add(JSON.parseObject(i, BpmnTaskDelegateAssigner.class)));
            assigneeMap.put(k, assigners);
        });
        this.category = category;
        this.global = global;
    }

    @Override
    public String getType() {
        return "mock";
    }

    @Override
    public boolean support(String param) {
        return true;
    }

    @Override
    public List<BpmnTaskDelegateAssigner> select(FlowElement flowElement, DelegateExecution execution,
                                                 Boolean throwException) {
        List<BpmnTaskDelegateAssigner> users = new ArrayList<>();

        // 优先读取 Nacos 配置
        firstParseNacos(flowElement, execution, users);
        if (!CollectionUtils.isEmpty(users)) {
            return users;
        }

        // 这里是不配置 nacos 的前提下, 更偏向本地开发阶段的模拟数据的一种方式
//        if (Objects.equals(userTask.getId(), "custom_2")) {
//            BpmnTaskDelegateAssigner task_2 = new BpmnTaskDelegateAssigner();
//            task_2.setAssignee("200024");
//            task_2.setAssigneeType("3");
//            task_2.setAssignerName("杨秋菊");
//            task_2.setTenantId("0");
//            users.add(task_2);
//        }
        return users;
    }

    private void firstParseNacos(FlowElement flowElement, DelegateExecution execution,
                                 List<BpmnTaskDelegateAssigner> users) {
        if (global) {
            users.addAll(assigneeMap.getOrDefault(flowElement.getId(), Collections.emptyList()));
        } else if (Objects.equals(category, execution.getProcessDefinitionId().split(":")[0])) {
            users.addAll(assigneeMap.getOrDefault(flowElement.getId(), Collections.emptyList()));
        }
    }
}
