You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@brooklyn.apache.org by he...@apache.org on 2022/12/02 20:03:06 UTC
[brooklyn-server] 13/18: add a workflow.util expression namespace with time and random capabilities
This is an automated email from the ASF dual-hosted git repository.
heneveld pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/brooklyn-server.git
commit c0b03e152a1d05f261a64fc06deb6a4df2478ddf
Author: Alex Heneveld <al...@cloudsoft.io>
AuthorDate: Fri Dec 2 10:21:50 2022 +0000
add a workflow.util expression namespace with time and random capabilities
---
.../workflow/WorkflowExpressionResolution.java | 27 +++++++++++++++
.../workflow/WorkflowInputOutputExtensionTest.java | 40 ++++++++++++++++++++++
2 files changed, 67 insertions(+)
diff --git a/core/src/main/java/org/apache/brooklyn/core/workflow/WorkflowExpressionResolution.java b/core/src/main/java/org/apache/brooklyn/core/workflow/WorkflowExpressionResolution.java
index 4faeb11519..eede7a77c6 100644
--- a/core/src/main/java/org/apache/brooklyn/core/workflow/WorkflowExpressionResolution.java
+++ b/core/src/main/java/org/apache/brooklyn/core/workflow/WorkflowExpressionResolution.java
@@ -37,9 +37,11 @@ import org.apache.brooklyn.util.core.text.TemplateProcessor;
import org.apache.brooklyn.util.exceptions.Exceptions;
import org.apache.brooklyn.util.guava.Maybe;
import org.apache.brooklyn.util.javalang.Boxing;
+import org.apache.brooklyn.util.time.Time;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import java.time.Instant;
import java.util.*;
import java.util.concurrent.Callable;
import java.util.function.Supplier;
@@ -228,6 +230,7 @@ public class WorkflowExpressionResolution {
if ("current_step".equals(key)) return new WorkflowStepModel(currentStepInstance);
if ("previous_step".equals(key)) return newWorkflowStepModelForStepIndex(context.previousStepIndex);
if ("step".equals(key)) return new WorkflowStepModel();
+ if ("util".equals(key)) return new WorkflowUtilModel();
if ("var".equals(key)) return TemplateProcessor.wrapAsTemplateModel(context.workflowScratchVariables);
@@ -291,6 +294,30 @@ public class WorkflowExpressionResolution {
}
}
+ class WorkflowUtilModel implements TemplateHashModel {
+
+ WorkflowUtilModel() {}
+ @Override
+ public TemplateModel get(String key) throws TemplateModelException {
+
+ //id (a token representing an item uniquely within its root instance)
+ if ("now".equals(key)) return TemplateProcessor.wrapAsTemplateModel(System.currentTimeMillis());
+ if ("now_utc".equals(key)) return TemplateProcessor.wrapAsTemplateModel(System.currentTimeMillis());
+ if ("now_instant".equals(key)) return TemplateProcessor.wrapAsTemplateModel(Instant.now());
+ if ("now_iso".equals(key)) return TemplateProcessor.wrapAsTemplateModel(Time.makeIso8601DateStringZ(Instant.now()));
+ if ("now_stamp".equals(key)) return TemplateProcessor.wrapAsTemplateModel(Time.makeDateStampString());
+ if ("now_nice".equals(key)) return TemplateProcessor.wrapAsTemplateModel(Time.makeDateString(Instant.now()));
+ if ("random".equals(key)) return TemplateProcessor.wrapAsTemplateModel(Math.random());
+
+ return ifNoMatches();
+ }
+
+ @Override
+ public boolean isEmpty() throws TemplateModelException {
+ return false;
+ }
+ }
+
public <T> T resolveWithTemplates(Object expression, TypeToken<T> type) {
expression = processTemplateExpression(expression);
return resolveCoercingOnly(expression, type);
diff --git a/core/src/test/java/org/apache/brooklyn/core/workflow/WorkflowInputOutputExtensionTest.java b/core/src/test/java/org/apache/brooklyn/core/workflow/WorkflowInputOutputExtensionTest.java
index a15376328c..ecd28d2f31 100644
--- a/core/src/test/java/org/apache/brooklyn/core/workflow/WorkflowInputOutputExtensionTest.java
+++ b/core/src/test/java/org/apache/brooklyn/core/workflow/WorkflowInputOutputExtensionTest.java
@@ -23,6 +23,7 @@ import org.apache.brooklyn.api.entity.EntityLocal;
import org.apache.brooklyn.api.entity.EntitySpec;
import org.apache.brooklyn.api.mgmt.Task;
import org.apache.brooklyn.api.typereg.RegisteredType;
+import org.apache.brooklyn.core.entity.Dumper;
import org.apache.brooklyn.core.entity.EntityAsserts;
import org.apache.brooklyn.core.resolve.jackson.BeanWithTypePlanTransformer;
import org.apache.brooklyn.core.resolve.jackson.BeanWithTypeUtils;
@@ -44,6 +45,7 @@ import org.apache.brooklyn.util.text.StringEscapes;
import org.apache.brooklyn.util.text.Strings;
import org.testng.annotations.Test;
+import java.time.Instant;
import java.util.List;
import java.util.Map;
import java.util.function.BiFunction;
@@ -669,4 +671,42 @@ public class WorkflowInputOutputExtensionTest extends BrooklynMgmtUnitTestSuppor
Asserts.assertEquals(app.invoke(app.getEntityType().getEffectorByName("myWorkflow").get(), MutableMap.of("x", "A")).getUnchecked(), "Zzz");
}
+ @Test
+ public void testUtil() throws JsonProcessingException {
+ loadTypes();
+ BasicApplication app = mgmt.getEntityManager().createEntity(EntitySpec.create(BasicApplication.class));
+
+ WorkflowEffector eff = new WorkflowEffector(ConfigBag.newInstance()
+ .configure(WorkflowEffector.EFFECTOR_NAME, "myWorkflow")
+ .configure(WorkflowEffector.EFFECTOR_PARAMETER_DEFS, MutableMap.of("x", null))
+ .configure(WorkflowEffector.STEPS, MutableList.<Object>of(
+ "set-sensor random = ${workflow.util.random}",
+ "set-sensor random2 = ${workflow.util.random}",
+ "set-sensor now = ${workflow.util.now}",
+ "set-sensor now_utc = ${workflow.util.now_utc}",
+ "set-sensor now_instant = ${workflow.util.now_instant}",
+ "set-sensor now_stamp = ${workflow.util.now_stamp}",
+ "set-sensor now_iso = ${workflow.util.now_iso}",
+ "set-sensor now_nice = ${workflow.util.now_nice}"
+ ))
+ );
+ eff.apply((EntityLocal) app);
+
+ app.invoke(app.getEntityType().getEffectorByName("myWorkflow").get(), null).getUnchecked();
+ Dumper.dumpInfo(app);
+
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(Double.class, "random"), x -> x>0);
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(Double.class, "random2"), x -> x>0);
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(Double.class, "random"), x -> !app.sensors().get(Sensors.newSensor(Double.class, "random2")).equals(x));
+
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(Long.class, "now"), l -> l > System.currentTimeMillis() - 5*1000 && l <= System.currentTimeMillis());
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(Long.class, "now_utc"), l -> l > System.currentTimeMillis() - 5*1000 && l <= System.currentTimeMillis());
+
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(Instant.class, "now_instant"), l -> l.toEpochMilli() > System.currentTimeMillis() - 5*1000 && l.toEpochMilli() <= System.currentTimeMillis());
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(String.class, "now_iso"), l -> l.startsWith("202") && l.endsWith("Z"));
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(String.class, "now_nice"), l -> l.startsWith("202"));
+ EntityAsserts.assertAttribute(app, Sensors.newSensor(String.class, "now_stamp"), l -> l.startsWith("202"));
+
+ }
+
}