3.2 XPath Functions, System Tokens & Date Math
Key Takeaways
- System tokens (such as [%CurrentUser%], [%CurrentDateTime%], and [%BeginOfCurrentDay%]) are dynamic server-side placeholders evaluated at query runtime in UTC.
- The XPath string function starts-with() translates to SQL LIKE 'val%' and utilizes B-tree indexes, whereas contains() translates to LIKE '%val%' and forces a full table scan.
- Mathematical functions (round(), floor(), ceil()) execute on numeric attributes, but wrapping an attribute in a function makes the predicate non-sargable and disables index optimization.
- Date arithmetic combines a time-related token with a duration token, and Mendix requires the whole expression inside one pair of single quotes — for example [OrderDate >= '[%CurrentDateTime%] - 30 * [%DayLength%]'].
- Entity access rules strictly forbid microflow variables ($Variable) and only permit system tokens and fixed literals, whereas microflow database retrieves permit both.
3.2 XPath Functions, System Tokens & Date Math
Intermediate Exam Focus: XPath expressions in Mendix frequently require dynamic evaluation of current users, timestamps, date intervals, and string patterns. For the Intermediate Developer exam, you must distinguish between tokens valid in Entity Access Rules versus Microflows, calculate rolling date ranges using Mendix duration constants, and recognize which XPath functions support or destroy database index utilization.
System Tokens: Dynamic Server-Side Context
System tokens are pre-defined runtime variables enclosed in brackets and percent signs: [%TokenName%]. They are evaluated on the Mendix server when executing an XPath query, converting dynamic environmental context into static parameters passed to the database engine.
Mendix categorizes system tokens into three primary groups:
- User and Identity Tokens: Reflect the active session user.
- Date and Time Boundary Tokens: Provide standardized temporal checkpoints based on calendar periods.
- Time Duration Constants: Represent fixed millisecond intervals used in date math expressions.
User & Identity Tokens
[%CurrentUser%]: Returns theSystem.Userobject ID corresponding to the user executing the query. Frequently used in access rules:[System.owner = '[%CurrentUser%]'][%UserRole_RoleName%]: One token is generated for each user role in the app, and it resolves to that role's identifier rather than to a boolean. It is compared against a user's roles:
Like every other token it must be written inside single quotes.//System.User[System.UserRoles = '[%UserRole_Administrator%]']
Date and Time Boundary Tokens
To prevent discrepancies caused by server vs client clock offsets, Mendix provides calendar boundary tokens. These tokens evaluate to 00:00:00.000 (start of period) or 23:59:59.999 (end of period) in the server's time zone:
| Token Name | Evaluated Time Window | Common Exam Use Case |
|---|---|---|
[%CurrentDateTime%] | Exact current millisecond | Comparing expiration dates, recording audit timestamps |
[%BeginOfCurrentDay%] | 00:00:00.000 of today | Filtering records created or modified today |
[%EndOfCurrentDay%] | 23:59:59.999 of today | Scheduling tasks due before end of day |
[%BeginOfCurrentWeek%] | 00:00:00.000 of Monday (locale default) | Weekly KPI dashboards and weekly task lists |
[%EndOfCurrentWeek%] | 23:59:59.999 of Sunday | Weekly completion tracking |
[%BeginOfCurrentMonth%] | 00:00:00.000 on 1st day of month | Monthly invoicing and reporting ranges |
[%EndOfCurrentMonth%] | 23:59:59.999 on last day of month | Monthly deadline verifications |
[%BeginOfCurrentYear%] | 00:00:00.000 on Jan 1st | Year-to-date (YTD) financial retrieves |
[%EndOfCurrentYear%] | 23:59:59.999 on Dec 31st | Annual audit boundaries |
Each of these tokens also has a corresponding UTC variant (e.g., [%BeginOfCurrentDayUTC%], [%BeginOfCurrentMonthUTC%]), which calculates the boundary relative to UTC rather than the server's local operating system timezone.
Date Arithmetic and Duration Constants
Mendix XPath allows calculating relative date offsets using standard mathematical operators (+ and -) alongside built-in duration tokens.
Duration Tokens
Duration tokens are the period constants you add to or subtract from a date token:
| Token | Length |
|---|---|
[%SecondLength%] | one second |
[%MinuteLength%] | one minute |
[%HourLength%] | one hour |
[%DayLength%] | one day (24 hours) |
[%WeekLength%] | one week (seven days) |
[%MonthLength%] | one month |
[%YearLength%] | one year |
The One-String Rule (memorise this)
Mendix documents two rules for tokens, and the second one is the exam's favourite trap:
- Tokens must be used as string values, placed between quotes.
- A time-related token combined with a duration token must be placed within one string — one opening quote before the date token, one closing quote after the whole arithmetic expression.
// Orders placed in the last 30 days — ONE string, quotes only on the outside
[OrderDate >= '[%CurrentDateTime%] - 30 * [%DayLength%]']
Both of these are wrong:
[OrderDate >= [%CurrentDateTime%] - 30 * [%DayLength%]] // unquoted: parse error
[OrderDate >= '[%CurrentDateTime%]' - 30 * '[%DayLength%]'] // three separate strings, not one expression
A plain boundary comparison with no arithmetic is still a single quoted token, which is why constraints such as [OrderDate >= '[%BeginOfCurrentWeek%]' and OrderDate < '[%EndOfCurrentWeek%]'] are correct — each token is its own complete string because nothing is being added to it.
To retrieve orders created during the previous calendar month:
[OrderDate >= '[%BeginOfCurrentMonth%] - 1 * [%MonthLength%]' and OrderDate < '[%BeginOfCurrentMonth%]']
XPath String Functions
Mendix provides three primary string functions that execute directly inside database queries: contains(), starts-with(), and length().
1. contains(Attribute, 'searchString')
The contains() function determines whether an attribute contains a specified substring.
[contains(CustomerName, 'Logistics')]
- SQL Translation: Compiles to
WHERE CustomerName LIKE '%Logistics%'. - Performance Impact: Extremely costly on large tables. The leading wildcard (
%) prevents the database engine from using standard B-tree indexes, forcing a Full Table Scan.
2. starts-with(Attribute, 'prefixString')
The starts-with() function checks if an attribute begins with a given prefix.
[starts-with(InvoiceNumber, 'INV-2026')]
- SQL Translation: Compiles to
WHERE InvoiceNumber LIKE 'INV-2026%'. - Performance Impact: Highly efficient if an index exists on
InvoiceNumber. Because there is no leading wildcard, the database can perform an Index Range Scan, jumping straight to matching records.
3. length(Attribute)
The length() function returns the integer character count of a string attribute.
[length(PostalCode) = 5]
- SQL Translation: Compiles to
WHERE LEN(PostalCode) = 5(orLENGTH()in PostgreSQL). - Use Case: Data quality checks, validation pipelines, and filtering legacy records missing standardized lengths.
XPath Numeric Functions
Mendix XPath includes mathematical rounding functions applicable to Integer, Long, and Decimal attributes:
round(Attribute): Rounds to the nearest integer according to standard mathematical rounding (0.5 rounds up).[round(DiscountRate) = 15]floor(Attribute): Rounds down to the nearest lower integer.[floor(Rating) >= 4]ceil(Attribute): Rounds up to the nearest higher integer.[ceil(ShippingWeight) <= 10]
The SARGability Trap
Applying functions to an entity attribute inside a predicate (e.g., [round(TotalAmount) = 100]) is a classic performance trap known in database engineering as creating a non-sargable (Search ARGument Able) query. Even if an index exists on TotalAmount, the database must execute the round() function on every single row in the table before evaluating equality.
To maintain index optimization, transform the literal value instead of the attribute:
[TotalAmount >= 99.5 and TotalAmount < 100.5]
Architectural Context: Microflows vs Entity Access Rules
A critical certification distinction is where tokens and variables can be applied:
| Capability | Microflow Retrieve Action | Entity Access Rule (Security) | Page Data Grid Constraint |
|---|---|---|---|
System Tokens ([%CurrentUser%], [%CurrentDateTime%]) | Allowed | Allowed | Allowed |
Microflow Variables ($VariableName, $Parameter) | Allowed | FORBIDDEN (Consistency Error) | FORBIDDEN (Consistency Error) |
Enclosing Page Object ([%CurrentObject%]) | N/A | FORBIDDEN | Allowed (inside nested Data Views) |
| Date Math Calculations | Allowed | Allowed | Allowed |
String Functions (starts-with, contains) | Allowed | Allowed | Allowed |
Why are microflow variables prohibited in Entity Access Rules? Entity Access Rules are compiled at application startup and enforced universally by the Mendix Object Server whenever an entity is accessed—regardless of whether access originates from a page, a REST API, or an internal engine action. Because microflow variables only exist in the call stack of a specific microflow execution, they cannot exist in the global security scope.
Practical Exam Traps & Common Gotchas
Trap 1: Quoting Date Math Incorrectly
Writing [CreatedDate >= [%CurrentDateTime%] - 7 * [%DayLength%]] fails because tokens must be strings. But quoting each token separately — '[%CurrentDateTime%]' - 7 * '[%DayLength%]' — is equally wrong: a time token combined with a duration token has to sit inside one string. The correct constraint is [CreatedDate >= '[%CurrentDateTime%] - 7 * [%DayLength%]'].
Trap 2: Using Microflow Parameters in Entity Access Rules
Attempting to reference $CurrentDepartment or any $Variable in module security entity access rules causes an immediate Studio Pro consistency error. Security rules can only reference system tokens, fixed literals, or paths to [%CurrentUser%].
Trap 3: Month Boundary Arithmetic vs Subtracting 30 Days
Using 30 * [%DayLength%] to find records from "last month" introduces bugs in February, March, and 31-day months. Anchor on [%BeginOfCurrentMonth%] and step back with [%MonthLength%] to respect true calendar boundaries.
An intermediate developer attempts to configure an Entity Access Rule on the Order entity with the following XPath constraint: [Sales.Order_Department/Sales.Department/Id = $UserDepartmentId]. Studio Pro displays a consistency error. Why is this expression rejected?
A microflow needs to retrieve all SupportTicket entities created within the last 14 days relative to the exact moment the microflow runs. Which XPath constraint implements this requirement correctly?
A database contains 2,000,000 Customer records with an index on the PostalCode attribute. Which XPath filter will allow the database engine to execute an efficient index range scan rather than a full table scan?