Understanding Core Expressions

Tasks scripts, use core expressions to handle data. For example, the following task takes two numeric arguments as input, and returns the addition of them as a result.

@Configuration
public class Tasks {
    @Bean
    public ScriptedTaskDescription additionTask() {
        ScriptedTaskDescription task = new ScriptedTaskDescription("add", "Addition");
        task.setDescription("Performs an addition");
        task.getScript()
            .addStatement(AskInputStatement.of("operand 1", true, JobInputType.REAL))
            .addStatement(AskInputStatement.of("operand 2", true, JobInputType.REAL))
            .addStatement(SetVariableStatement.of("sum", NumericExpression.plus(VariableAccessExpression.of("operand 1"), VariableAccessExpression.of("operand 2"))))
            .addStatement(SetTaskOutputStatement.of("result", VariableAccessExpression.of("sum")))
            .addStatement(LogStatement.info(StringExpression.concat(
                VariableAccessExpression.of("operand 1"),
                StringExpression.of(" + "),
                VariableAccessExpression.of("operand 2"),
                StringExpression.of(" = "),
                VariableAccessExpression.of("sum")
            )));
        return task;
    }
}

The generated web client component for this task is the following:

Addition

The following data types are compatible with the Platform:

  • Boolean constants can be returned using the BooleanExpression.TRUE and BooleanExpression.FALSE expressions.

    • The BooleanExpression class also provides the not(Expression), and(Expression...), and or(Expression...) methods that create Boolean expressions evaluating to the corresponding logical operations on the values of their operands, which must evaluate to Boolean values.

    • The BooleanExpression.eq(Expression...) method creates an expression that, when evaluated, evaluates all provided expressions and returns true if, and only if, they all evaluate to the same value. Values are compared with Objects.equals(). Evaluation of the provided expressions stops as soon as the result can be determined. The BooleanExpression.neq(Expression...) method is the negation of the previous.

    • The BooleanExpression.isNull(Expression) method tests whether the provided expression evaluates to the null value. The BooleanExpression.isNotNull(Expression) method is its negation.

  • String constants can be returned using the StringExpression.of(String constant) method.

    • This method is heavily used in scripts, to provide constant string values to methods that expect an expression. The StringExpression.of(Expression expression) method creates an expression that, when evaluated, returns the string representation of the provided expression. This method is similar to Java Object.toString() and is automatically called on the arguments of LogStatement.info() and of StringExpression.concat().

    • The StringExpression.concat(Expression... expressions) method creates an expression that, when evaluated, returns the concatenation of the values of the provided expressions, or their string representations if they do not evaluate to strings.

    • The StringExpression.isEmpty(Expression) method creates an expression that evaluates to a Boolean value. It expects an expression evaluating to a string. The returned expression evaluates to true if the provided expression evaluates to an empty string. If the provided expression evaluates to the null value, the returned expression evaluates to false. The StringExpression.isEmptyOrNull(Expression) method creates an expression that evaluates to true if the provided expression evaluates to an empty string or to the null value.

    • The StringExpression class also provides the following methods, whose semantics is the same as the equivalent Java methods of the String class: startsWith(Expression, Expression), endsWith(Expression, Expression), contains(Expression, Expression), matches(Expression, Expression), lengthOf(Expression), substringOf(Expression, Expression [, Expression]), indexOf(Expression, Expression), lastIndexOf(Expression, Expression), toLowerCase(Expression), toUpperCase(Expression).

  • Number constants can be returned using the NumericExpression class through the of(Number) method.

    • The of(Expression) method parses string expressions for numeric values. Finally, the plus(Expression...), minus(Expression), minus(Expression, Expression), times(Expression...), divide(Expression, Expression), abs(Expression), max(Expression...), and min(Expression...) methods provide the eponymous operations.

    • In addition, the class provides the lt(Expression, Expression), le(Expression, Expression), ge(Expression, Expression), and gt(Expression, Expression) methods, which compare the (expectedly numeric) values of the provided expressions. The expression created by close(Expression expression1, Expression expression2, Expression maxGap) evaluates to true if the absolute value of the difference between the values of expression1 and expression2 is strictly less than the value of maxGap.

  • Temporal constants can be returned using the TemporalExpression class which provides a significant number of methods to create expressions that evaluate to one of the Instant, ZonedDateTime, LocalDateTime, LocalDate, or LocalTime class of the java.time package. All these methods are close replicas of the methods on the respective Java types.

    • In addition, the class provides the isBefore(Expression, Expression) and isAfter(Expression, Expression) methods, which compare the values of the provided expressions. The durationInMilliseconds(Expression, Expression) method returns an expression that evaluates to the duration in milliseconds between the provided expressions. The expressions must evaluate to comparable temporal value, in the sense that they either are both of the same Java type, or they can be converted to the other type, which boils down to one being an Instant and the other a ZonedDateTime.

    • The epochSecondOf(Expression) and epochMilliOf(Expression) methods return expressions that evaluate to the number of seconds, resp. milliseconds, for the provided expressions, which must evaluate to an Instant or a ZonedDateTime.

  • Blob (Opaque Objects) constants can be returned using the BlobExpression.of(byte[] bytes) method which creates an expression that, when evaluated, returns the array of bytes provided. This is typically useful for passing arbitrary and opaque data structures between routines or worker tasks.

    • The BlobExpression.of(Expression) method creates an expression that, when evaluated, returns the representation of the value or content of the provided expression as an array of bytes. For Boolean and numeric values, this will be the bytes of the string representation of the value. For string values, this will be its bytes. For file values, this will be the file content. For scenario data values, this will be the raw content of the scenario data. For list of strings, this will be the bytes of the comma-separated concatenation of the strings. Other kinds of lists are not supported.

    • The BlobExpression.sizeOf(Expression) method creates an expression that, when evaluated, returns a number. It expects the provided expression to evaluate to an array of bytes. The returned expression then evaluates to the size, in bytes, of this array.

  • File constants can be returned using the FileExpression.of(String filename, byte[] fileContent [, String mimeType]) method which creates an expression that, when evaluated, returns a file value object that holds the provided byte array, associated with the provided file name, and optionally the provided MIME type.

    • The FileExpression.of(Expression, Expression, Expression) method is analogous to the previous one, with its first and third arguments expected to evaluate to string values, and its second to an array of bytes. The third argument may also be passed null.

    • The FileExpression.filenameOf(Expression) method creates an expression that evaluates to a string. It expects the provided expression to evaluate to a file value object. The returned expression then evaluates to the file name of this file value object. Similarly, the FileExpression.sizeOf(Expression) and FileExpression.mimeTypeOf(Expression) methods create expressions that evaluate to, respectively, the size (in bytes) of the content and the MIME type of the file value object that the provided expression is expected to evaluate to.

  • List constants can be returned using the ListExpression.of(Expression...) method which creates an expression that, when evaluated, returns the collection of the values to which the provided expressions evaluate. There must be at least one provided expression, and they must all evaluate to the same type. The ListExpression.empty(Type) method creates an expression that evaluates to an empty list, typed as specified.

    • The ListExpression.sizeOf(Expression) method creates an expression that evaluates to the number of elements in the list that the provided expression evaluates to.

    • The ListExpression.elementAt(Expression list, Expression index) method creates an expression that evaluates the expression list and return the element at the index provided by the expression index.

      Note:

      Note that, following best practice for performances, it is preferable to use elementAt on an already created/evaluated list. Also, lists like ListExpression.of(ScenarioDataExpression.of(...) are created and load data on each call of elementAt.