package cn.axzo.workflow.core.converter.json;

import cn.axzo.workflow.common.model.request.bpmn.BpmnJsonNode;
import cn.axzo.workflow.core.common.exception.WorkflowEngineException;
import cn.hutool.json.JSONUtil;
import org.flowable.bpmn.model.ExtensionElement;
import org.flowable.bpmn.model.FlowElement;
import org.flowable.bpmn.model.Process;
import org.flowable.bpmn.model.ReceiveTask;
import org.flowable.bpmn.model.ServiceTask;
import org.flowable.bpmn.model.UserTask;

import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_NODE_TYPE;
import static cn.axzo.workflow.common.constant.BpmnConstants.FLOW_NODE_JSON;
import static cn.axzo.workflow.core.common.code.ConvertorRespCode.CONVERTOR_NODE_TYPE_NOT_SUPPORT;

/**
 * 抽象的 JSON 转 BPMN 协议的转换器
 *
 * @author wangli
 * @since 2023/10/12 11:06
 */
public abstract class AbstractBpmnJsonConverter<T extends FlowElement> {

    public T convertJsonToElement(BpmnJsonNode node, Process process) {
        throw new WorkflowEngineException(CONVERTOR_NODE_TYPE_NOT_SUPPORT, node.getType().getType());
    }

    public final void addNodeTypeAttribute(T flowElement, BpmnJsonNode jsonNode) {
        if (flowElement instanceof UserTask
                || flowElement instanceof ServiceTask
                || flowElement instanceof ReceiveTask) {
            ExtensionElement nodeTypeElement = new ExtensionElement();
            nodeTypeElement.setName(CONFIG_NODE_TYPE);
            nodeTypeElement.setElementText(jsonNode.getType().getType());
            flowElement.addExtensionElement(nodeTypeElement);
        }
    }

    public final void addJsonValueAttribute(T flowElement, BpmnJsonNode jsonNode) {
        if (flowElement instanceof UserTask
                || flowElement instanceof ServiceTask
                || flowElement instanceof ReceiveTask) {
            ExtensionElement jsonValueElement = new ExtensionElement();
            jsonValueElement.setName(FLOW_NODE_JSON);
            jsonValueElement.setElementText(JSONUtil.toJsonStr(jsonNode));
            flowElement.addExtensionElement(jsonValueElement);
        }
    }
}
