Ana içeriğe geç

Array Processing with JEXL Script

Overview

The Message Builder policy supports both single-line JEXL expressions and multi-line JEXL scripts. Script mode is activated when the template expression contains var, for, while, or if/else constructs.

Key Differences

FeatureJEXL ExpressionJEXL Script
Single-line evaluation
Multi-line code
for loop
var declaration
if/else block
return statement

Example 1: Converting a Tag Array to a JSON Array

Input Body

{
"tags": [
{ "id": 1, "name": "outdoor" },
{ "id": 2, "name": "premium" },
{ "id": 3, "name": "sale" }
]
}

Template (JEXL Script)

#{
var result = '[';
var first = true;
for (tag : body.$.tags) {
if (!first) { result = result + ','; }
result = result + '"' + tag.name + '"';
first = false;
}
result + ']'
}
not

Body variables extracted via JSONPath are automatically converted to Java List or Map objects, so they support .size() and index access.

Expected Output

["outdoor","premium","sale"]

Example 2: Summing Order Items

Input Body

{
"items": [
{ "name": "Book", "price": 29.99, "quantity": 2 },
{ "name": "Pen", "price": 4.50, "quantity": 5 },
{ "name": "Notebook", "price": 12.00, "quantity": 3 }
]
}

Template (JEXL Script)

#{
var total = 0;
for (item : body.$.items) {
total = total + (item.price * item.quantity);
}
total
}

Expected Output

118.48

Example 3: Conditional Array Filtering

Filter array elements that meet a specific condition and build a new array.

Input Body

{
"products": [
{ "name": "Laptop", "stock": 0 },
{ "name": "Phone", "stock": 15 },
{ "name": "Tablet", "stock": 0 },
{ "name": "Monitor", "stock": 8 }
]
}

Template (JEXL Script)

#{
var result = '[';
var first = true;
for (p : body.$.products) {
if (p.stock > 0) {
if (!first) { result = result + ','; }
result = result + '"' + p.name + '"';
first = false;
}
}
result + ']'
}

Expected Output

["Phone","Monitor"]

Example 4: Role-Based Authorization with if/else

Assign an authorization level based on user roles.

Setup

Assume a custom variable userRoles is already populated (e.g., from the request body) with value ["admin","editor"].

Template (JEXL Script)

#{
var roles = userRoles;
var level = 'NONE';
for (var role : roles) {
if (role == 'admin') {
level = 'FULL';
} else if (role == 'editor' && level != 'FULL') {
level = 'WRITE';
} else if (role == 'viewer' && level == 'NONE') {
level = 'READ';
}
}
level
}

Result

RolesauthLevel Value
["admin"]FULL
["editor","viewer"]WRITE
["viewer"]READ
[]NONE

Example 5: Accessing Array Elements with $[n] Syntax

To access a specific element of a root-level array, use $[n] syntax.

Input Body (Root Array)

[
{ "id": 1, "name": "First" },
{ "id": 2, "name": "Second" }
]

Variable Reference in Template

#{body.$[0].name}

Output

First
ipucu

$[0] refers to the first element of the root array. $[1].id would return the id of the second element.


Tips and Common Mistakes

How do I reference body array variables?

Use the standard body.$.path syntax directly inside the JEXL script. For example, for (tag : body.$.tags) iterates over the tags array. JSON array and object values are automatically converted to Java List and Map objects, enabling iteration and property access.

Can I use the `return` keyword?

Yes, in JEXL Script mode you can use return value explicitly. However, returning a value from the last expression (as in examples above) is the recommended approach.

Can I include `{` and `}` inside script templates?

Yes. The Message Builder uses a balanced brace scanner to correctly identify #{} blocks, including those with nested curly braces such as JSON object literals.

Can I use while loops?

Yes, JEXL Script supports while loops as well:

#{
var list = body.$.items;
var i = 0;
var sum = 0;
while (i < list.size()) {
sum = sum + list[i].value;
i = i + 1;
}
sum
}