diff --git a/pom.xml b/pom.xml index cb8485f636f0e73a7173fdebde18f960b272cdac..d524125a82507e7fae8d476c7b6001a8fae7b65a 100644 --- a/pom.xml +++ b/pom.xml @@ -5,37 +5,17 @@ org.smartboot flow-engine - 1.0.0 + 1.0.1 4.0.0 pom smart-flow-core smart-flow-spring-extension + smart-flow-manager + smart-flow-example - - - com.google.guava - guava - 31.1-jre - - - - - org.slf4j - slf4j-api - 2.0.3 - - - - org.slf4j - slf4j-log4j12 - 2.0.3 - - - - flow-engine diff --git a/smart-flow-core/pom.xml b/smart-flow-core/pom.xml index 85b85114352fe9fecb1d5236a1eac1a9afe6fc9c..5fefaf48bf2c81e57e34c278dc0398ed7040f5ed 100644 --- a/smart-flow-core/pom.xml +++ b/smart-flow-core/pom.xml @@ -5,7 +5,7 @@ org.smartboot flow-engine - 1.0.0 + 1.0.1 4.0.0 @@ -26,26 +26,25 @@ - ch.qos.logback - logback-core - 1.4.4 + org.junit.jupiter + junit-jupiter-engine + 5.9.1 + test + org.slf4j - jcl-over-slf4j + slf4j-api 2.0.3 + - ch.qos.logback - logback-classic - 1.2.3 - - - org.slf4j - slf4j-api - - + org.slf4j + slf4j-log4j12 + 2.0.3 + test + \ No newline at end of file diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/DefaultIdentifierManager.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/DefaultIdentifierManager.java index 0dbe68234661072952153c3810106c791bf86126..92a75c491050e022e1e51449746f7dcd08225a39 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/DefaultIdentifierManager.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/DefaultIdentifierManager.java @@ -1,9 +1,10 @@ package org.smartboot.flow.core; -import org.smartboot.flow.core.parser.ElementUtils; +import org.smartboot.flow.core.util.ContactUtils; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.atomic.AtomicInteger; /** * @author qinluo @@ -16,14 +17,15 @@ public class DefaultIdentifierManager implements IdentifierManager { * Generated identifiers. */ private final Map identifiers = new ConcurrentHashMap<>(); + private final AtomicInteger sequence = new AtomicInteger(0); @Override public String generateIdentifier(String prefix) { - String identifier = ElementUtils.random(prefix); + String identifier = ContactUtils.contact(prefix, sequence.getAndAdd(1)); // Ensure identifier is unique. while (identifiers.containsKey(identifier) || identifiers.put(identifier, 1) != null) { - identifier = ElementUtils.random(prefix); + identifier = ContactUtils.contact(prefix, sequence.getAndAdd(1)); } return identifier; diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/EngineContext.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/EngineContext.java index d3cc257fe199892217f8ad8f273abf0948a2281e..6aa5b360b5652d55c2244faed828acc09b68df85 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/EngineContext.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/EngineContext.java @@ -20,6 +20,10 @@ import java.util.concurrent.Future; */ public class EngineContext { + public static final int DISABLED = -1; + public static final int EXECUTING = 1; + public static final int ROLLBACK = 2; + public static final Logger LOGGER = LoggerFactory.getLogger(EngineContext.class); private T req; private S result; @@ -31,6 +35,12 @@ public class EngineContext { private ExceptionHandler handler; private boolean rollback; private final Map> asyncInvokes = new ConcurrentHashMap<>(); + private String engineName; + private ExecutionListener listener; + /** + * 执行状态 + */ + private int executing; /** * Returns current invoked trace. @@ -93,6 +103,26 @@ public class EngineContext { this.handler = handler; } + public int getExecuting() { + return executing; + } + + public void setExecuting(int executing) { + this.executing = executing; + } + + public void setListener(ExecutionListener listener) { + this.listener = listener; + } + + public String getEngineName() { + return engineName; + } + + public void setEngineName(String engineName) { + this.engineName = engineName; + } + public void addAsyncInvoke(Component component, Future future, List> belongs) { AsyncCallResult result = new AsyncCallResult<>(); result.setFuture(future); @@ -111,19 +141,30 @@ public class EngineContext { this.asyncInvokes.forEach((k, v) -> v.checkAndWait(this)); } - /* - Delegate methods - */ - public void enter(String message) { + public void enter(Object obj) { + String message = this.executing == ROLLBACK ? "rollback " : ""; + if (obj instanceof Describable) { + message += ("rollback " + ((Describable) obj).describe()); + } else if (obj instanceof String) { + message += ("rollback " + obj); + } + this.tracer.enter(message); - } - public void exit() { - this.tracer.exit(); + if (executing == EXECUTING) { + listener.beforeExecute(this, obj); + } else if (executing == ROLLBACK) { + listener.beforeRollback(this, obj); + } } - public void enterRollback(String message) { - this.tracer.enter("rollback " + message); + public void exit(Object obj) { + this.tracer.exit(); + if (executing == EXECUTING) { + listener.afterExecute(this, obj); + } else if (executing == ROLLBACK) { + listener.afterRollback(this, obj); + } } @SuppressWarnings("unchecked") @@ -154,6 +195,9 @@ public class EngineContext { this.broken = false; this.rollback = false; this.fatal = null; + this.listener = null; + this.engineName = null; + this.executing = DISABLED; } private static class Value implements Serializable { diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListener.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListener.java new file mode 100644 index 0000000000000000000000000000000000000000..88328754706b07fedb262a843fadfb6034e47c1e --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListener.java @@ -0,0 +1,14 @@ +package org.smartboot.flow.core; + +/** + * @author qinluo + * @date 2022-11-25 20:34:35 + * @since 1.0.0 + */ +public interface ExecutionListener { + + void beforeExecute(EngineContext context, Object object); + void afterExecute(EngineContext context, Object object); + void beforeRollback(EngineContext context, Object object); + void afterRollback(EngineContext context, Object object); +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListenerRegistry.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListenerRegistry.java new file mode 100644 index 0000000000000000000000000000000000000000..2e7b7521f02e05d9799e56b6d7b67969dd352ad9 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListenerRegistry.java @@ -0,0 +1,28 @@ +package org.smartboot.flow.core; + +import org.smartboot.flow.core.util.AssertUtil; + +import java.util.ArrayList; +import java.util.List; + +/** + * @author qinluo + * @date 2022-11-25 21:15:22 + * @since 1.0.0 + */ +public class ExecutionListenerRegistry { + + private static final List REGISTERED = new ArrayList<>(); + + public synchronized static void register(ExecutionListener listener) { + AssertUtil.notNull(listener, "listener must not be null"); + + if (!REGISTERED.contains(listener)) { + REGISTERED.add(listener); + } + } + + public static List getRegistered() { + return new ArrayList<>(REGISTERED); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListenerSupport.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListenerSupport.java new file mode 100644 index 0000000000000000000000000000000000000000..f8062d7cfdc5031e65b3faa1e0108d0c24867f0e --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListenerSupport.java @@ -0,0 +1,29 @@ +package org.smartboot.flow.core; + +/** + * @author qinluo + * @date 2022-11-25 21:29:22 + * @since 1.0.0 + */ +public class ExecutionListenerSupport implements ExecutionListener { + + @Override + public void beforeExecute(EngineContext context, Object object) { + + } + + @Override + public void afterExecute(EngineContext context, Object object) { + + } + + @Override + public void beforeRollback(EngineContext context, Object object) { + + } + + @Override + public void afterRollback(EngineContext context, Object object) { + + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListeners.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListeners.java new file mode 100644 index 0000000000000000000000000000000000000000..5e62709104ec5b9e6f13070b312dacceec22bd74 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/ExecutionListeners.java @@ -0,0 +1,66 @@ +package org.smartboot.flow.core; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.List; + +/** + * @author qinluo + * @date 2022-11-25 21:54:14 + * @since 1.0.0 + */ +public class ExecutionListeners implements ExecutionListener { + + private static final Logger LOGGER = LoggerFactory.getLogger(ExecutionListeners.class); + + private final List listeners; + + public ExecutionListeners(List listeners) { + this.listeners = listeners; + } + + @Override + public void beforeExecute(EngineContext context, Object object) { + for (ExecutionListener listener : listeners) { + try { + listener.beforeExecute(context, object); + } catch (Throwable e) { + LOGGER.warn("execute listener {} failed", listener.getClass().getName(), e); + } + } + } + + @Override + public void afterExecute(EngineContext context, Object object) { + for (ExecutionListener listener : listeners) { + try { + listener.afterExecute(context, object); + } catch (Throwable e) { + LOGGER.warn("execute listener {} failed", listener.getClass().getName(), e); + } + } + } + + @Override + public void beforeRollback(EngineContext context, Object object) { + for (ExecutionListener listener : listeners) { + try { + listener.beforeRollback(context, object); + } catch (Throwable e) { + LOGGER.warn("execute listener {} failed", listener.getClass().getName(), e); + } + } + } + + @Override + public void afterRollback(EngineContext context, Object object) { + for (ExecutionListener listener : listeners) { + try { + listener.afterRollback(context, object); + } catch (Throwable e) { + LOGGER.warn("execute listener {} failed", listener.getClass().getName(), e); + } + } + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/FlowEngine.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/FlowEngine.java index a29bcbbdfed0f5ad0b10930152026ccb8c71e14a..3389146a518fe809f5add7e3e5cf023510a9ab4e 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/FlowEngine.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/FlowEngine.java @@ -3,6 +3,7 @@ package org.smartboot.flow.core; import org.smartboot.flow.core.exception.ExceptionHandler; import org.smartboot.flow.core.manager.DefaultEngineManager; +import org.smartboot.flow.core.metrics.MetricExecutionListener; import org.smartboot.flow.core.util.AssertUtil; import org.smartboot.flow.core.visitor.EngineVisitor; import org.smartboot.flow.core.visitor.PipelineVisitor; @@ -15,7 +16,7 @@ import java.util.concurrent.ExecutorService; * @date 2022-11-12 21:58:12 * @since 1.0.0 */ -public class FlowEngine implements Describable, Validator { +public class FlowEngine implements Describable, Validator, Measurable { private Pipeline pipeline; private ExceptionHandler exceptionHandler; @@ -43,7 +44,7 @@ public class FlowEngine implements Describable, Validator { initContext(context); - context.enter(describe()); + context.enter(this); boolean rollback = false; try { @@ -56,10 +57,13 @@ public class FlowEngine implements Describable, Validator { context.ensureFinished(); if (rollback || context.getRollback()) { + context.setExecuting(EngineContext.ROLLBACK); pipeline.rollback(context); } - context.exit(); + // For end flow-engine. + context.setExecuting(EngineContext.EXECUTING); + context.exit(this); if (context.getFatal() != null && exceptionHandler != null) { context.getHandler().handle(context, context.getFatal()); @@ -72,6 +76,12 @@ public class FlowEngine implements Describable, Validator { context.clear(); context.setHandler(exceptionHandler); context.executor = executor; + context.setEngineName(this.name); + context.setExecuting(EngineContext.EXECUTING); + + // Execution Listener. + ExecutionListeners listeners = new ExecutionListeners(ExecutionListenerRegistry.getRegistered()); + context.setListener(listeners); } public void setExceptionHandler(ExceptionHandler exceptionHandler) { @@ -125,9 +135,11 @@ public class FlowEngine implements Describable, Validator { } AssertUtil.notBlank(name, "engine's name must not be null"); - AssertUtil.notNull(pipeline, "engine[ " + getName() + " ]pipeline must not be null"); + AssertUtil.notNull(pipeline, "engine[ " + name + " ]pipeline must not be null"); pipeline.validate(); validateCalled = true; + // Register metrics listener. + ExecutionListenerRegistry.register(MetricExecutionListener.getInstance()); DefaultEngineManager.getDefaultManager().register(this); } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/Measurable.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/Measurable.java new file mode 100644 index 0000000000000000000000000000000000000000..57a12ca6d35c46b6cac5710b40c3e106a78ef05c --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/Measurable.java @@ -0,0 +1,31 @@ +package org.smartboot.flow.core; + +import org.smartboot.flow.core.metrics.Metrics; +import org.smartboot.flow.core.metrics.MetricsManager; + +/** + * @author qinluo + * @date 2022-11-25 20:31:12 + * @since 1.0.0 + */ +public interface Measurable { + + /** + * 获取可度量的指标数据 + * + * @return 指标数据 + */ + default Metrics getMetrics() { + return MetricsManager.allocate(this); + } + + /** + * Reset metrics + */ + default void reset() { + Metrics metrics = MetricsManager.allocate(this); + if (metrics != null) { + metrics.reset(); + } + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/NamedCondition.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/NamedCondition.java new file mode 100644 index 0000000000000000000000000000000000000000..ee5e559cf480df5f6f01becb505dc290c95ef30e --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/NamedCondition.java @@ -0,0 +1,20 @@ +package org.smartboot.flow.core; + +/** + * @author qinluo + * @date 2022-11-11 21:57:29 + * @since 1.0.0 + */ +public abstract class NamedCondition extends Condition { + + private String name; + + public void setName(String name) { + this.name = name; + } + + @Override + public String describe() { + return this.name; + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/Pipeline.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/Pipeline.java index efbdc092adf2699c955b50a1d9be40e40cb84173..b9d845758b0b2539464067363fb5f49b987c4eec 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/Pipeline.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/Pipeline.java @@ -15,7 +15,7 @@ import java.util.concurrent.Future; * @date 2022-11-12 21:57:43 * @since 1.0.0 */ -public class Pipeline implements Rollback, Describable, Validator { +public class Pipeline implements Rollback, Describable, Validator, Measurable { private final List> components = new ArrayList<>(); private String name; @@ -35,7 +35,7 @@ public class Pipeline implements Rollback, Describable, Validator { context.putExt(Key.of(this), executed); // Enter record track - context.enter(describe()); + context.enter(this); for (Component component : components) { if (context.isBroken()) { @@ -67,7 +67,7 @@ public class Pipeline implements Rollback, Describable, Validator { } // Exit record track - context.exit(); + context.exit(this); } private void ensureAllDependsExecuted(Component component, EngineContext context) { @@ -118,7 +118,7 @@ public class Pipeline implements Rollback, Describable, Validator { return; } - context.enterRollback(describe()); + context.enter(this); // Execute rollback desc. for (int i = executed.size() - 1; i >= 0; i--) { @@ -130,7 +130,7 @@ public class Pipeline implements Rollback, Describable, Validator { } } - context.exit(); + context.exit(this); } public boolean isRollbackable(EngineContext context) { diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/EngineBuilder.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/EngineBuilder.java index 4a813398770f2d4641fe790704fb6e23185ca973..d54e1c0acda8926ba5608f7d56d1cbd5e2061e3e 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/EngineBuilder.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/EngineBuilder.java @@ -18,8 +18,8 @@ public class EngineBuilder { private String name; private ExecutorService executor; - public EngineBuilder() { - this.name = "defaultEngine"; + public EngineBuilder(String name) { + this.name = name; } public EngineBuilder pipeline(Pipeline pipeline) { @@ -29,7 +29,7 @@ public class EngineBuilder { } public EngineBuilder name(String name) { - AssertUtil.notNull(name, "must not be null"); + AssertUtil.notBlank(name, "engine's name is required"); this.name = name; return this; } @@ -42,6 +42,8 @@ public class EngineBuilder { public FlowEngine build() { + AssertUtil.notBlank(name, "engine's name is required"); + FlowEngine engine = new FlowEngine<>(); engine.setName(name); engine.setPipeline(pipeline); diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/PipelineBuilder.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/PipelineBuilder.java index c0337043583894cad7dcccac3689e8858cbe718a..4b5adff317125ba071336f4b8c55ee80fd9389ac 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/PipelineBuilder.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/builder/PipelineBuilder.java @@ -32,15 +32,11 @@ public class PipelineBuilder { } public PipelineBuilder(String name) { - this((PipelineBuilder)null, name); - } - - public PipelineBuilder() { - this((PipelineBuilder)null, "DefaultPipeline"); + this(null, name); } public PipelineBuilder name(String name) { - AssertUtil.notNull(name, "must not be null"); + AssertUtil.notBlank(name, "must not be null"); this.name = name; return this; } @@ -68,12 +64,8 @@ public class PipelineBuilder { return new ChooseBuilder<>(this, condition); } - public PipelineBuilder pipeline() { - return pipeline("Subprocess"); - } - public PipelineBuilder pipeline(String name) { - AssertUtil.notNull(name, "must not be null"); + AssertUtil.notBlank(name, "must not be null"); return new PipelineBuilder<>(this, name); } @@ -85,12 +77,15 @@ public class PipelineBuilder { Pipeline pipeline = build(); PipelineComponent pipelineComponent = new PipelineComponent<>(pipeline); + pipelineComponent.setName("anonymous@" + name); parent.next(pipelineComponent); return parent; } public Pipeline build() { + AssertUtil.notBlank(name, "pipeline's name is required"); + Pipeline pipeline = new Pipeline<>(); pipeline.setComponents(this.components); pipeline.setName(name); diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/ChooseComponent.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/ChooseComponent.java index d831e6f3ca78577b65b33b75b0adeae2261aff42..4e4563e5c1a378d9b019b109a931fe287e7a045e 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/ChooseComponent.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/ChooseComponent.java @@ -50,7 +50,7 @@ public class ChooseComponent extends Component { @Override public int invoke(EngineContext context) throws Exception { - context.enter(describe()); + context.enter(this); try { Object branch = condition.test(context); Component execute = null; @@ -73,11 +73,11 @@ public class ChooseComponent extends Component { try { return execute.invoke(context); } finally { - context.exit(); + context.exit("branch##" + branch); } } } finally { - context.exit(); + context.exit(this); } return 1; @@ -96,18 +96,18 @@ public class ChooseComponent extends Component { return; } - context.enterRollback(describe()); + context.enter(this); try { executed.rollback(context); } finally { - context.exit(); + context.exit(this); } } @Override public String describe() { - return "choose##" + condition.describe(); + return "choose@" + condition.describe(); } @Override diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/Component.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/Component.java index bb5b75c9cb443a50460d344cd6a03105deef762b..25f24159f0cfbd3fa26610860f1445d8842fad04 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/Component.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/Component.java @@ -3,6 +3,7 @@ package org.smartboot.flow.core.component; import org.smartboot.flow.core.Describable; import org.smartboot.flow.core.EngineContext; +import org.smartboot.flow.core.Measurable; import org.smartboot.flow.core.Rollback; import org.smartboot.flow.core.Validator; import org.smartboot.flow.core.visitor.ComponentVisitor; @@ -16,7 +17,7 @@ import java.util.List; * @date 2022-11-12 17:58:34 * @since 1.0.0 */ -public abstract class Component implements Rollback, Describable, Validator { +public abstract class Component implements Rollback, Describable, Validator, Measurable { /** * 是否可降级 @@ -30,7 +31,7 @@ public abstract class Component implements Rollback, Describable, Va private boolean async; private long timeout; private List dependsOn; - private String name = "none"; + private String name; private boolean enabled = true; protected final List attributes = new ArrayList<>(0); diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/IfComponent.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/IfComponent.java index 25706d2928c383f623b2dc0eeec4a4ca2069b278..e04fa635486bb04bdb08029faf666c52974734d3 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/IfComponent.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/IfComponent.java @@ -40,7 +40,7 @@ public class IfComponent extends Component{ @Override public int invoke(EngineContext context) throws Exception { - context.enter(describe()); + context.enter(this); try { Object test = condition.test(context); Component execute = null; @@ -56,7 +56,7 @@ public class IfComponent extends Component{ return execute.invoke(context); } } finally { - context.exit(); + context.exit(this); } return 1; @@ -75,17 +75,17 @@ public class IfComponent extends Component{ return; } - context.enterRollback(describe()); + context.enter(this); try { executed.rollback(context); } finally { - context.exit(); + context.exit(this); } } @Override public String describe() { - return "if-component condition = " + condition.describe(); + return "if@" + condition.describe(); } @Override diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/PipelineComponent.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/PipelineComponent.java index 8c2b18c89be3152795433cedbd29e1b41ddc12e9..8f8b01b640ac9682c2d9877af7397afc93d7be60 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/component/PipelineComponent.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/component/PipelineComponent.java @@ -43,17 +43,17 @@ public class PipelineComponent extends Component { if (!isRollbackable(context)) { return; } - context.enterRollback(describe()); + context.enter(this); try { pipeline.rollback(context); } finally { - context.exit(); + context.exit(this); } } @Override public String describe() { - return "pipeline##" + pipeline.describe(); + return "pipeline@" + pipeline.describe(); } @Override diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/executable/ExecutableAdapter.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/executable/ExecutableAdapter.java index 43c5848e3f444f29ab3e8abc9d7d58c373cd9d4a..b5423dcca0c4847638ac3f1ccc76953daf703f85 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/executable/ExecutableAdapter.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/executable/ExecutableAdapter.java @@ -29,12 +29,12 @@ public class ExecutableAdapter extends Component implements Rollback< } public int invoke(EngineContext context) { - context.enter(describe()); + context.enter(this); try { executable.execute(context); } finally { - context.exit(); + context.exit(this); } return 1; @@ -43,12 +43,12 @@ public class ExecutableAdapter extends Component implements Rollback< @Override public void rollback(EngineContext context) { - context.enter("rollback " + describe()); + context.enter(this); try { executable.rollback(context); } finally { - context.exit(); + context.exit(this); } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/extension/ExtensionFactory.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/extension/ExtensionFactory.java deleted file mode 100644 index 9e30d23855be138de414f2de52d487e453fd567e..0000000000000000000000000000000000000000 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/extension/ExtensionFactory.java +++ /dev/null @@ -1,27 +0,0 @@ -package org.smartboot.flow.core.extension; - -import org.smartboot.flow.core.util.AssertUtil; - -import java.util.ServiceLoader; - -/** - * @author qinluo - * @date 2022/11/19 14:23 - * @since 1.0.0 - */ -public class ExtensionFactory { - - /** - * 获取扩展实现 - */ - public static T getExtension(Class type) { - AssertUtil.notNull(type, "type must not be null!"); - - ServiceLoader loaded = ServiceLoader.load(type); - if (!loaded.iterator().hasNext()) { - return null; - } - - return loaded.iterator().next(); - } -} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/ComponentModel.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/ComponentModel.java index e844c38d9ec7f3f548456bd64aea53f6c2ca509e..417690129baf31254c63288adc35eeb46ba3e77b 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/ComponentModel.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/ComponentModel.java @@ -5,6 +5,7 @@ import org.smartboot.flow.core.common.Uniqueness; import org.smartboot.flow.core.component.AttributeHolder; import org.smartboot.flow.core.component.Attributes; import org.smartboot.flow.core.component.Component; +import org.smartboot.flow.core.metrics.Metrics; import java.util.HashMap; import java.util.List; @@ -31,13 +32,15 @@ public class ComponentModel extends Uniqueness { // Used with type pipeline. PipelineModel pipeline; String condition; - String branch; + private String branch; + private final Metrics metrics; ComponentModel(String identifier, Component component) { this.identifier = identifier; this.component = component; this.name = component.getName(); this.describe = component.describe(); + this.metrics = component.getMetrics(); } public Map getHolders() { @@ -70,17 +73,40 @@ public class ComponentModel extends Uniqueness { return branch; } + public void setBranch(String branch) { + this.branch = branch; + } + public Map getComponents() { + return new HashMap<>(components); + } + + Map collect() { if (type == ComponentType.PIPELINE) { - this.pipeline.collect(); - return pipeline.getComponents(); + Map collected = this.pipeline.collect(); + collected.put(this.identifier, this); + return collected; + } else if (type == ComponentType.BASIC) { + Map temp = new HashMap<>(); + temp.put(this.identifier, this); + return temp; + } else { + Map temp = new HashMap<>(); + this.components.forEach((k, v) -> temp.putAll(v.collect())); + temp.put(this.identifier, this); + return temp; } - - return components; } void addComponent(ComponentModel model) { - this.components.put(model.getIdentifier(), model); + if (this.type == ComponentType.CHOOSE) { + this.components.put(model.getBranch(), model); + } else if (this.type == ComponentType.IF) { + String key = this.components.size() > 0 ? "else" : "then"; + this.components.put(key, model); + } else { + this.components.put(model.getIdentifier(), model); + } } public String getName() { @@ -104,4 +130,13 @@ public class ComponentModel extends Uniqueness { } } + + public Metrics getMetrics() { + return metrics; + } + + public void reset() { + this.metrics.reset(); + components.forEach((k, v) -> v.reset()); + } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/DefaultEngineManager.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/DefaultEngineManager.java index 722214f2346abbbae4acc98eaa4f4f479e7fe95f..1af1541724b33aef5c3844bcbca0de7fe86ceb15 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/DefaultEngineManager.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/DefaultEngineManager.java @@ -1,10 +1,12 @@ package org.smartboot.flow.core.manager; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import org.smartboot.flow.core.FlowEngine; -import org.smartboot.flow.core.IdentifierManager; import org.smartboot.flow.core.component.AttributeHolder; import org.smartboot.flow.core.util.AssertUtil; +import java.util.ArrayList; import java.util.List; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; @@ -16,6 +18,7 @@ import java.util.concurrent.ConcurrentHashMap; */ public class DefaultEngineManager implements EngineManager { + private static final Logger LOGGER = LoggerFactory.getLogger(DefaultEngineManager.class); private static final DefaultEngineManager INSTANCE = new DefaultEngineManager(); private final Map registeredEngines = new ConcurrentHashMap<>(); @@ -26,8 +29,18 @@ public class DefaultEngineManager implements EngineManager { @Override public void register(FlowEngine engine) { - IdentifierManager identifierManager = new NamedIdentifierManager(engine.getName()); - RegisterEngineVisitor visitor = new RegisterEngineVisitor(identifierManager); + AssertUtil.notNull(engine, "registered engine must not be null"); + AssertUtil.notBlank(engine.getName(), "registered engine name must not be blank"); + + if (registeredEngines.get(engine.getName()) != null) { + LOGGER.error("engine {} already registered", engine.getName()); + return; + } + + // Ensure engine and components is valid + engine.validate(); + + RegisterEngineVisitor visitor = new RegisterEngineVisitor(); visitor.visit(engine); EngineModel model = visitor.getEngine(); @@ -36,12 +49,13 @@ public class DefaultEngineManager implements EngineManager { @Override public EngineModel getEngineModel(String name) { - AssertUtil.notNull(name, "name must not be null!"); + AssertUtil.notBlank(name, "name must not be blank!"); return registeredEngines.get(name); } @Override public void changeAttributes(String identifier, List attributeHolders) { + AssertUtil.notBlank(identifier, "identifier must not be blank!"); if (registeredEngines.containsKey(identifier)) { // change engine attributes. return; @@ -54,4 +68,40 @@ public class DefaultEngineManager implements EngineManager { } } } + + @Override + public List getRegisteredEngineNames() { + return new ArrayList<>(registeredEngines.keySet()); + } + + @Override + public void resetStatistic(String identifier) { + AssertUtil.notBlank(identifier, "identifier must not be blank!"); + for (Map.Entry entry : registeredEngines.entrySet()) { + if (entry.getKey().equals(identifier) || entry.getValue().getPipeline().getIdentifier().equals(identifier)) { + entry.getValue().reset(); + break; + } + + } + + for (Map.Entry entry : registeredEngines.entrySet()) { + if (entry.getValue().containsComponent(identifier)) { + entry.getValue().reset(identifier); + break; + } + + } + } + + @Override + public void detachAll() { + this.registeredEngines.clear(); + } + + @Override + public void detach(String name) { + AssertUtil.notBlank(name, "name must not be blank!"); + this.registeredEngines.remove(name); + } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineManager.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineManager.java index accf946240c5e140d3c351e1d18ac2261699b066..92406ee080e7aae6536d143eef248c272de1b879 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineManager.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineManager.java @@ -38,6 +38,13 @@ public interface EngineManager { */ void changeAttributes(String identifier, List attributeHolders); + /** + * Returns all registered engine's name. + * + * @return engine's names. + */ + List getRegisteredEngineNames(); + /** * Dynamic change component attributes. * @@ -47,4 +54,23 @@ public interface EngineManager { default void changeAttributes(String identifier, AttributeHolder holder) { this.changeAttributes(identifier, Collections.singletonList(holder)); } + + /** + * Reset statistic data. + * + * @param identifier component identifier + */ + void resetStatistic(String identifier); + + /** + * Make all engine detach from manager. + */ + void detachAll(); + + /** + * Make specific engine detach from manager + * + * @param name engine name. + */ + void detach(String name); } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineModel.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineModel.java index 88febc21425ce505d4284b7f63e73949026ddc0e..cd5ee5a9d272b6923a199fce6a9797d5382817e3 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineModel.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/EngineModel.java @@ -4,6 +4,7 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.smartboot.flow.core.common.Uniqueness; import org.smartboot.flow.core.component.AttributeHolder; +import org.smartboot.flow.core.metrics.Metrics; import java.util.HashMap; import java.util.List; @@ -20,7 +21,8 @@ public class EngineModel extends Uniqueness { private static final Logger LOGGER = LoggerFactory.getLogger(EngineModel.class); private PipelineModel pipeline; - private final Map components = new ConcurrentHashMap<>(); + private transient final Map components = new ConcurrentHashMap<>(); + private Metrics metrics; public EngineModel(String name) { // Engine's name must be global unique. @@ -54,7 +56,29 @@ public class EngineModel extends Uniqueness { } void collect() { - this.pipeline.collect(); - this.components.putAll(this.pipeline.getComponents()); + this.components.putAll(this.pipeline.collect()); + } + + public Metrics getMetrics() { + return metrics; + } + + public void setMetrics(Metrics metrics) { + this.metrics = metrics; + } + + public void reset() { + this.metrics.reset(); + this.pipeline.reset(); + } + + public void reset(String identifier) { + ComponentModel model = components.get(identifier); + if (model == null) { + LOGGER.warn("change component attributes failed, identifier = {}", identifier); + return; + } + + model.reset(); } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/ManagerAction.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/ManagerAction.java new file mode 100644 index 0000000000000000000000000000000000000000..b0d536f8ed0e0e5674d9ba9470dad965a3cdd61d --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/ManagerAction.java @@ -0,0 +1,32 @@ +package org.smartboot.flow.core.manager; + +import java.util.Objects; + +/** + * @author qinluo + * @date 2022/11/22 22:02 + * @since 1.0.0 + */ +public enum ManagerAction { + /** + * Change component attributes. + */ + CHANGE_ATTRIBUTES, + + /** + * Reset statistic metrics. + */ + RESET_METRICS, + + ; + + public static ManagerAction get(String name) { + if (Objects.equals(name, CHANGE_ATTRIBUTES.name())) { + return CHANGE_ATTRIBUTES; + } else if (Objects.equals(name, RESET_METRICS.name())) { + return RESET_METRICS; + } + + return null; + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/NamedIdentifierManager.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/NamedIdentifierManager.java deleted file mode 100644 index 3e1d8867ffde818c135389c2199cf763dc69f051..0000000000000000000000000000000000000000 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/NamedIdentifierManager.java +++ /dev/null @@ -1,24 +0,0 @@ -package org.smartboot.flow.core.manager; - -import org.smartboot.flow.core.DefaultIdentifierManager; -import org.smartboot.flow.core.IdentifierManager; - -/** - * @author qinluo - * @date 2022/11/19 12:37 - * @since 1.0.0 - */ -public class NamedIdentifierManager implements IdentifierManager { - - private final String name; - private final IdentifierManager delegate = new DefaultIdentifierManager(); - - public NamedIdentifierManager(String name) { - this.name = name; - } - - @Override - public String generateIdentifier(String prefix) { - return delegate.generateIdentifier(name + "-" + prefix); - } -} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/PipelineModel.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/PipelineModel.java index 121226188d247d124ae475b98f791153375d9294..0c03cf7994662ad50771b1ac1a0234dce85f7ba9 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/PipelineModel.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/PipelineModel.java @@ -1,8 +1,11 @@ package org.smartboot.flow.core.manager; import org.smartboot.flow.core.common.Uniqueness; +import org.smartboot.flow.core.metrics.Metrics; +import java.util.ArrayList; import java.util.HashMap; +import java.util.List; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; @@ -13,29 +16,46 @@ import java.util.concurrent.ConcurrentHashMap; */ public class PipelineModel extends Uniqueness { - private final Map components = new ConcurrentHashMap<>(); + private final List components = new ArrayList<>(); private final String name; + private Metrics metrics; PipelineModel(String name, String identifier) { this.name = name; this.identifier = identifier; } - public Map getComponents() { - return new HashMap<>(components); + public List getComponents() { + return new ArrayList<>(components); } void addComponent(ComponentModel component) { - this.components.put(component.getIdentifier(), component); + this.components.add(component); } public String getName() { return name; } - void collect() { - for (ComponentModel model : components.values()) { - this.components.putAll(model.getComponents()); + Map collect() { + HashMap collected = new HashMap<>(components.size()); + for (ComponentModel model : components) { + collected.putAll(model.collect()); } + + return collected; + } + + public Metrics getMetrics() { + return metrics; + } + + public void setMetrics(Metrics metrics) { + this.metrics = metrics; + } + + public void reset() { + this.metrics.reset(); + components.forEach(ComponentModel::reset); } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisterEngineVisitor.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisterEngineVisitor.java index 4163e3e3565586d8c0434d899068c11ff9c123e9..6b66aa47e1e27dfb65865e3a60f0a5136d2c1be7 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisterEngineVisitor.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisterEngineVisitor.java @@ -1,7 +1,8 @@ package org.smartboot.flow.core.manager; -import org.smartboot.flow.core.IdentifierManager; +import org.smartboot.flow.core.FlowEngine; import org.smartboot.flow.core.Pipeline; +import org.smartboot.flow.core.util.ContactUtils; import org.smartboot.flow.core.visitor.EngineVisitor; import org.smartboot.flow.core.visitor.PipelineVisitor; @@ -13,10 +14,12 @@ import org.smartboot.flow.core.visitor.PipelineVisitor; public class RegisterEngineVisitor extends EngineVisitor { private EngineModel model; - private final IdentifierManager identifierManager; - public RegisterEngineVisitor(IdentifierManager identifierManager) { - this.identifierManager = identifierManager; + @Override + public void visit(FlowEngine flowEngine) { + this.model = new EngineModel(flowEngine.getName()); + this.model.setMetrics(flowEngine.getMetrics()); + super.visit(flowEngine); } @Override @@ -24,16 +27,12 @@ public class RegisterEngineVisitor extends EngineVisitor { this.model.collect(); } - @Override - public void visit(String engine) { - this.model = new EngineModel(engine); - } - @Override public PipelineVisitor visitPipeline(Pipeline pipeline) { - PipelineModel pipelineModel = new PipelineModel(pipeline.describe(), identifierManager.generateIdentifier(pipeline.describe())); + PipelineModel pipelineModel = new PipelineModel(pipeline.describe(), ContactUtils.contact(this.model.getIdentifier(), pipeline.describe())); this.model.setPipeline(pipelineModel); - return new RegisteredPipelineVisitor(pipelineModel, identifierManager); + pipelineModel.setMetrics(pipeline.getMetrics()); + return new RegisteredPipelineVisitor(pipelineModel); } public EngineModel getEngine() { diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredComponentVisitor.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredComponentVisitor.java index e383a794aa7f7856e8a5b91a791796dbfc753f94..0193f4acc29b892952365173c9f0e7e94f028fe1 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredComponentVisitor.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredComponentVisitor.java @@ -1,10 +1,11 @@ package org.smartboot.flow.core.manager; -import org.smartboot.flow.core.IdentifierManager; import org.smartboot.flow.core.Pipeline; import org.smartboot.flow.core.common.ComponentType; import org.smartboot.flow.core.component.AttributeHolder; import org.smartboot.flow.core.component.Component; +import org.smartboot.flow.core.util.AuxiliaryUtils; +import org.smartboot.flow.core.util.ContactUtils; import org.smartboot.flow.core.visitor.ComponentVisitor; import org.smartboot.flow.core.visitor.PipelineVisitor; @@ -18,19 +19,18 @@ import java.util.List; public class RegisteredComponentVisitor extends ComponentVisitor { private final ComponentModel model; - private final IdentifierManager identifierManager; - public RegisteredComponentVisitor(ComponentModel comp, IdentifierManager identifierManager) { + public RegisteredComponentVisitor(ComponentModel comp) { this.model = comp; - this.identifierManager = identifierManager; } @Override public PipelineVisitor visitPipeline(Pipeline pipeline) { - PipelineModel pipelineModel = new PipelineModel(pipeline.describe(), identifierManager.generateIdentifier("pipeline")); + PipelineModel pipelineModel = new PipelineModel(pipeline.describe(), ContactUtils.contact(model.getIdentifier(), pipeline.describe())); this.model.pipeline = pipelineModel; this.model.type = (ComponentType.PIPELINE); - return new RegisteredPipelineVisitor(pipelineModel, identifierManager); + pipelineModel.setMetrics(pipeline.getMetrics()); + return new RegisteredPipelineVisitor(pipelineModel); } @Override @@ -41,9 +41,17 @@ public class RegisteredComponentVisitor extends ComponentVisitor { @Override public ComponentVisitor visitComponent(Component component) { - ComponentModel comp = new ComponentModel(identifierManager.generateIdentifier(component.getName()), component); + String identifier = ContactUtils.contact(model.getIdentifier(), AuxiliaryUtils.or(component.getName(), component.describe())); + String branch = null; + if (this.model.type == ComponentType.CHOOSE) { + identifier = ContactUtils.contact(model.getIdentifier(), "default"); + branch = "default"; + } + + ComponentModel comp = new ComponentModel(identifier, component); + comp.setBranch(branch); this.model.addComponent(comp); - return new RegisteredComponentVisitor(comp, identifierManager); + return new RegisteredComponentVisitor(comp); } @Override @@ -53,11 +61,11 @@ public class RegisteredComponentVisitor extends ComponentVisitor { @Override public ComponentVisitor visitBranch(Object branch, Component component) { - ComponentModel model = new ComponentModel(identifierManager.generateIdentifier(component.getName()), component); - model.branch = (String.valueOf(branch)); - this.model.addComponent(model); + ComponentModel model = new ComponentModel(ContactUtils.contact(this.model.getIdentifier(), "branch", String.valueOf(branch)), component); + model.setBranch((String.valueOf(branch))); this.model.type = (ComponentType.CHOOSE); - return new RegisteredComponentVisitor(model, identifierManager); + this.model.addComponent(model); + return new RegisteredComponentVisitor(model); } @Override diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredPipelineVisitor.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredPipelineVisitor.java index e79ae84638e51e304b7160cfda17ed4342b58829..9c62badb17c047310e0570d3977fe343bdb981bf 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredPipelineVisitor.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/manager/RegisteredPipelineVisitor.java @@ -1,7 +1,8 @@ package org.smartboot.flow.core.manager; -import org.smartboot.flow.core.IdentifierManager; import org.smartboot.flow.core.component.Component; +import org.smartboot.flow.core.util.AuxiliaryUtils; +import org.smartboot.flow.core.util.ContactUtils; import org.smartboot.flow.core.visitor.ComponentVisitor; import org.smartboot.flow.core.visitor.PipelineVisitor; @@ -13,17 +14,15 @@ import org.smartboot.flow.core.visitor.PipelineVisitor; public class RegisteredPipelineVisitor extends PipelineVisitor { private final PipelineModel pipelineModel; - private final IdentifierManager identifierManager; - public RegisteredPipelineVisitor(PipelineModel pipelineModel, IdentifierManager identifierManager) { + public RegisteredPipelineVisitor(PipelineModel pipelineModel) { this.pipelineModel = pipelineModel; - this.identifierManager = identifierManager; } @Override public ComponentVisitor visitComponent(Component component) { - ComponentModel comp = new ComponentModel(identifierManager.generateIdentifier(this.pipelineModel.getName() + "-" +component.getName()), component); + ComponentModel comp = new ComponentModel(ContactUtils.contact(this.pipelineModel.getIdentifier(), AuxiliaryUtils.or(component.getName(), component.describe())), component); this.pipelineModel.addComponent(comp); - return new RegisteredComponentVisitor(comp, identifierManager); + return new RegisteredComponentVisitor(comp); } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/DefaultMetricsCreator.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/DefaultMetricsCreator.java new file mode 100644 index 0000000000000000000000000000000000000000..2f15888110ac9ab340f40154177593fac15ac3e9 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/DefaultMetricsCreator.java @@ -0,0 +1,14 @@ +package org.smartboot.flow.core.metrics; + +/** + * @author qinluo + * @date 2022-11-25 21:51:52 + * @since 1.0.0 + */ +public class DefaultMetricsCreator implements MetricsCreator { + + @Override + public Metrics create() { + return new Metrics(); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricExecutionListener.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricExecutionListener.java new file mode 100644 index 0000000000000000000000000000000000000000..0d441c7b2fbd4fb2081dee56e7d169d501117402 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricExecutionListener.java @@ -0,0 +1,108 @@ +package org.smartboot.flow.core.metrics; + +import org.smartboot.flow.core.EngineContext; +import org.smartboot.flow.core.ExecutionListener; +import org.smartboot.flow.core.Key; +import org.smartboot.flow.core.Measurable; + +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +/** + * @author qinluo + * @date 2022-11-25 21:23:28 + * @since 1.0.0 + */ +public class MetricExecutionListener implements ExecutionListener { + + private static final ExecutionListener INSTANCE = new MetricExecutionListener(); + + public static ExecutionListener getInstance() { + return INSTANCE; + } + + @Override + public void beforeExecute(EngineContext context, Object object) { + if (!(object instanceof Measurable)) { + return; + } + + Map escaped = context.getExt(Key.of(this)); + if (escaped == null) { + escaped = new ConcurrentHashMap<>(); + context.putExt(Key.of(this), escaped); + } + + + Measurable measurable = (Measurable) object; + Metrics metrics = measurable.getMetrics(); + metrics.addMetric("execute-count", 1); + escaped.put(object, System.currentTimeMillis()); + } + + @Override + public void afterExecute(EngineContext context, Object object) { + if (!(object instanceof Measurable)) { + return; + } + + Map escaped = context.getExt(Key.of(this)); + if (escaped == null) { + return; + } + + Long start = escaped.remove(object); + if (start == null) { + return; + } + + Measurable measurable = (Measurable) object; + Metrics metrics = measurable.getMetrics(); + if (context.getFatal() != null) { + metrics.addMetric("execute-fail-count", 1); + } + long now = System.currentTimeMillis(); + metrics.addMetric("execute-total", (now - start)); + metrics.addMetric(MetricKind.MAX,"execute-max", (now - start)); + } + + @Override + public void beforeRollback(EngineContext context, Object object) { + if (!(object instanceof Measurable)) { + return; + } + + Map escaped = context.getExt(Key.of(this)); + if (escaped == null) { + return; + } + + Measurable measurable = (Measurable) object; + Metrics metrics = measurable.getMetrics(); + metrics.addMetric("rollback-count", 1); + escaped.put(object, System.currentTimeMillis()); + } + + @Override + public void afterRollback(EngineContext context, Object object) { + if (!(object instanceof Measurable)) { + return; + } + + Map escaped = context.getExt(Key.of(this)); + if (escaped == null) { + return; + } + + Long start = escaped.remove(object); + if (start == null) { + return; + } + + Measurable measurable = (Measurable) object; + Metrics metrics = measurable.getMetrics(); + long now = System.currentTimeMillis(); + metrics.addMetric("rollback-total", (now - start)); + metrics.addMetric(MetricKind.MAX,"rollback-max", (now - start)); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricKind.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricKind.java new file mode 100644 index 0000000000000000000000000000000000000000..e779d0749c760e42baed80cd7fa3aa62c55d78d0 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricKind.java @@ -0,0 +1,14 @@ +package org.smartboot.flow.core.metrics; + +/** + * @author qinluo + * @date 2022/11/23 21:45 + * @since 1.0.0 + */ +public enum MetricKind { + + ACCUMULATE, + + MAX, + ; +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/Metrics.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/Metrics.java new file mode 100644 index 0000000000000000000000000000000000000000..236678eebf1339a06116a60ba2e90fc2d9a033fc --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/Metrics.java @@ -0,0 +1,47 @@ +package org.smartboot.flow.core.metrics; + +import org.smartboot.flow.core.metrics.counter.Counter; +import org.smartboot.flow.core.metrics.counter.MaxCounter; +import org.smartboot.flow.core.util.AssertUtil; + +import java.util.Collections; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +/** + * @author qinluo + * @date 2022/11/23 21:35 + * @since 1.0.0 + */ +public class Metrics { + + private final Map COUNTERS = new ConcurrentHashMap<>(); + + public void addMetric(String name, long value) { + this.addMetric(MetricKind.ACCUMULATE, name, value); + } + + public void addMetric(MetricKind kind, String name, long value) { + AssertUtil.notNull(name, "metric name must not be null"); + AssertUtil.notNull(kind, "metric kind must not be null"); + + Counter counter = COUNTERS.computeIfAbsent(name, k -> createCounter(kind)); + counter.increment(value); + } + + public Map getMetrics() { + return Collections.unmodifiableMap(COUNTERS); + } + + private Counter createCounter(MetricKind kind) { + if (kind == MetricKind.MAX) { + return new MaxCounter(); + } + + return new Counter(); + } + + public void reset() { + COUNTERS.forEach((k, v) -> v.reset()); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricsCreator.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricsCreator.java new file mode 100644 index 0000000000000000000000000000000000000000..4eabcb97b6d984184aaa6ea02a7bca1b2f824518 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricsCreator.java @@ -0,0 +1,16 @@ +package org.smartboot.flow.core.metrics; + +/** + * @author qinluo + * @date 2022-11-25 21:50:10 + * @since 1.0.0 + */ +public interface MetricsCreator { + + /** + * 创建一个metrics实力 + * + * @return metrics + */ + Metrics create(); +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricsManager.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricsManager.java new file mode 100644 index 0000000000000000000000000000000000000000..3ad8d56c68eec135d5f9002ad708870075938381 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/MetricsManager.java @@ -0,0 +1,36 @@ +package org.smartboot.flow.core.metrics; + +import org.smartboot.flow.core.util.AssertUtil; + +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +/** + * @author qinluo + * @date 2022-11-25 21:06:10 + * @since 1.0.0 + */ +public class MetricsManager { + + private static final Map MANAGED = new ConcurrentHashMap<>(); + private static MetricsCreator metricsCreator = new DefaultMetricsCreator(); + + public static MetricsCreator getMetricsCreator() { + return metricsCreator; + } + + public static void setMetricsCreator(MetricsCreator metricsCreator) { + MetricsManager.metricsCreator = metricsCreator; + } + + public static Metrics allocate(Object key) { + AssertUtil.notNull(key, "key must not be null!"); + Metrics metrics = MANAGED.get(key); + if (metrics == null) { + metrics = metricsCreator.create(); + MANAGED.put(key, metrics); + } + + return metrics; + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/counter/Counter.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/counter/Counter.java new file mode 100644 index 0000000000000000000000000000000000000000..c8be0c2548407d37a39ea8bd93cd7b56ff9d3172 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/counter/Counter.java @@ -0,0 +1,27 @@ +package org.smartboot.flow.core.metrics.counter; + +import java.util.concurrent.atomic.LongAdder; + +/** + * Count some metrics. + * + * @author qinluo + * @date 2022/11/23 21:35 + * @since 1.0.0 + */ +public class Counter { + + protected final LongAdder sum = new LongAdder(); + + public void increment(long value) { + sum.add(value); + } + + public long getValue() { + return sum.sum(); + } + + public void reset() { + this.sum.reset(); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/counter/MaxCounter.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/counter/MaxCounter.java new file mode 100644 index 0000000000000000000000000000000000000000..2166e19ebc8b9ef71419f9508750df178a192456 --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/metrics/counter/MaxCounter.java @@ -0,0 +1,32 @@ +package org.smartboot.flow.core.metrics.counter; + +import java.util.concurrent.atomic.AtomicLong; + +/** + * @author qinluo + * @date 2022/11/23 21:41 + * @since 1.0.0 + */ +public class MaxCounter extends Counter { + + private final AtomicLong counter = new AtomicLong(); + + @Override + public void increment(long value) { + while (counter.get() < value) { + counter.compareAndSet(counter.get(), value); + } + + } + + @Override + public long getValue() { + return counter.get(); + } + + @Override + public void reset() { + super.reset(); + this.counter.set(0); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/AbstractElementParser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/AbstractElementParser.java index 4375f5fa96067f7dda7e76578db91cf8573ddb97..07e22ba5ca57c75dd28d4fd78abd5a75c755d26f 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/AbstractElementParser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/AbstractElementParser.java @@ -22,7 +22,7 @@ public abstract class AbstractElementParser implements ElementParser { AssertUtil.notNull(element, "[" + getElementName() + "] element must not be null!"); String localName = ElementUtils.getName(element); AssertUtil.assertEquals(localName, getElementName(), "element must be [" + getElementName() + "] tag"); - this.parseElementInternal(element, context); + this.doParse(element, context); } protected String getIdentifier(Element element, ParserContext context) { @@ -48,24 +48,25 @@ public abstract class AbstractElementParser implements ElementParser { /** * Parse internal. */ - public abstract void parseElementInternal(Element element, ParserContext context); + public abstract void doParse(Element element, ParserContext context); protected ElementDefinition parseElementsAsPipeline(Element element, ParserContext context) { // pipeline identifier. - String identifier = context.allocateIdentifier("anonymous-pipeline"); + String pipelineIdentifier = context.allocateIdentifier("anonymous-pipeline"); // Wrap sub elements as pipeline. + String identifier = context.allocateIdentifier("anonymous-pipeline-wrapper"); PipelineComponentDefinition def = new PipelineComponentDefinition(); - def.setName("anonymous-pipeline-component"); - def.setIdentifier(context.allocateIdentifier("anonymous-pipeline-component")); - def.setPipeline(identifier); + def.setName(identifier); + def.setIdentifier(identifier); + def.setPipeline(pipelineIdentifier); def.getAttributes().addAll(ElementUtils.extraAttributes(element)); context.register(def); // Wrap as pipeline. PipelineDefinition pipelineDef = new PipelineDefinition(); - pipelineDef.setName("anonymous-pipeline"); - pipelineDef.setIdentifier(identifier); + pipelineDef.setName(pipelineIdentifier); + pipelineDef.setIdentifier(pipelineIdentifier); List subs = ElementUtils.subElements(element); AssertUtil.isTrue(subs.size() != 0, "[" + ElementUtils.getName(element) + "] childNodes can't be null"); @@ -82,8 +83,8 @@ public abstract class AbstractElementParser implements ElementParser { // nested subprocess if (Objects.equals(subName, ParseConstants.PIPELINE)) { PipelineComponentDefinition nestedWrap = new PipelineComponentDefinition(); - String nestedIdentifier = context.allocateIdentifier("pipelineComponent"); - nestedWrap.setName(ElementUtils.resolveName(sub, "pipeline-component")); + String nestedIdentifier = context.allocateIdentifier("anonymous-pipeline-wrapper"); + nestedWrap.setName("anonymous-pipeline-wrapper-" + sub.getAttribute(ParseConstants.NAME)); nestedWrap.setIdentifier(nestedIdentifier); nestedWrap.setPipeline(elementIdentifier); context.register(nestedWrap); diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/BuilderDefinitionVisitor.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/BuilderDefinitionVisitor.java index e86ff2236c06d01f17e56ce5c59ca2a1753b4222..c8521b645ecc4821254d76bb47c8a6ca7baadf68 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/BuilderDefinitionVisitor.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/BuilderDefinitionVisitor.java @@ -11,9 +11,6 @@ import org.smartboot.flow.core.builder.PipelineBuilder; import org.smartboot.flow.core.component.Component; import org.smartboot.flow.core.component.PipelineComponent; import org.smartboot.flow.core.executable.Executable; -import org.smartboot.flow.core.extension.DefaultObjectCreator; -import org.smartboot.flow.core.extension.ExtensionFactory; -import org.smartboot.flow.core.extension.ObjectCreator; import org.smartboot.flow.core.parser.definition.ChooseDefinition; import org.smartboot.flow.core.parser.definition.ElementDefinition; import org.smartboot.flow.core.parser.definition.EngineDefinition; @@ -38,15 +35,12 @@ public class BuilderDefinitionVisitor implements DefinitionVisitor { private final Map> namedPipelines = new ConcurrentHashMap<>(); private final Map> namedEngines = new ConcurrentHashMap<>(); private final Map> callbacks = new ConcurrentHashMap<>(); - private ObjectCreator objectCreator; + private final ObjectCreator objectCreator; private final boolean useCache; - public BuilderDefinitionVisitor(boolean useCache) { + public BuilderDefinitionVisitor(boolean useCache, ObjectCreator objectCreator) { this.useCache = useCache; - objectCreator = ExtensionFactory.getExtension(ObjectCreator.class); - if (objectCreator == null) { - objectCreator = new DefaultObjectCreator(); - } + this.objectCreator = objectCreator; } @Override @@ -77,7 +71,7 @@ public class BuilderDefinitionVisitor implements DefinitionVisitor { @Override public void visit(EngineDefinition ed) { String engineName = ed.getIdentifier(); - EngineBuilder engineBuilder = new EngineBuilder<>().name(engineName); + EngineBuilder engineBuilder = new EngineBuilder<>(engineName); PipelineBuilder pipelineBuilder = this.namedPipelines.get(ed.getPipeline()); if (pipelineBuilder == null) { diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ChooseElementParser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ChooseElementParser.java index c33d987ea32e33f61c1503a330c688b0bd29b97a..57f08882fdc2581d510f4f27c89682a85f8436df 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ChooseElementParser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ChooseElementParser.java @@ -3,6 +3,7 @@ package org.smartboot.flow.core.parser; import org.smartboot.flow.core.parser.definition.ChooseDefinition; import org.smartboot.flow.core.parser.definition.ElementDefinition; import org.smartboot.flow.core.util.AssertUtil; +import org.smartboot.flow.core.util.AuxiliaryUtils; import org.w3c.dom.Element; import java.util.ArrayList; @@ -27,10 +28,10 @@ public class ChooseElementParser extends AbstractElementParser{ } @Override - public void parseElementInternal(Element element, ParserContext context) { + public void doParse(Element element, ParserContext context) { String test = element.getAttribute(ParseConstants.TEST); String ref = element.getAttribute(ParseConstants.REF); - if (ElementUtils.isBlank(ref) && ElementUtils.isBlank(test)) { + if (AuxiliaryUtils.isBlank(ref) && AuxiliaryUtils.isBlank(test)) { throw new IllegalArgumentException("attribute [ref] [type] cannot be null"); } @@ -68,7 +69,7 @@ public class ChooseElementParser extends AbstractElementParser{ String type = subElement.getAttribute(ParseConstants.TYPE); ref = subElement.getAttribute(ParseConstants.REF); - if (ElementUtils.isNotBlank(type) || ElementUtils.isNotBlank(ref)) { + if (AuxiliaryUtils.isNotBlank(type) || AuxiliaryUtils.isNotBlank(ref)) { continue; } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ComponentElementParser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ComponentElementParser.java index 1f73f91e11f348de4391323efccca301b3e239da..37958392a7ee2f97bba5c5010064c0f5ec46356b 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ComponentElementParser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ComponentElementParser.java @@ -2,6 +2,7 @@ package org.smartboot.flow.core.parser; import org.smartboot.flow.core.parser.definition.ElementDefinition; import org.smartboot.flow.core.parser.definition.PipelineComponentDefinition; +import org.smartboot.flow.core.util.AuxiliaryUtils; import org.w3c.dom.Element; /** @@ -18,7 +19,7 @@ public class ComponentElementParser extends AbstractElementParser { */ @Override - public void parseElementInternal(Element element, ParserContext context) { + public void doParse(Element element, ParserContext context) { ElementDefinition elementDefinition = new ElementDefinition(); ElementDefinition.build(elementDefinition, element); @@ -26,10 +27,10 @@ public class ComponentElementParser extends AbstractElementParser { elementDefinition.setIdentifier(super.getIdentifier(element, context)); String subprocess = element.getAttribute(ParseConstants.SUBPROCESS); - if (ElementUtils.isNotBlank(subprocess)) { + if (AuxiliaryUtils.isNotBlank(subprocess)) { PipelineComponentDefinition def = new PipelineComponentDefinition(); ElementDefinition.build(def, element); - def.setName(ElementUtils.resolveName(element, "pipeline-component")); + def.setName(ElementUtils.resolveName(element, "pipeline-wrapper-" + subprocess)); def.setIdentifier(super.getIdentifier(element, context)); def.setPipeline(subprocess); context.register(def); @@ -38,7 +39,7 @@ public class ComponentElementParser extends AbstractElementParser { String ref = elementDefinition.getRef(); String type = elementDefinition.getType(); - if (ElementUtils.isBlank(ref) && ElementUtils.isBlank(type)) { + if (AuxiliaryUtils.isBlank(ref) && AuxiliaryUtils.isBlank(type)) { throw new IllegalArgumentException("attribute [ref] [type] cannot be null"); } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/extension/DefaultObjectCreator.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/DefaultObjectCreator.java similarity index 95% rename from smart-flow-core/src/main/java/org/smartboot/flow/core/extension/DefaultObjectCreator.java rename to smart-flow-core/src/main/java/org/smartboot/flow/core/parser/DefaultObjectCreator.java index a67db127a19c16dbdd838a86884601036a0b92d5..67df7a505396e815ae6e4c607180ed6e346fa73a 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/extension/DefaultObjectCreator.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/DefaultObjectCreator.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.core.extension; +package org.smartboot.flow.core.parser; import org.smartboot.flow.core.util.AssertUtil; diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/DefaultParser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/DefaultParser.java index 7fbe2a55a41c3de8a52504fd69b7e91e394ddeaf..1af113abf2c207636f2c9a44e9eb3152fd47516f 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/DefaultParser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/DefaultParser.java @@ -28,32 +28,77 @@ public class DefaultParser implements Parser { } private BuilderDefinitionVisitor visitor; + private final ParserContext context = new ParserContext(); @Override - public void parse(InputStream is) { + public void parse(InputStream is, InputStream... streams) { AssertUtil.notNull(is, "Stream must not be null"); - Element root = readRoot(is); - AssertUtil.notNull(root, "Read root element is null"); - AssertUtil.assertEquals(ElementUtils.getName(root), ParseConstants.ENGINES, "Root element must be engines"); - - List elements = ElementUtils.subElements(root); - AssertUtil.isTrue(elements.size() != 0, "[engines] element's sub elements must not be empty"); - - ParserContext context = new ParserContext(); - for (Element sub : elements) { - String subName = ElementUtils.getName(sub); - AssertUtil.isTrue(ALLOWED.contains(subName), "element " + subName + " not allowed in engines"); - ElementParser parser = context.getParser(subName); - AssertUtil.notNull(parser, "Could not find parser for element " + subName); - parser.parseElement(sub, context); + List willParsedStreams = new ArrayList<>(); + willParsedStreams.add(is); + + if (streams != null && streams.length != 0) { + for (InputStream stream : streams) { + AssertUtil.notNull(stream, "Stream must not be null"); + willParsedStreams.add(stream); + } } - boolean useCache = Boolean.parseBoolean(root.getAttribute("useCache")); - this.visitor = new BuilderDefinitionVisitor(useCache); + boolean useCache = false; + + for (InputStream stream : willParsedStreams) { + Element root = readRoot(stream); + AssertUtil.notNull(root, "Read root element is null"); + AssertUtil.assertEquals(ElementUtils.getName(root), ParseConstants.ENGINES, "Root element must be engines"); + + List elements = ElementUtils.subElements(root); + AssertUtil.isTrue(elements.size() != 0, "[engines] element's sub elements must not be empty"); + + for (Element sub : elements) { + String subName = ElementUtils.getName(sub); + AssertUtil.isTrue(ALLOWED.contains(subName), "element " + subName + " not allowed in engines"); + ElementParser parser = context.getParser(subName); + AssertUtil.notNull(parser, "Could not find parser for element " + subName); + parser.parseElement(sub, context); + } + + useCache = useCache || Boolean.parseBoolean(root.getAttribute("useCache")); + } + + this.visitor = new BuilderDefinitionVisitor(useCache, getObjectCreator()); context.getRegistered().forEach(ElementDefinition::validate); context.getRegistered().forEach(p -> visitor.visit(p)); } + @Override + public void parse(String f, String... files) { + AssertUtil.notBlank(f, "filename must not be null!"); + if (files != null && files.length != 0) { + for (String file : files) { + AssertUtil.notBlank(file, "filename must not be null!"); + } + } + + InputStream fstream = this.getClass().getResourceAsStream(f); + AssertUtil.notNull(fstream, "filename " + f + " not exist"); + + InputStream[] streams = new InputStream[0]; + int index = 0; + if (files != null && files.length != 0) { + streams = new InputStream[files.length]; + for (String file : files) { + InputStream stream = this.getClass().getResourceAsStream(f); + AssertUtil.notNull(stream, "filename " + file + " not exist"); + streams[index++] = stream; + } + } + + this.parse(fstream, streams); + } + + protected ObjectCreator getObjectCreator() { + return new DefaultObjectCreator(); + } + public FlowEngine getEngine(String name) { return visitor.getEngine(name); } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ElementUtils.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ElementUtils.java index 2e435b45b2b1925781ebbbcb5a2c7356047409d2..35143acded5689c2a216a6c61c66c19d20eb93a7 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ElementUtils.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ElementUtils.java @@ -2,6 +2,7 @@ package org.smartboot.flow.core.parser; import org.smartboot.flow.core.component.AttributeHolder; import org.smartboot.flow.core.component.Attributes; +import org.smartboot.flow.core.util.AuxiliaryUtils; import org.w3c.dom.Element; import org.w3c.dom.NamedNodeMap; import org.w3c.dom.Node; @@ -9,7 +10,6 @@ import org.w3c.dom.NodeList; import java.util.ArrayList; import java.util.List; -import java.util.concurrent.ThreadLocalRandom; /** * @author qinluo @@ -18,12 +18,6 @@ import java.util.concurrent.ThreadLocalRandom; */ public final class ElementUtils { - private static final byte[] CHARS = new byte[] {'a', 'b', 'c', 'd', 'e', 'f', 'g', - 'h', 'i', 'j', 'k', 'l', 'm', 'n', - 'o', 'p', 'q', 'r', 's', 't', 'u', - 'v', 'w', 'x', 'y', 'z', '0', '1', - '2', '3', '4', '5', '6', '7', '8', '9'}; - /** * Extra all well-known attributes. */ @@ -63,7 +57,7 @@ public final class ElementUtils { public static String resolveName(Element element, String suffix) { String name = element.getAttribute(ParseConstants.NAME); - if (isBlank(name)) { + if (AuxiliaryUtils.isBlank(name)) { return "anonymous-" + suffix; } @@ -77,20 +71,4 @@ public final class ElementUtils { } return localName; } - - public static String random(String prefix) { - StringBuilder sb = new StringBuilder(prefix).append("-"); - for (int i = 0; i < 8; i++) { - sb.append((char)CHARS[ThreadLocalRandom.current().nextInt(CHARS.length)]); - } - return sb.toString(); - } - - public static boolean isBlank(String value) { - return value == null || value.trim().length() == 0; - } - - public static boolean isNotBlank(String value) { - return !isBlank(value); - } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/EngineElementParser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/EngineElementParser.java index b835c06c478977786b91fd08d3e0c70e103f9e73..4c398deb74dd910570cac07b9c7f2f1bf595c9ea 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/EngineElementParser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/EngineElementParser.java @@ -19,7 +19,7 @@ import org.w3c.dom.Element; public class EngineElementParser extends AbstractElementParser { @Override - public void parseElementInternal(Element element, ParserContext context) { + public void doParse(Element element, ParserContext context) { EngineDefinition definition = new EngineDefinition(); // name String name = element.getAttribute(ParseConstants.NAME); diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/IfElementParser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/IfElementParser.java index 6bb1360f19542a9b2ee26fc20433552ca50d40e5..2fa9b95f842b7d7a11fa4b9322b132256d87c349 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/IfElementParser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/IfElementParser.java @@ -3,6 +3,7 @@ package org.smartboot.flow.core.parser; import org.smartboot.flow.core.parser.definition.ElementDefinition; import org.smartboot.flow.core.parser.definition.IfElementDefinition; import org.smartboot.flow.core.util.AssertUtil; +import org.smartboot.flow.core.util.AuxiliaryUtils; import org.w3c.dom.Element; import java.util.ArrayList; @@ -29,10 +30,10 @@ public class IfElementParser extends AbstractElementParser { } @Override - public void parseElementInternal(Element element, ParserContext context) { + public void doParse(Element element, ParserContext context) { String test = element.getAttribute(ParseConstants.TEST); String ref = element.getAttribute(ParseConstants.REF); - if (ElementUtils.isBlank(ref) && ElementUtils.isBlank(test)) { + if (AuxiliaryUtils.isBlank(ref) && AuxiliaryUtils.isBlank(test)) { throw new IllegalArgumentException("attribute [ref] [type] cannot be null"); } @@ -71,7 +72,7 @@ public class IfElementParser extends AbstractElementParser { String type = subElement.getAttribute(ParseConstants.TYPE); ref = subElement.getAttribute(ParseConstants.REF); - if (ElementUtils.isNotBlank(type) || ElementUtils.isNotBlank(ref)) { + if (AuxiliaryUtils.isNotBlank(type) || AuxiliaryUtils.isNotBlank(ref)) { continue; } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/extension/ObjectCreator.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ObjectCreator.java similarity index 88% rename from smart-flow-core/src/main/java/org/smartboot/flow/core/extension/ObjectCreator.java rename to smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ObjectCreator.java index a0384566a907181dd84fd68a9edc9965ac05c06f..28c05500ca77a616eb22d2136818b7262dbccf13 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/extension/ObjectCreator.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/ObjectCreator.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.core.extension; +package org.smartboot.flow.core.parser; /** * @author qinluo diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/Parser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/Parser.java index a6d57062194fee5d75ac7245b8d95c3b966ded2b..58ddbdb7bb294b0120d22cbf105bb035e36e1a1f 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/Parser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/Parser.java @@ -10,7 +10,17 @@ public interface Parser { /** * Parse config file + * @param is is + * @param streams other multiple is. + */ + void parse(InputStream is, InputStream ... streams); + + /** + * Parse file and other multiple files. * + * @param f file location + * @param files other multiple file location */ - void parse(InputStream is); + void parse(String f, String... files); + } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/PipelineElementParser.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/PipelineElementParser.java index c3191178757e3681b1d767a44dc361277c6ddfbd..64576f8c2f6ea464626b32565ea9d274fc998164 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/PipelineElementParser.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/parser/PipelineElementParser.java @@ -30,19 +30,18 @@ import java.util.Objects; public class PipelineElementParser extends AbstractElementParser { @Override - public void parseElementInternal(Element element, ParserContext context) { + public void doParse(Element element, ParserContext context) { PipelineDefinition definition = new PipelineDefinition(); - // identifier - String identifier = context.getIdentifier(element); - if (identifier == null && ElementUtils.isBlank(element.getAttribute(ParseConstants.NAME))) { - throw new IllegalArgumentException("pipeline name must not be null"); - } + // pipeline name as identifier + String identifier = element.getAttribute(ParseConstants.NAME); + AssertUtil.notBlank(identifier, "pipeline name must not be null"); + // Check has any elements. List elements = ElementUtils.subElements(element); AssertUtil.isTrue(elements.size() != 0, "[pipeline] element's sub elements must not be empty"); definition.setName(element.getAttribute(ParseConstants.NAME)); - definition.setIdentifier(super.getIdentifier(element, context)); + definition.setIdentifier(identifier); definition.getAttributes().addAll(ElementUtils.extraAttributes(element)); List subDefinitions = new ArrayList<>(); @@ -57,8 +56,8 @@ public class PipelineElementParser extends AbstractElementParser { // nested subprocess if (Objects.equals(subName, ParseConstants.PIPELINE)) { PipelineComponentDefinition nestedWrap = new PipelineComponentDefinition(); - String nestedIdentifier = context.allocateIdentifier("pipelineComponent"); - nestedWrap.setName(ElementUtils.resolveName(sub, "pipelineComponent")); + String nestedIdentifier = context.allocateIdentifier("anonymous-pipeline-wrapper"); + nestedWrap.setName("anonymous-pipeline-wrapper-" + sub.getAttribute(ParseConstants.NAME)); nestedWrap.setIdentifier(nestedIdentifier); nestedWrap.setPipeline(identifier); context.register(nestedWrap); diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/util/AuxiliaryUtils.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/util/AuxiliaryUtils.java new file mode 100644 index 0000000000000000000000000000000000000000..c6d6694593d84d82406bae9b9a772b9c6c357daa --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/util/AuxiliaryUtils.java @@ -0,0 +1,25 @@ +package org.smartboot.flow.core.util; + +/** + * @author qinluo + * @date 2022-11-20 11:32:23 + * @since 1.0.0 + */ +public final class AuxiliaryUtils { + + public static T or(T t, T defaultValue) { + return t != null ? t : defaultValue; + } + + public static String or(String t, String defaultValue) { + return t != null && t.trim().length() > 0 ? t : defaultValue; + } + + public static boolean isBlank(String value) { + return value == null || value.trim().length() == 0; + } + + public static boolean isNotBlank(String value) { + return !isBlank(value); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/util/ContactUtils.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/util/ContactUtils.java new file mode 100644 index 0000000000000000000000000000000000000000..e1979185df85c8fbff103958d3bb14b7e7c023eb --- /dev/null +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/util/ContactUtils.java @@ -0,0 +1,20 @@ +package org.smartboot.flow.core.util; + +/** + * @author qinluo + * @date 2022/11/20 22:10 + * @since 1.0.0 + */ +public final class ContactUtils { + + public static String contact(String p, Object ...s) { + StringBuilder sb = new StringBuilder(); + sb.append(p); + + for (Object suffix : s) { + sb.append("-").append(suffix); + } + + return sb.toString(); + } +} diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponent.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponent.java index c401e98fca4bf1c19a9d37fbe2083bccf5088cf7..9602c7a6d277b6365f03b95528480bc48805c51f 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponent.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponent.java @@ -3,6 +3,7 @@ package org.smartboot.flow.core.view.plantuml; import org.smartboot.flow.core.common.ComponentType; import org.smartboot.flow.core.component.AttributeHolder; import org.smartboot.flow.core.component.Attributes; +import org.smartboot.flow.core.util.AuxiliaryUtils; import java.util.ArrayList; import java.util.List; @@ -23,7 +24,7 @@ public class PlantumlComponent { private String condition; private String branch; private final List components = new ArrayList<>(); - private String wrapped; + private String executable; public PlantumlComponent(String name, String describe) { this.name = name; @@ -90,16 +91,16 @@ public class PlantumlComponent { this.components.add(component); } - public String getWrapped() { - return wrapped; + public String getExecutable() { + return executable; } - public void setWrapped(String wrapped) { - this.wrapped = wrapped; + public void setExecutable(String executable) { + this.executable = executable; } public void generate(StringBuilder content) { - String nodeName = name == null ? describe : name + "#" + describe; + String nodeName = AuxiliaryUtils.isBlank(name) ? describe : name; if (getType() == ComponentType.BASIC) { String serialAttributes = serialAttributes(); @@ -134,8 +135,9 @@ public class PlantumlComponent { content.append("endswitch\n"); } else if (getType() == ComponentType.PIPELINE) { - content.append(":").append("subprocess:").append(pipeline.getName()).append(";\n"); + content.append("partition 子流程:").append(pipeline.getName()).append("{ \n"); pipeline.generate(content); + content.append(" } \n"); } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponentVisitor.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponentVisitor.java index 869699e6008a486865a24bff5f235dd2633e48ec..5eb8a4119eed22a4f8126f1b6aa6850a1f6f325d 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponentVisitor.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlComponentVisitor.java @@ -60,6 +60,6 @@ public class PlantumlComponentVisitor extends ComponentVisitor { @Override public void visitExecutable(String executable) { this.plantumlComponent.setType(ComponentType.BASIC); - this.plantumlComponent.setWrapped(executable); + this.plantumlComponent.setExecutable(executable); } } diff --git a/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlEngineVisitor.java b/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlEngineVisitor.java index 87d284127426a4785c4794e5131c862bb8cc451b..40c013fc510bf4da9eba1933fe3e105c5107f9f6 100644 --- a/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlEngineVisitor.java +++ b/smart-flow-core/src/main/java/org/smartboot/flow/core/view/plantuml/PlantumlEngineVisitor.java @@ -60,6 +60,8 @@ public class PlantumlEngineVisitor extends EngineVisitor { } content.append("\nend split\n"); + content.append("\n : start ;\n"); + plantumlEngine.getPipeline().generate(content); content.append("\n : end ;\n"); diff --git a/smart-flow-core/src/main/resources/smart-flow-1.0.0.xsd b/smart-flow-core/src/main/resources/smart-flow-1.0.0.xsd index bcbdbfee02027540eb37052ec658800473a3cd79..a7c713086740c00e05316fe508d30ad2f1241fb9 100644 --- a/smart-flow-core/src/main/resources/smart-flow-1.0.0.xsd +++ b/smart-flow-core/src/main/resources/smart-flow-1.0.0.xsd @@ -1,48 +1,34 @@ + elementFormDefault="qualified"> - + - - - + + - - - - - - - - - - - - - - - - + + + + @@ -54,7 +40,6 @@ - @@ -62,7 +47,22 @@ + + + + + + + + + + + + + + + @@ -86,7 +86,6 @@ - @@ -107,7 +106,6 @@ - @@ -147,7 +145,6 @@ - @@ -168,7 +165,6 @@ - diff --git a/smart-flow-core/src/test/java/org/smartboot/flow/core/BaseTest.java b/smart-flow-core/src/test/java/org/smartboot/flow/core/BaseTest.java index b4949e96478ecb1480e887de3304033bb1d2b6ed..12b0b87551a2c2b06ca0efe252ed1b0cfcf27726 100644 --- a/smart-flow-core/src/test/java/org/smartboot/flow/core/BaseTest.java +++ b/smart-flow-core/src/test/java/org/smartboot/flow/core/BaseTest.java @@ -1,7 +1,9 @@ package org.smartboot.flow.core; +import org.junit.jupiter.api.BeforeEach; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import org.smartboot.flow.core.manager.DefaultEngineManager; /** * @author yamikaze @@ -11,4 +13,9 @@ public class BaseTest { protected static final Logger LOGGER = LoggerFactory.getLogger(BaseTest.class); + @BeforeEach + public void setUp() { + DefaultEngineManager.getDefaultManager().detachAll(); + } + } diff --git a/smart-flow-core/src/test/java/org/smartboot/flow/core/EngineTest.java b/smart-flow-core/src/test/java/org/smartboot/flow/core/EngineTest.java index 79775badeb2d1a1f7ae4880e01c66c3a038b434d..e705f528d12b83b88d81033052394d4456714e4d 100644 --- a/smart-flow-core/src/test/java/org/smartboot/flow/core/EngineTest.java +++ b/smart-flow-core/src/test/java/org/smartboot/flow/core/EngineTest.java @@ -66,8 +66,8 @@ public class EngineTest { @Test public void testSimpleBuilder() { - EngineBuilder builder = new EngineBuilder<>(); - FlowEngine engine = builder.pipeline(new PipelineBuilder().next(new AbstractExecutable() { + EngineBuilder builder = new EngineBuilder<>("defaultEngine"); + FlowEngine engine = builder.pipeline(new PipelineBuilder("DefaultPipeline").next(new AbstractExecutable() { @Override public void execute(Integer o, String o2) { System.out.println(o); @@ -99,8 +99,8 @@ public class EngineTest { @Test public void testSimpleBuilder02() { - EngineBuilder builder = new EngineBuilder<>(); - FlowEngine engine = builder.pipeline(new PipelineBuilder().next(new AbstractExecutable() { + EngineBuilder builder = new EngineBuilder<>("defaultEngine"); + FlowEngine engine = builder.pipeline(new PipelineBuilder("DefaultPipeline").next(new AbstractExecutable() { @Override public void execute(Integer o, String o2) { System.out.println(o); @@ -166,7 +166,7 @@ public class EngineTest { @Test public void testBuildPipeline() { - EngineBuilder builder = new EngineBuilder<>(); + EngineBuilder builder = new EngineBuilder<>("defaultEngine"); PipelineBuilder pipelineBuilder = new PipelineBuilder<>("main process"); diff --git a/smart-flow-core/src/test/java/org/smartboot/flow/core/async/AsyncTest.java b/smart-flow-core/src/test/java/org/smartboot/flow/core/async/AsyncTest.java index 43b4008f2b457161e6b2d89e19c6a31a3215064c..54e5afd49718119d3c292b3e6d044bef7dfbe3d3 100644 --- a/smart-flow-core/src/test/java/org/smartboot/flow/core/async/AsyncTest.java +++ b/smart-flow-core/src/test/java/org/smartboot/flow/core/async/AsyncTest.java @@ -41,7 +41,7 @@ public class AsyncTest extends BaseTest { @Test public void testAsync() { - EngineBuilder builder = new EngineBuilder<>(); + EngineBuilder builder = new EngineBuilder<>("defaultEngine"); PipelineBuilder pipelineBuilder = new PipelineBuilder<>("main process"); diff --git a/smart-flow-core/src/test/java/org/smartboot/flow/core/attributes/AttributeTest.java b/smart-flow-core/src/test/java/org/smartboot/flow/core/attributes/AttributeTest.java index c24ed166c512c1f896d2475c679463be3a22a66d..d16e59fba18e0280edaf1f4baa2271c455d6e633 100644 --- a/smart-flow-core/src/test/java/org/smartboot/flow/core/attributes/AttributeTest.java +++ b/smart-flow-core/src/test/java/org/smartboot/flow/core/attributes/AttributeTest.java @@ -26,14 +26,14 @@ public class AttributeTest extends BaseTest { @Test public void testEnabled() { - PipelineBuilder builder = new PipelineBuilder<>(); + PipelineBuilder builder = new PipelineBuilder<>("DefaultPipeline"); Pipeline build = builder.next(new IfCondition()).apply(Attributes.DEGRADABLE, true).then(new DefaultStep()) .choose(new ChooseCondition()).newBranch(1, new IntegerStep()) .apply(Attributes.DEGRADABLE, true).end() .next(ExecutableBuilder.newBuilder().apply(Attributes.ENABLED, false).newAdapter(new Step5())) .build(); - EngineBuilder engineBuilder = new EngineBuilder<>(); + EngineBuilder engineBuilder = new EngineBuilder<>("defaultEngine"); FlowEngine engine = engineBuilder.pipeline(build).build(); EngineContext context = engine.execute(1); diff --git a/smart-flow-core/src/test/java/org/smartboot/flow/core/builder/IfComponentBuilderTest.java b/smart-flow-core/src/test/java/org/smartboot/flow/core/builder/IfComponentBuilderTest.java index 4f545069954136a5e534770d370feb100ada9eb5..f7677c240c2902f207e8dc9c805c2835540c9a95 100644 --- a/smart-flow-core/src/test/java/org/smartboot/flow/core/builder/IfComponentBuilderTest.java +++ b/smart-flow-core/src/test/java/org/smartboot/flow/core/builder/IfComponentBuilderTest.java @@ -20,12 +20,12 @@ public class IfComponentBuilderTest extends BaseTest{ @Test public void testBuild() { - PipelineBuilder builder = new PipelineBuilder<>(); + PipelineBuilder builder = new PipelineBuilder<>("DefaultPipeline"); Pipeline build = builder.next(new IfCondition()).apply(Attributes.DEGRADABLE, true).then(new DefaultStep()) .choose(new ChooseCondition()).newBranch(1, new IntegerStep()) .apply(Attributes.DEGRADABLE, true).end().build(); - EngineBuilder engineBuilder = new EngineBuilder<>(); + EngineBuilder engineBuilder = new EngineBuilder<>("defaultEngine"); FlowEngine engine = engineBuilder.pipeline(build).build(); EngineContext context = engine.execute(1); diff --git a/smart-flow-core/src/test/java/org/smartboot/flow/core/manager/ManagerTest.java b/smart-flow-core/src/test/java/org/smartboot/flow/core/manager/ManagerTest.java index c8cd6bea77be5ffddae9c2ca0c59377ce8bd4741..b7f40c40f6ef8391cf5aacfa8d7e4150c044c012 100644 --- a/smart-flow-core/src/test/java/org/smartboot/flow/core/manager/ManagerTest.java +++ b/smart-flow-core/src/test/java/org/smartboot/flow/core/manager/ManagerTest.java @@ -1,5 +1,6 @@ package org.smartboot.flow.core.manager; +import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.smartboot.flow.core.AsyncStep1; import org.smartboot.flow.core.AsyncStep2; @@ -32,10 +33,16 @@ import java.util.Map; */ public class ManagerTest extends BaseTest { + @BeforeEach + public void setUp() { + DefaultEngineManager.getDefaultManager().detachAll(); + LOGGER.info("detachAll executed"); + } + @Test public void testModifyAttributes() { - PipelineBuilder builder = new PipelineBuilder<>(); + PipelineBuilder builder = new PipelineBuilder<>("DefaultPipeline"); Pipeline build = builder.next(new IfCondition()).apply(Attributes.DEGRADABLE, true).then(new DefaultStep()) .choose(new ChooseCondition()).newBranch(1, new IntegerStep()) .apply(Attributes.DEGRADABLE, true).end() @@ -44,7 +51,7 @@ public class ManagerTest extends BaseTest { .pipeline("subprocess##2").next(new AsyncStep1()).next(new AsyncStep2()).next(new AsyncStep3()).end() .build(); - EngineBuilder engineBuilder = new EngineBuilder<>(); + EngineBuilder engineBuilder = new EngineBuilder<>("defaultEngine"); FlowEngine engine = engineBuilder.pipeline(build).build(); EngineContext context = engine.execute(1); @@ -57,7 +64,7 @@ public class ManagerTest extends BaseTest { Map components = engineModel.getComponents(); String identifier = null; for (Map.Entry modelEntry : components.entrySet()) { - if (modelEntry.getValue().getDescribe().contains("pipeline##subprocess##2")) { + if (modelEntry.getValue().getDescribe().contains("pipeline@subprocess##2")) { identifier = modelEntry.getKey(); } diff --git a/smart-flow-core/src/test/java/org/smartboot/flow/core/parser/DefaultParserTest.java b/smart-flow-core/src/test/java/org/smartboot/flow/core/parser/DefaultParserTest.java index 6314b2ae6b47ef6f82f0ff868d14627841e28453..725bc139ccc989f5469c108f37e8b92cc192231e 100644 --- a/smart-flow-core/src/test/java/org/smartboot/flow/core/parser/DefaultParserTest.java +++ b/smart-flow-core/src/test/java/org/smartboot/flow/core/parser/DefaultParserTest.java @@ -1,12 +1,16 @@ package org.smartboot.flow.core.parser; import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.smartboot.flow.core.BaseTest; import org.smartboot.flow.core.EngineContext; import org.smartboot.flow.core.FlowEngine; +import org.smartboot.flow.core.manager.DefaultEngineManager; import org.smartboot.flow.core.view.plantuml.PlantumlEngineVisitor; +import java.io.InputStream; + /** * @author qinluo * @date 2022-11-15 23:42:32 @@ -14,10 +18,15 @@ import org.smartboot.flow.core.view.plantuml.PlantumlEngineVisitor; */ public class DefaultParserTest extends BaseTest { + @BeforeEach + public void setUp() { + DefaultEngineManager.getDefaultManager().detachAll(); + } + @Test public void testParseNull() { DefaultParser parser = new DefaultParser(); - Exception e = Assertions.assertThrows(IllegalArgumentException.class, () -> parser.parse(null)); + Exception e = Assertions.assertThrows(IllegalArgumentException.class, () -> parser.parse((InputStream) null)); LOGGER.error("", e); } @@ -29,14 +38,6 @@ public class DefaultParserTest extends BaseTest { LOGGER.error("", e); } - @Test - public void testParseWithUncorrectedSubElement() { - DefaultParser parser = new DefaultParser(); - Exception e = Assertions.assertThrows(IllegalArgumentException.class, () -> - parser.parse(this.getClass().getResourceAsStream("/flow-example2.xsd"))); - LOGGER.error("", e); - } - @Test public void testParseSimple() { DefaultParser parser = new DefaultParser(); @@ -71,7 +72,6 @@ public class DefaultParserTest extends BaseTest { @Test public void testParseNestedElementsInPipeline2() { - System.setProperty("use.try", "true"); DefaultParser parser = new DefaultParser(); parser.parse(this.getClass().getResourceAsStream("/flow-example6.xsd")); @@ -84,7 +84,6 @@ public class DefaultParserTest extends BaseTest { @Test public void testParseNestedElementsInPipeline3() { - System.setProperty("use.try", "true"); DefaultParser parser = new DefaultParser(); parser.parse(this.getClass().getResourceAsStream("/flow-example7.xsd")); diff --git a/smart-flow-core/src/test/resources/flow-example.xsd b/smart-flow-core/src/test/resources/flow-example.xsd index 644ae1b414f45adc0e02d879b971e28393efc07b..7231d98d739f050894e97494818efee17ddb1670 100644 --- a/smart-flow-core/src/test/resources/flow-example.xsd +++ b/smart-flow-core/src/test/resources/flow-example.xsd @@ -5,53 +5,4 @@ xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/smart-flow-core/src/test/resources/flow-example2.xsd b/smart-flow-core/src/test/resources/flow-example2.xsd deleted file mode 100644 index 8e3035be70622849dd2c3e13c65617b7e2f07a21..0000000000000000000000000000000000000000 --- a/smart-flow-core/src/test/resources/flow-example2.xsd +++ /dev/null @@ -1,42 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/smart-flow-core/src/test/resources/flow-example7.xsd b/smart-flow-core/src/test/resources/flow-example7.xsd index 23103a0c8f822f5d6aadb2b0d423cc505d7776b3..24d33458090ae6d895a08963ebb3f6854ef5676c 100644 --- a/smart-flow-core/src/test/resources/flow-example7.xsd +++ b/smart-flow-core/src/test/resources/flow-example7.xsd @@ -7,7 +7,7 @@ - + diff --git a/smart-flow-core/src/test/resources/logback.xml b/smart-flow-core/src/test/resources/logback.xml deleted file mode 100644 index 347cb45af1b5f98385fe293ff152629226d2ce4a..0000000000000000000000000000000000000000 --- a/smart-flow-core/src/test/resources/logback.xml +++ /dev/null @@ -1,37 +0,0 @@ - - - - - - - - - %d{yyyy-MM-dd HH:mm:ss.SSS} %-5level %logger{0} [%file:%line] - %msg%n - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/smart-flow-example/pom.xml b/smart-flow-example/pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..fd01f888e08edf97557e722ef7eb28d07fabefd3 --- /dev/null +++ b/smart-flow-example/pom.xml @@ -0,0 +1,54 @@ + + + + flow-engine + org.smartboot + 1.0.1 + + 4.0.0 + + smart-flow-example + + + 8 + 8 + + + + + org.smartboot + smart-flow-manager + 1.0.1 + + + + org.smartboot + smart-flow-spring-extension + 1.0.1 + + + + org.junit.jupiter + junit-jupiter-api + 5.9.1 + test + + + + org.junit.jupiter + junit-jupiter-engine + 5.9.1 + test + + + + org.slf4j + slf4j-log4j12 + 2.0.3 + + + + + \ No newline at end of file diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep1.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep1.java similarity index 88% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep1.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep1.java index e99b3b3ea84f3ad009fe10da14387ffdd2f5c7fc..67645c080934d72e780a1a37d4ba3c41b151d3e7 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep1.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep1.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep2.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep2.java similarity index 90% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep2.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep2.java index dfe37041a76b26a12b3e1d98e7c4661b76ffac4c..8bff547fb6efdf87129c223124dce7392e8ee796 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep2.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep2.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep3.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep3.java similarity index 90% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep3.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep3.java index 804301790b9dce53b8ea0367f8ab1f1cad0635fb..f326a1d82453940fd46b0792ee4fe47ef169ff3d 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/AsyncStep3.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/AsyncStep3.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ChooseCondition.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ChooseCondition.java similarity index 91% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ChooseCondition.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ChooseCondition.java index 521f06b42c6ab7439c3c812aa649297fcaee9ee4..0bba2773ba6022e03602609f3a4e2c37608bacdc 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ChooseCondition.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ChooseCondition.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.Condition; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/DefaultStep.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/DefaultStep.java similarity index 89% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/DefaultStep.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/DefaultStep.java index aebfe7c378e51feb3546bc8bfe9390255b23e22b..679f1a74fceb53cf0f760cda6a4c39c18d4cfec2 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/DefaultStep.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/DefaultStep.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ElseStep.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ElseStep.java similarity index 89% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ElseStep.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ElseStep.java index cfb95e3e9382d9b4e2e945994a72b4c6e4fee29b..22d429501ea6bbcfc6b9e212c8829496dac86400 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ElseStep.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ElseStep.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ErrorStep.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ErrorStep.java similarity index 90% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ErrorStep.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ErrorStep.java index e259f8e7b9fc578925113046dc548966e0b4269f..f0b97fe29c4901e6871b3d63d87144cb275146e1 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ErrorStep.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/ErrorStep.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; import org.springframework.stereotype.Service; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition.java similarity index 88% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition.java index 2a0be9422dfc4805021c73de789f61e58a28d4e5..99b01b2c10b2d2a8538230b67135557b3f85bd5a 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.Condition; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition2.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition2.java similarity index 88% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition2.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition2.java index 02020f621c2446baf35fc9fc408146998c18b5f4..4533495f8c9fb90d2afe96e748e8a50d727e375c 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition2.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition2.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.Condition; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition3.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition3.java similarity index 88% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition3.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition3.java index edf569560369e724a4d756b563ab100735724896..1fb61d9bfde858a01c6ee351682276d0523ecbf4 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IfCondition3.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IfCondition3.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.Condition; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IntegerStep.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IntegerStep.java similarity index 89% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IntegerStep.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IntegerStep.java index 1e2223e9f073723d53a645cc3cbc65e1080864f0..54dbeb4f7a36d00d1ac0cc82ec79957e5a596cd6 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/IntegerStep.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/IntegerStep.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/NullStep.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/NullStep.java similarity index 72% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/NullStep.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/NullStep.java index 6c178159778ffcc2258491c48e1b4022dcbd18b6..f3c6512bd1f07faa67a837b8da293fca089d974a 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/NullStep.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/NullStep.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; @@ -14,6 +14,10 @@ public class NullStep extends AbstractExecutable { @Override public void execute(Integer integer, String s) { + if (integer == null) { + throw new RuntimeException("null value"); + } + System.out.println(getClass()); } } diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step1.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step1.java similarity index 87% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step1.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step1.java index 70a31cc9decdca76bcacb9489d8ae7d07903f54e..a0ff762ee505c3d206ac4635100acd681dc44e93 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step1.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step1.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step2.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step2.java similarity index 87% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step2.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step2.java index 2e450dd2b7036069941b5d28f26069f24f825ffb..0fa36ebd7ef490c194adc839dbf4072ee6a7243c 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step2.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step2.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step3.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step3.java similarity index 89% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step3.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step3.java index b479de47985780c7499be9cf4abb7bc4d7e6a0cc..5c1a1dae20216fbbca97c9b8f41ebe44cec8ee55 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step3.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step3.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step4.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step4.java similarity index 89% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step4.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step4.java index 53f6af02889f11768f55990735a4ddd653a5022e..d343a894f930c80d5a0da1bc9935dcce6643cb63 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step4.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step4.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step5.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step5.java similarity index 89% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step5.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step5.java index c41c06fb318a094e6dc52a586566f812d6e2e3c7..3cd8014aaa99839735ddb5a83d94df378373afaa 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step5.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step5.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step6.java b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step6.java similarity index 89% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step6.java rename to smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step6.java index 1e51c81893ccac4aa74f944e7d8aa7ed734db1a7..54b3661e7caf28b087776e450650164b02adea95 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/Step6.java +++ b/smart-flow-example/src/main/java/org/smartboot/flow/example/extension/Step6.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example.extension; import org.smartboot.flow.core.executable.AbstractExecutable; diff --git a/smart-flow-spring-extension/src/test/resources/bean.xml b/smart-flow-example/src/main/resources/bean.xml similarity index 59% rename from smart-flow-spring-extension/src/test/resources/bean.xml rename to smart-flow-example/src/main/resources/bean.xml index 3258b460575bfa075760f52d0f063d1972acf012..64a4bd9f2de5c97b572f5fb86f06ae00b26d6b90 100644 --- a/smart-flow-spring-extension/src/test/resources/bean.xml +++ b/smart-flow-example/src/main/resources/bean.xml @@ -11,15 +11,34 @@ http://org.smartboot/smart-flow-1.0.0.xsd"> - + + + + + + + + + + + + + + + + + + + - - + + + - + diff --git a/smart-flow-spring-extension/src/test/resources/log4j.properties b/smart-flow-example/src/main/resources/log4j.properties similarity index 100% rename from smart-flow-spring-extension/src/test/resources/log4j.properties rename to smart-flow-example/src/main/resources/log4j.properties diff --git a/smart-flow-spring-extension/src/test/resources/log4j2.properties b/smart-flow-example/src/main/resources/log4j2.properties similarity index 100% rename from smart-flow-spring-extension/src/test/resources/log4j2.properties rename to smart-flow-example/src/main/resources/log4j2.properties diff --git a/smart-flow-spring-extension/src/test/resources/log4jdbc.log4j2.properties b/smart-flow-example/src/main/resources/log4jdbc.log4j2.properties similarity index 100% rename from smart-flow-spring-extension/src/test/resources/log4jdbc.log4j2.properties rename to smart-flow-example/src/main/resources/log4jdbc.log4j2.properties diff --git a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ParseTest.java b/smart-flow-example/src/test/java/org/smartboot/flow/example/ParseTest.java similarity index 84% rename from smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ParseTest.java rename to smart-flow-example/src/test/java/org/smartboot/flow/example/ParseTest.java index 623c891e793a7fdcccd49e03e06134ac0340ae8c..8cdcda6f2364fd67c98dfd6621abbd443275f1ec 100644 --- a/smart-flow-spring-extension/src/test/java/org/smartboot/flow/spring/extension/ParseTest.java +++ b/smart-flow-example/src/test/java/org/smartboot/flow/example/ParseTest.java @@ -1,4 +1,4 @@ -package org.smartboot.flow.spring.extension; +package org.smartboot.flow.example; import org.junit.jupiter.api.Test; @@ -19,7 +19,7 @@ public class ParseTest { private static final Logger LOGGER = LoggerFactory.getLogger(ParseTest.class); @Test - public void testXml() { + public void testXml() throws Exception { ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("classpath:bean.xml"); Object step = context.getBean("step3"); LOGGER.info("step is " + step.getClass().getName()); @@ -29,7 +29,8 @@ public class ParseTest { EngineContext executeContext = testEngine.execute(1); LOGGER.info("trace\n {}", executeContext.getTrace()); - PlantumlEngineVisitor visitor = new PlantumlEngineVisitor("engine-flow3"); - visitor.visit(testEngine); + testEngine.execute((Integer) null); + + Thread.sleep(60000); } } diff --git a/smart-flow-manager/pom.xml b/smart-flow-manager/pom.xml new file mode 100644 index 0000000000000000000000000000000000000000..39dea515ebf0b2dcd229c357989bafc73f0e8f2a --- /dev/null +++ b/smart-flow-manager/pom.xml @@ -0,0 +1,39 @@ + + + + flow-engine + org.smartboot + 1.0.1 + + 4.0.0 + + smart-flow-manager + + + 8 + 8 + + + + + org.smartboot + smart-flow-core + 1.0.1 + + + + org.smartboot.http + smart-http-client + 1.1.17 + + + + com.alibaba + fastjson + 2.0.19 + + + + \ No newline at end of file diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/NamedThreadFactory.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/NamedThreadFactory.java new file mode 100644 index 0000000000000000000000000000000000000000..e358bdae9172c976cf69ff71d716d9b2fbe06a49 --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/NamedThreadFactory.java @@ -0,0 +1,31 @@ +package org.smartboot.flow.manager; + +import java.util.concurrent.ThreadFactory; +import java.util.concurrent.atomic.AtomicInteger; + +/** + * @author qinluo + * @date 2022-11-25 21:38:57 + * @since 1.0.0 + */ +public class NamedThreadFactory implements ThreadFactory { + + private final AtomicInteger sequence = new AtomicInteger(0); + private final String name; + + public NamedThreadFactory(String name) { + this.name = name; + } + + @Override + public Thread newThread(Runnable r) { + if (r instanceof Thread) { + ((Thread) r).setName(name + "-" + sequence.addAndGet(1)); + return (Thread) r; + } + + Thread t = new Thread(r); + t.setName(name + "-" + sequence.addAndGet(1)); + return t; + } +} diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/ChangeModel.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/ChangeModel.java new file mode 100644 index 0000000000000000000000000000000000000000..d1991831dbada424660e57d3059b848fefbc3888 --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/ChangeModel.java @@ -0,0 +1,68 @@ +package org.smartboot.flow.manager.change; + +import java.io.Serializable; + +/** + * @author qinluo + * @date 2022/11/23 21:29 + * @since 1.0.0 + */ +public class ChangeModel implements Serializable { + private static final long serialVersionUID = -3610942087085947434L; + + /** + * Change action + * + * @see org.smartboot.flow.core.manager.ManagerAction + */ + private String action; + + /** + * Change value. + */ + private String value; + + private String identifier; + private String name; + private long timestamp; + + public long getTimestamp() { + return timestamp; + } + + public void setTimestamp(long timestamp) { + this.timestamp = timestamp; + } + + public String getIdentifier() { + return identifier; + } + + public void setIdentifier(String identifier) { + this.identifier = identifier; + } + + public String getAction() { + return action; + } + + public void setAction(String action) { + this.action = action; + } + + public String getValue() { + return value; + } + + public void setValue(String value) { + this.value = value; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } +} diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/HttpManager.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/HttpManager.java new file mode 100644 index 0000000000000000000000000000000000000000..844d4c4bbe72d0b7162c8c5ec94b35e5f2ad0fab --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/HttpManager.java @@ -0,0 +1,184 @@ +package org.smartboot.flow.manager.change; + +import com.alibaba.fastjson.JSON; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.smartboot.flow.core.component.AttributeHolder; +import org.smartboot.flow.core.component.Attributes; +import org.smartboot.flow.core.manager.DefaultEngineManager; +import org.smartboot.flow.core.manager.ManagerAction; +import org.smartboot.flow.core.util.AssertUtil; +import org.smartboot.flow.manager.NamedThreadFactory; +import org.smartboot.flow.manager.report.HostUtils; +import org.smartboot.http.client.HttpClient; +import org.smartboot.http.client.HttpPost; +import org.smartboot.http.common.enums.HeaderNameEnum; + +import java.net.URL; +import java.nio.charset.StandardCharsets; +import java.util.List; +import java.util.Map; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.ScheduledThreadPoolExecutor; +import java.util.concurrent.TimeUnit; + +/** + * @author qinluo + * @date 2022-11-25 22:12:24 + * @since 1.0.0 + */ +public class HttpManager { + + private static final Logger LOGGER = LoggerFactory.getLogger(HttpManager.class); + private final ScheduledExecutorService executorService + = new ScheduledThreadPoolExecutor(1, new NamedThreadFactory("smart-flow-manager-thread")); + + private String url; + private long timeout; + private Map headers; + private long idle; + private HttpClient client; + private String path; + private long delayAtFirst; + private long lastest; + + public void start() { + URL parsedUrl; + try { + parsedUrl = new URL(url); + } catch (Exception e) { + throw new IllegalStateException("invalid url " + url, e); + } + + path = parsedUrl.getPath(); + if (parsedUrl.getQuery() != null) { + path = path + "?" + parsedUrl.getQuery(); + } + + client = new HttpClient(parsedUrl.getHost(), parsedUrl.getPort()); + client.timeout((int)timeout); + + lastest = System.currentTimeMillis(); + executorService.schedule(this::pull, delayAtFirst, TimeUnit.MILLISECONDS); + } + + public void pull() { + client.connect(); + HttpPost post = client.post(path); + + if (headers != null) { + headers.forEach(post::addHeader); + } + + try { + RequestModel model = new RequestModel(); + model.setAddress(HostUtils.getHostIp()); + model.setHost(HostUtils.getHostName()); + model.setTimestamp(lastest); + // 只请求当前机器有的engines + model.setEngineNames(DefaultEngineManager.getDefaultManager().getRegisteredEngineNames()); + + String json = JSON.toJSONString(model); + byte[] bytes = json.getBytes(StandardCharsets.UTF_8); + + post.addHeader(HeaderNameEnum.CONTENT_TYPE.getName(), "application/json;charset=UTF-8"); + post.addHeader(HeaderNameEnum.CONTENT_LENGTH.getName(), String.valueOf(bytes.length)); + + // Use body stream write. + post.bodyStream().write(bytes, 0, bytes.length); + post.bodyStream().flush(); + post.onSuccess(httpResponse -> { + if (httpResponse.getStatus() != 200) { + LOGGER.info("request remote address failed {}, code = {}", url, httpResponse.getStatus()); + return; + } + + LOGGER.info("request remote address success {}", url); + String body = httpResponse.body(); + List changeModels = JSON.parseArray(body, ChangeModel.class); + + for (ChangeModel cm : changeModels) { + ManagerAction action = ManagerAction.get(cm.getAction()); + if (action == null) { + LOGGER.error("unknown action {}", cm.getAction()); + continue; + } + + if (cm.getTimestamp() < lastest) { + continue; + } + + if (action == ManagerAction.CHANGE_ATTRIBUTES) { + AssertUtil.notBlank(cm.getIdentifier(), "identifier must not be null"); + AssertUtil.notBlank(cm.getValue(), "value must not be null"); + Attributes attribute = Attributes.with(cm.getName()); + if (attribute == null) { + LOGGER.error("unknown supported attribute {}, please check version", cm.getName()); + continue; + } + + try { + DefaultEngineManager.getDefaultManager().changeAttributes(cm.getIdentifier(), new AttributeHolder(attribute, cm.getValue())); + } catch (Exception e) { + LOGGER.error("update attribute failed, attribute = {}, identifier = {}, value = {}", + attribute, cm.getIdentifier(), cm.getValue(), e); + } + } else if (action == ManagerAction.RESET_METRICS){ + DefaultEngineManager.getDefaultManager().resetStatistic(cm.getIdentifier()); + } + + } + lastest = System.currentTimeMillis(); + + }) + .onFailure(throwable -> LOGGER.error("request remote address {} failed", url, throwable)); + + post.send(); + } catch (Exception e) { + LOGGER.error("request remote address {} failed", url, e); + } finally { + this.executorService.schedule(this::pull, idle, TimeUnit.MILLISECONDS); + } + } + + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + this.url = url; + } + + public long getTimeout() { + return timeout; + } + + public void setTimeout(long timeout) { + this.timeout = timeout; + } + + public Map getHeaders() { + return headers; + } + + public void setHeaders(Map headers) { + this.headers = headers; + } + + public long getIdle() { + return idle; + } + + public void setIdle(long idle) { + this.idle = idle; + } + + public long getDelayAtFirst() { + return delayAtFirst; + } + + public void setDelayAtFirst(long delayAtFirst) { + this.delayAtFirst = delayAtFirst; + } +} diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/RequestModel.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/RequestModel.java new file mode 100644 index 0000000000000000000000000000000000000000..8aee84d400696a340232594639ea3b4060d4dfe1 --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/change/RequestModel.java @@ -0,0 +1,50 @@ +package org.smartboot.flow.manager.change; + +import java.io.Serializable; +import java.util.List; + +/** + * @author qinluo + * @date 2022-11-25 10:38:04 + * @since 1.0.0 + */ +public class RequestModel implements Serializable { + private static final long serialVersionUID = -457007982997285755L; + + private long timestamp; + private String address; + private String host; + private List engineNames; + + public List getEngineNames() { + return engineNames; + } + + public void setEngineNames(List engineNames) { + this.engineNames = engineNames; + } + + public long getTimestamp() { + return timestamp; + } + + public void setTimestamp(long timestamp) { + this.timestamp = timestamp; + } + + public String getAddress() { + return address; + } + + public void setAddress(String address) { + this.address = address; + } + + public String getHost() { + return host; + } + + public void setHost(String host) { + this.host = host; + } +} diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/AbstractReporter.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/AbstractReporter.java new file mode 100644 index 0000000000000000000000000000000000000000..72ad70c8acf6bd8f905477804518a88cc3b86cce --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/AbstractReporter.java @@ -0,0 +1,68 @@ +package org.smartboot.flow.manager.report; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.smartboot.flow.core.manager.DefaultEngineManager; +import org.smartboot.flow.core.manager.EngineManager; +import org.smartboot.flow.core.manager.EngineModel; +import org.smartboot.flow.manager.NamedThreadFactory; + +import java.util.List; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.ScheduledThreadPoolExecutor; +import java.util.concurrent.TimeUnit; + +/** + * @author qinluo + * @date 2022/11/23 20:35 + * @since 1.0.0 + */ +public abstract class AbstractReporter { + + private static final Logger LOGGER = LoggerFactory.getLogger(AbstractReporter.class); + private final ScheduledExecutorService executorService = new ScheduledThreadPoolExecutor(1, new NamedThreadFactory("export-thread")); + + /** + * Report idle in mills. + */ + protected long idle; + + public long getIdle() { + return idle; + } + + public void setIdle(long idle) { + this.idle = idle; + } + + final void export() { + EngineManager defaultManager = DefaultEngineManager.getDefaultManager(); + List registeredEngineNames = defaultManager.getRegisteredEngineNames(); + + try { + for (String name : registeredEngineNames) { + this.doExport(defaultManager.getEngineModel(name)); + } + } catch (Exception e) { + LOGGER.error("{} export engine model failed.", getClass().getName(), e); + } finally { + executorService.schedule(this::export, idle, TimeUnit.MILLISECONDS); + } + } + + /** + * Start to export data. + */ + public void start() { + this.export(); + } + + + /** + * Export engine model + * + * @param model engine model. + */ + public abstract void doExport(EngineModel model); + +} diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HostUtils.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HostUtils.java new file mode 100644 index 0000000000000000000000000000000000000000..79a9c759820783a30b65fe9ba727c7805e2d4df3 --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HostUtils.java @@ -0,0 +1,51 @@ +package org.smartboot.flow.manager.report; + +import java.net.InetAddress; +import java.net.NetworkInterface; +import java.util.Enumeration; + +/** + * @author qinluo + * @date 2021-10-14 01:52:12 + * @since 1.0.0 + */ +public final class HostUtils { + + /** + * Default hostname and ip. + */ + private static String hostname = "localhost"; + private static String hostIp = "127.0.0.1"; + + private HostUtils() { + + } + + static { + try { + hostname = InetAddress.getLocalHost().getHostName(); + Enumeration networkInterfaces = NetworkInterface.getNetworkInterfaces(); + while (networkInterfaces.hasMoreElements()) { + NetworkInterface networkInterface = networkInterfaces.nextElement(); + Enumeration inetAddresses = networkInterface.getInetAddresses(); + while (inetAddresses.hasMoreElements()) { + InetAddress inetAddress = inetAddresses.nextElement(); + if (!inetAddress.isLoopbackAddress() + && !inetAddress.getHostAddress().contains(":")) { + hostIp = inetAddress.getHostAddress(); + break; + } + } + } + } catch (Exception ignored) { + } + } + + public static String getHostName() { + return hostname; + } + + public static String getHostIp() { + return hostIp; + } +} diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HttpReportModel.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HttpReportModel.java new file mode 100644 index 0000000000000000000000000000000000000000..8de4864679f2894797f00ad51b12323b8d17f876 --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HttpReportModel.java @@ -0,0 +1,51 @@ +package org.smartboot.flow.manager.report; + +import org.smartboot.flow.core.manager.EngineModel; + +import java.io.Serializable; + +/** + * @author qinluo + * @date 2022-11-25 21:38:04 + * @since 1.0.0 + */ +public class HttpReportModel implements Serializable { + private static final long serialVersionUID = -457007982997285755L; + + private long timestamp; + private String address; + private String host; + private EngineModel data; + + public long getTimestamp() { + return timestamp; + } + + public void setTimestamp(long timestamp) { + this.timestamp = timestamp; + } + + public String getAddress() { + return address; + } + + public void setAddress(String address) { + this.address = address; + } + + public String getHost() { + return host; + } + + public void setHost(String host) { + this.host = host; + } + + public EngineModel getData() { + return data; + } + + public void setData(EngineModel data) { + this.data = data; + } +} diff --git a/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HttpReporter.java b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HttpReporter.java new file mode 100644 index 0000000000000000000000000000000000000000..7c7d3d51e48060c783fbebdc394cc3e2f769a1f7 --- /dev/null +++ b/smart-flow-manager/src/main/java/org/smartboot/flow/manager/report/HttpReporter.java @@ -0,0 +1,103 @@ +package org.smartboot.flow.manager.report; + +import com.alibaba.fastjson.JSON; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.smartboot.flow.core.manager.EngineModel; +import org.smartboot.flow.core.util.AssertUtil; +import org.smartboot.http.client.HttpClient; +import org.smartboot.http.client.HttpPost; +import org.smartboot.http.common.enums.HeaderNameEnum; + +import java.net.URL; +import java.nio.charset.StandardCharsets; +import java.util.Map; + +/** + * @author qinluo + * @date 2022/11/23 20:47 + * @since 1.0.0 + */ +public class HttpReporter extends AbstractReporter { + + private static final Logger LOGGER = LoggerFactory.getLogger(HttpReporter.class); + + private String url; + private long timeout; + private URL parsedUrl; + private Map headers; + + @Override + public void start() { + try { + this.parsedUrl = new URL(url); + } catch (Exception e) { + throw new IllegalStateException("invalid url " + url, e); + } + + super.start(); + } + + @Override + public void doExport(EngineModel model) { + AssertUtil.notNull(parsedUrl, "url is invalid."); + + String path = parsedUrl.getPath(); + if (parsedUrl.getQuery() != null) { + path = path + "?" + parsedUrl.getQuery(); + } + + HttpClient httpClient = new HttpClient(parsedUrl.getHost(), parsedUrl.getPort()); + httpClient.timeout((int)timeout); + httpClient.connect(); + HttpPost post = httpClient.post(path); + + if (headers != null) { + headers.forEach(post::addHeader); + } + + HttpReportModel reportModel = new HttpReportModel(); + reportModel.setAddress(HostUtils.getHostIp()); + reportModel.setHost(HostUtils.getHostName()); + reportModel.setTimestamp(System.currentTimeMillis()); + reportModel.setData(model); + + String json = JSON.toJSONString(reportModel); + byte[] bytes = json.getBytes(StandardCharsets.UTF_8); + + post.addHeader(HeaderNameEnum.CONTENT_TYPE.getName(), "application/json;charset=UTF-8"); + post.addHeader(HeaderNameEnum.CONTENT_LENGTH.getName(), String.valueOf(bytes.length)); + + // Use body stream write. + post.bodyStream().write(bytes, 0, bytes.length); + post.bodyStream().flush(); + post.onSuccess(httpResponse -> LOGGER.info("send statistic success, engine: {}", model.getIdentifier())) + .onFailure(throwable -> LOGGER.info("send statistic failed, engine: {}", model.getIdentifier(), throwable)); + + post.send(); + } + + public Map getHeaders() { + return headers; + } + + public void setHeaders(Map headers) { + this.headers = headers; + } + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + this.url = url; + } + + public long getTimeout() { + return timeout; + } + + public void setTimeout(long timeout) { + this.timeout = timeout; + } +} diff --git a/smart-flow-spring-extension/pom.xml b/smart-flow-spring-extension/pom.xml index feb576da67c496a10eecdaef09a885e415a54555..4fb8869f8dff061ce5ef289fef9adddaf7b7bcf1 100644 --- a/smart-flow-spring-extension/pom.xml +++ b/smart-flow-spring-extension/pom.xml @@ -5,7 +5,7 @@ flow-engine org.smartboot - 1.0.0 + 1.0.1 4.0.0 @@ -21,7 +21,7 @@ org.smartboot smart-flow-core - 1.0.0 + 1.0.1 @@ -68,5 +68,12 @@ 5.9.1 test + + + org.junit.jupiter + junit-jupiter-engine + 5.9.1 + test + \ No newline at end of file diff --git a/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/BeanDefinitionVisitor.java b/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/BeanDefinitionVisitor.java index f7ad11b705e19050363c645a867fd6b3ac23db6a..e85745ddda01ce2ba5230d6d8923f82d89b07de0 100644 --- a/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/BeanDefinitionVisitor.java +++ b/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/BeanDefinitionVisitor.java @@ -3,7 +3,6 @@ package org.smartboot.flow.spring.extension; import org.smartboot.flow.core.component.AttributeHolder; import org.smartboot.flow.core.component.Attributes; import org.smartboot.flow.core.parser.DefinitionVisitor; -import org.smartboot.flow.core.parser.ElementUtils; import org.smartboot.flow.core.parser.definition.ChooseDefinition; import org.smartboot.flow.core.parser.definition.ElementDefinition; import org.smartboot.flow.core.parser.definition.EngineDefinition; @@ -11,6 +10,7 @@ import org.smartboot.flow.core.parser.definition.IfElementDefinition; import org.smartboot.flow.core.parser.definition.PipelineComponentDefinition; import org.smartboot.flow.core.parser.definition.PipelineDefinition; import org.smartboot.flow.core.util.AssertUtil; +import org.smartboot.flow.core.util.AuxiliaryUtils; import org.springframework.beans.PropertyValue; import org.springframework.beans.factory.config.BeanDefinition; import org.springframework.beans.factory.config.RuntimeBeanReference; @@ -108,7 +108,7 @@ public class BeanDefinitionVisitor implements DefinitionVisitor { definition.setBeanClass(ed.resolveType()); definition.getPropertyValues().addPropertyValue(name); - if (ElementUtils.isNotBlank(ed.getType()) && isType(ed.getType())) { + if (AuxiliaryUtils.isNotBlank(ed.getType()) && isType(ed.getType())) { RootBeanDefinition conditionDef = new RootBeanDefinition(); conditionDef.setBeanClassName(ed.getType()); definition.getPropertyValues().add("executable", conditionDef); @@ -138,7 +138,7 @@ public class BeanDefinitionVisitor implements DefinitionVisitor { definition.setBeanClass(ed.resolveType()); definition.getPropertyValues().addPropertyValue(name); - if (ElementUtils.isNotBlank(ed.getTest()) && isType(ed.getTest())) { + if (AuxiliaryUtils.isNotBlank(ed.getTest()) && isType(ed.getTest())) { RootBeanDefinition conditionDef = new RootBeanDefinition(); conditionDef.setBeanClassName(ed.getTest()); definition.getPropertyValues().add("condition", conditionDef); @@ -172,7 +172,7 @@ public class BeanDefinitionVisitor implements DefinitionVisitor { definition.getPropertyValues().addPropertyValue(name); definition.getPropertyValues().add("allBranchWasString", true); - if (ElementUtils.isNotBlank(ed.getTest()) && isType(ed.getTest())) { + if (AuxiliaryUtils.isNotBlank(ed.getTest()) && isType(ed.getTest())) { RootBeanDefinition conditionDef = new RootBeanDefinition(); conditionDef.setBeanClassName(ed.getTest()); definition.getPropertyValues().add("condition", conditionDef); diff --git a/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/NameAwareCondition.java b/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/NameAwareCondition.java new file mode 100644 index 0000000000000000000000000000000000000000..6f753bfa4fa9e1f680d1f3b4f3a30c834f6e3c99 --- /dev/null +++ b/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/NameAwareCondition.java @@ -0,0 +1,18 @@ +package org.smartboot.flow.spring.extension; + +import org.smartboot.flow.core.NamedCondition; +import org.springframework.beans.factory.BeanNameAware; + +/** + * @author qinluo + * @date 2022-11-11 21:57:29 + * @since 1.0.0 + */ +public abstract class NameAwareCondition extends NamedCondition implements BeanNameAware { + + @SuppressWarnings("NullableProblems") + @Override + public void setBeanName(String name) { + super.setName(name); + } +} diff --git a/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/NamedAbstractExecutable.java b/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/NamedAbstractExecutable.java index e36ab04c1e215690933bde08b3b75722e9b56e0b..17783f5ebf6dcdfac2cdc57e99e87f9b9496ea5e 100644 --- a/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/NamedAbstractExecutable.java +++ b/smart-flow-spring-extension/src/main/java/org/smartboot/flow/spring/extension/NamedAbstractExecutable.java @@ -20,6 +20,6 @@ public abstract class NamedAbstractExecutable extends AbstractExecutable - - - - - - - - %d{yyyy-MM-dd HH:mm:ss.SSS} %-5level %logger{0} [%file:%line] - %msg%n - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file