PARSE_ONE_ON_FIRST_EXEC对脚本node生效

This commit is contained in:
jay li
2024-11-08 19:34:55 +08:00
parent da052e3aa1
commit ae4c3e1260
4 changed files with 119 additions and 3 deletions

View File

@@ -20,6 +20,7 @@ import com.yomahub.liteflow.core.ScriptComponent;
import com.yomahub.liteflow.core.proxy.DeclWarpBean;
import com.yomahub.liteflow.enums.FlowParserTypeEnum;
import com.yomahub.liteflow.enums.NodeTypeEnum;
import com.yomahub.liteflow.enums.ParseModeEnum;
import com.yomahub.liteflow.exception.ComponentCannotRegisterException;
import com.yomahub.liteflow.exception.NullNodeTypeException;
import com.yomahub.liteflow.flow.element.Chain;
@@ -53,6 +54,7 @@ import java.util.stream.Stream;
*
* @author Bryan.Zhang
* @author DaleLee
* @author Jay li
*/
public class FlowBus {
@@ -183,8 +185,16 @@ public class FlowBus {
*/
public static void addScriptNode(String nodeId, String name, NodeTypeEnum nodeType, String script,
String language) {
addNode(nodeId, name, nodeType, ScriptComponent.ScriptComponentClassMap.get(nodeType), script, language);
}
LiteflowConfig liteflowConfig = LiteflowConfigGetter.get();
// 如果是PARSE_ONE_ON_FIRST_EXEC模式则不进行脚本加载而是直接把脚本内容放到node中
if (liteflowConfig.getParseMode().equals(ParseModeEnum.PARSE_ONE_ON_FIRST_EXEC)) {
Node node = new Node(nodeId, name, nodeType, script, language);
nodeMap.put(nodeId, node);
} else {
addNode(nodeId, name, nodeType, ScriptComponent.ScriptComponentClassMap.get(nodeType), script, language);
}
}
private static void addNode(String nodeId, String name, NodeTypeEnum type, Class<?> cmpClazz, String script,
String language) {
@@ -245,6 +255,7 @@ public class FlowBus {
}
String activeNodeId = StrUtil.isEmpty(cmpInstance.getNodeId()) ? nodeId : cmpInstance.getNodeId();
node.setCompiled(true);
put2NodeMap(activeNodeId, node);
addFallbackNode(node);
}
@@ -258,7 +269,16 @@ public class FlowBus {
}
public static Node getNode(String nodeId) {
return nodeMap.get(nodeId);
Node node = nodeMap.get(nodeId);
if (!Objects.isNull(node) && !node.isCompiled()) {
addNode(nodeId, node.getName(), node.getType(), ScriptComponent.ScriptComponentClassMap.get(node.getType()),
node.getScript(), node.getLanguage());
// 编译完脚本节点需重新获取
return nodeMap.get(nodeId);
} else {
return node;
}
}
// 获取某一个 chainId 下的所有 nodeId

View File

@@ -34,6 +34,7 @@ import java.util.concurrent.locks.ReentrantLock;
*
* @author Bryan.Zhang
* @author luo yi
* @author Jay li
*/
public class Node implements Executable, Cloneable, Rollbackable{
@@ -61,6 +62,8 @@ public class Node implements Executable, Cloneable, Rollbackable{
private String currChainId;
private boolean isCompiled = true;
// node 的 isAccess 结果,主要用于 WhenCondition 的提前 isAccess 判断,避免 isAccess 方法重复执行
private TransmittableThreadLocal<Boolean> accessResult = new TransmittableThreadLocal<>();
@@ -91,6 +94,17 @@ public class Node implements Executable, Cloneable, Rollbackable{
this.clazz = instance.getClass().getName();
}
public Node(String nodeId, String name, NodeTypeEnum nodeType, String script, String language) {
this.id = nodeId;
this.name = name;
this.type = nodeType;
this.script = script;
this.language = language;
this.isCompiled = false;
}
@Override
public String getId() {
return id;
@@ -457,6 +471,14 @@ public class Node implements Executable, Cloneable, Rollbackable{
this.language = language;
}
public boolean isCompiled() {
return isCompiled;
}
public void setCompiled(boolean compiled) {
isCompiled = compiled;
}
@Override
public <T> T getItemResultMetaValue(Integer slotIndex) {
return instance.getItemResultMetaValue(slotIndex);

View File

@@ -0,0 +1,72 @@
package com.yomahub.liteflow.test.script.qlexpress;
import cn.hutool.core.io.resource.ResourceUtil;
import com.yomahub.liteflow.core.FlowExecutor;
import com.yomahub.liteflow.enums.FlowParserTypeEnum;
import com.yomahub.liteflow.flow.FlowBus;
import com.yomahub.liteflow.flow.LiteflowResponse;
import com.yomahub.liteflow.slot.DefaultContext;
import com.yomahub.liteflow.test.BaseTest;
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.test.context.TestPropertySource;
import org.springframework.test.context.junit.jupiter.SpringExtension;
import javax.annotation.Resource;
/**
* PARSE_ONE_ON_FIRST_EXEC 第一次执行时解析脚本节点
* 测试springboot下的脚本组件
*
* @author jay li
* @since 2.12.4
*/
@ExtendWith(SpringExtension.class)
@TestPropertySource(value = "classpath:/xml-script/application-parse-first.properties")
@SpringBootTest(classes = LiteflowXmlScriptQLExpressELParseModeTest.class)
@EnableAutoConfiguration
@ComponentScan({ "com.yomahub.liteflow.test.script.qlexpress.cmp" })
public class LiteflowXmlScriptQLExpressELParseModeTest extends BaseTest {
@Resource
private FlowExecutor flowExecutor;
// 测试普通脚本节点
@Test
public void testScript1() {
LiteflowResponse response = flowExecutor.execute2Resp("chain1", "arg");
DefaultContext context = response.getFirstContextBean();
Assertions.assertTrue(response.isSuccess());
Assertions.assertEquals(Integer.valueOf(6), context.getData("s1"));
}
// 测试条件脚本节点
@Test
public void testScript2() {
LiteflowResponse response = flowExecutor.execute2Resp("chain2", "arg");
Assertions.assertTrue(response.isSuccess());
Assertions.assertEquals("d==>s2[条件脚本]==>b", response.getExecuteStepStr());
}
@Test
public void testScript3() throws Exception {
// 根据配置加载的应该是flow.xml执行原来的规则
LiteflowResponse responseOld = flowExecutor.execute2Resp("chain2", "arg");
Assertions.assertTrue(responseOld.isSuccess());
Assertions.assertEquals("d==>s2[条件脚本]==>b", responseOld.getExecuteStepStr());
// 更改规则重新加载更改的规则内容从flow_update.xml里读取这里只是为了模拟下获取新的内容。不一定是从文件中读取
String newContent = ResourceUtil.readUtf8Str("classpath: /xml-script/flow_update.el.xml");
// 进行刷新
FlowBus.refreshFlowMetaData(FlowParserTypeEnum.TYPE_EL_XML, newContent);
// 重新执行chain2这个链路结果会变
LiteflowResponse responseNew = flowExecutor.execute2Resp("chain2", "arg");
Assertions.assertTrue(responseNew.isSuccess());
Assertions.assertEquals("d==>s2[条件脚本_改]==>a==>s3[普通脚本_新增]", responseNew.getExecuteStepStr());
}
}

View File

@@ -0,0 +1,2 @@
liteflow.rule-source=xml-script/flow.el.xml
liteflow.parse-mode=PARSE_ONE_ON_FIRST_EXEC