AdapTableQL Expression Technical Reference

View as Markdown

Expression Options

ExpressionOptions

Options for managing Expressions in AdapTable's Query Language

Perform case-sensitive text comparisons when evaluating Expressions

Default

false

Bespoke Aggregated Expression Functions — to complement those provided by
AdapTable (Calculated Column Aggregated / Alert Aggregated).

Omit category (or set 'Aggregation') to list under the Aggregation
Functions-menu section; any other string creates a section with that name.
Use isAvailable with to limit
modules (Alert / Calculated Column only — not Layout Row Summary or Cell
Summary). Toolbar chips still use expressionEditorButtons.

The reducer receives currentValue as the computed input for that
row (the aggregation's input expression, not necessarily a raw column
cell). aggColumnId is set only when the input is a bare column ref.
A name registered in both customStandardFunctions and this map is a
dual name: NAME() is row-wise, NAME{…} is the aggregation.
Extra constants are positional args; per-row logic is a custom
scalar used as the input.

Every aggregation accepts GROUP_BY and WHERE. Further clauses are
capabilities the definition declares: cumulative (accept
CUMULATIVE([orderCol]) — a running value per row), weight (accept
WEIGHT([col]), delivered as weightValue) and returnType (static
result type for Calculated Column data type / type checks). Declared
capabilities are picked up automatically by validation, the Expression
Editor clause chips, the Cumulative editor and the Query Builder.
extends is not supported for aggregations.

Default

undefined (none)

Bespoke Standard Expression Functions — to complement those provided by
AdapTable. “Standard” matches the Expression Editor (vs Aggregated).

Registers both value-producing functions and boolean predicates. A custom
function is treated as a boolean predicate (usable as a filter or alert
condition) only when it declares returnType: 'boolean' — predicates
MUST set that property. returnType is required; use a value from
EXPRESSION_RETURN_TYPES ('boolean' | 'number' | 'string' | 'date' |
'object' | 'null' | 'any').

Set category to a value from EXPRESSION_CATEGORIES (e.g. 'date',
'general', 'custom') so the function appears in the matching Expression
Editor menu. Omit category (or use 'custom') for the Custom menu; any
other string creates a menu with that name.

Entries are flat objects combining the AQL evaluation props
(handler, returnType, operands, docs) with the Adaptable
presentation / availability props (label, icon, isAvailable, …) —
see AdaptableCustomExpressionFunction. Alternatively an entry may be
an AdaptableCustomExpressionFunctionWithExtends partial that inherits
metadata from a system (or previously registered custom) function via
extends — useful when overriding a system operator such as IS_BLANK
while keeping its label / icon / operands.

Boolean predicates stay Expression-Editor-only unless they declare
returnType: 'boolean' and operands with arity 1 or 2 (column-only, or
column + value). Optional label is used in the operator picker.
operands of arity 0 / 3+ do not appear in Query Builder / ColumnFilter.

Toolbar chips are separate: use expressionEditorButtons (same as for
system functions).

Default

undefined (none)

Reference a Column's Header (i.e. FriendlyName) in all Expression overviews (instead of ColumnId)

Default

true

Which UI editors are available for Boolean Expressions, and which opens first

Whether a Module (or specific expression) should be evaluated by AdaptableQL

Default

All Modules are evaluated by AdapTable

evaluateDatesUsingTime?

boolean | ((context:AdaptableColumnContext) => boolean)

Whether date comparisons use the full timestamp (exact instant) rather than the calendar day.

Affects the IN operator on date columns wherever Expressions are evaluated
(Queries, Styled Columns, Alerts, Column Filters, ...): true compares the exact
datetime, false compares the calendar day. Also controls whether the date Column
Filter's distinct-value tree drills down to individual times.
When an IN right-hand value is an ISO string containing T, the exact instant is used regardless.

Default

false

Customise the function/operator chips shown above the Expression Editor.

Called per editor surface with AdapTable's defaultButtons for that type.
Return those unchanged to keep defaults, or amend/replace them (useful when
adding chips for customStandardFunctions / customAggregatedFunctions).

Editor types are intentionally coarse (e.g. standard covers both boolean
and scalar editors; aggregated covers aggregated scalar and aggregated
boolean) so callers are not forced to treat those as separate concepts.

Only chips whose function is available for the current Module are rendered.

Default

undefined (use AdapTable defaults for each editor type)

Fields are items in Data Source that are NOT columns but can be used in Expressions (via FIELD keyword)

isColumnQueryable?

(queryableColumnContext:QueryableColumnContext) => boolean

Can a given column be included in Expressions

Default

undefined (all columns can be used in Expressions)

Whether an Expression Function is available in a given Module (or Column).

Called for each Expression Function and Module combination; return true
to make the function available or false to hide it. The context includes
defaultAvailability (whether the function would be available by default),
which can be returned to keep the standard behaviour.

For Column Filter operators the callback is additionally invoked
per-Column with context.column (and context.columnScope) set, so a
different operator set can be offered per Column. column is undefined
for the module-level pass, so guard on it before applying per-Column logic.

Hiding a function never disables a symbol operator: hiding SUM removes
SUM(…) but + still works (likewise = / EQ, > / GT, ? : / IF).
Keyword operators (CONTAINS, IN, CASE, …) are hidden with their function.

Structural functions (COL, FIELD, QUERY, DATE, $SCOPE, NULL,
VAR, TRUE, FALSE, AND, OR, NOT) cannot be hidden; returning
false for them is ignored (and logs a warning).

Default

undefined (all functions have their default availability)

Repaint cadence (in milliseconds) for cells whose rules depend on the clock
(NOW(), IS_PAST(), ROW_AGE{}) or on a sliding window (WITHIN(...)).
0 disables the live refresh — such cells only repaint on data changes.

Default

1000

Ring-buffer capacity per cell for the observable functions (CHANGE_COUNT,
NET_CHANGE, HIGHEST, PREVIOUS, …): how many changes of one cell are
retained for LAST_N / cumulative reads. Also the LAST_N(n) ceiling.

Default

1000

Maximum time (in milliseconds) to hold a Data Change event in a trailing timeframe

Default

28800000 (~8 hours)

Validate Expressions before they can be run or saved

Default

true

Query variables that can be referenced in Expressions via VAR('name').
Each variable has a name, a static or resolver value, and an optional description.
Evaluated synchronously with each expression evaluation.

AST contract versions a ServerSideRowModel / remote evaluator accepts.
Absent means v1 only (raw parse tree). Include 2 to receive
normalized contract-v2 ASTs from expressionApi.getASTForExpression.

customAggregatedFunctions entries are an AggregatedExpressionFunction:

AggregatedExpressionFunction

Defines an AdapTableQL function that aggregates data

category?

string

Freeform Functions-menu section for Alert Aggregated / Calculated Column
Aggregated editors. Omit (or use 'Aggregation') to list under Aggregation;
any other string becomes its own section label.

cumulative?

boolean | { currentValue: (context:AggregatedExpressionCumulativeValueContext) => any; }

Accept a CUMULATIVE([orderColumn]) clause, e.g.
MY_AGG{[notional], CUMULATIVE([tradeDate])}.

- true — generic running variant: rows are visited in CUMULATIVE
order (per GROUP_BY partition when grouped), reducer accumulates,
and the value recorded for each row is processAggregatedValue (or
the accumulator when absent) evaluated on the prefix so far.
- object — override the per-row read with currentValue when
processAggregatedValue is too expensive to run per row or the
running value is not a function of the accumulator alone.

Declaring the capability also makes the clause known to validation, the
Expression Editor clause chips / Cumulative editor and the Query Builder.

What the aggregation evaluates to (outcome), shown in editor
documentation. Often starts with "Returns …".

examples?

string[]

Examples to use the Aggregated Expression Function

Optional filter which is applied to each row before the reducer is called. If the filter returns false, the row is NOT included in the aggregation.

Mandatory Initial Value for the aggregation.

May be a plain value or a factory function returning a fresh value.
Use a factory when the reducer mutates its accumulator (objects, arrays,
Maps, Sets) — plain object values are deep-cloned per aggregation run
(and per group) for backward compatibility, which is slower.

inputTypes?

ExpressionFunctionInputType[]

Optional argument types.

Where the function is available — same semantics as standard
isAvailable, but restricted to
(Alert Aggregated and Calculated Column Aggregated).
undefined means both aggregated expression modules.

prepareRowValue?

(context:AggregatedExpressionPrepareRowValueContext) => number | string | boolean | Date | undefined

Called for each row AFTER the reducer() and processAggregatedValue() functions
Can be used when each row has a different aggregated value (e.g. percentage = row value / aggregated value).
Returns return value for each individual row (a boolean suits a boolean Calculated Column, e.g. "is in the top K")

Called AFTER the reducer() has processed all values / rows
Can be used to change result of reducer based on the values array (e.g. average = aggregated value / count)

Mandatory Reducer function which is called for each value(row) in the Column Data

Static result type of the aggregation. Drives the Calculated Column data
type, the outer expression type check and editor documentation.
'input' = same type as the aggregated column (MIN / MAX style). When
omitted the result type is unknown (Calculated Columns default to number).

signatures?

string[]

Example Signatures for the Aggregated Expression Function

weight?

boolean

Accept a WEIGHT([column]) clause, e.g.
MY_VWAP{[price], WEIGHT([quantity])}. The resolved weight of the
current row is delivered as weightValue on the reducer,
prepareRowValue and filterRow contexts (and on the cumulative
currentValue context).

editorOptions is an ExpressionEditorOptions:

ExpressionEditorOptions

Options for which Expression UI editors are available and which opens first

Which UI editors can be used for Boolean Expressions (Query Builder, Expression Editor, or both).
Takes precedence over defaultEditor: if only one editor is listed, that editor is shown
and defaultEditor is not evaluated.

Default

['QueryBuilder', 'ExpressionEditor']

Initial Columns/Fields panel layout in the Expression Editor.
- collapsed — column names only (more room for the editor)
- expanded — names plus sample/test value inputs

Default

'collapsed'

Which editor to open first when more than one editor is available.
Receives context (including Module) so the choice can vary by user or surface.
Ignored when availableEditors contains a single item.

Overridden to 'ExpressionEditor' when the current expression cannot be
edited in the Query Builder (non-boolean / value-producing expressions,
advanced constructs such as QUERY / FIELD, or expressions QB cannot
parse). Empty / new expressions still honour this preference.

Default

'QueryBuilder'

expressionEditorButtons returns ExpressionEditorButton objects and receives an ExpressionEditorButtonsContext:

ExpressionEditorButton

A function/operator chip shown above the Expression Editor textarea.

data

string

Text inserted into the editor when the chip is clicked

Registered Expression Function name. When set, the chip is only shown if
that function exists in the editor's function map. Omit for plain-text
inserts (e.g. "INCREASE" / "DECREASE").

icon?

string

Optional icon name (when set, typically shown instead of text)

newRowAfter?

boolean

When true, starts a new toolbar row after this chip

text?

string

Optional label shown on the chip

ExpressionEditorButtonsContext

Context passed when evaluating expressionOptions.expressionEditorButtons

AdapTable's default buttons for this editor type

Coarse editor category: scalar | aggregated | cumulative |
quantile | window | observable (the Observable Calculated Column
editor — hosts that add chips to scalar usually want them here too)

Custom application Context provided in AdaptableOptions.adaptableContext

fields entries are an AdaptableField:

AdaptableField

Used in Expressions to reference row values which are not a column definition

Data Type of field, used to validate and show correctly in UI

label?

string

Label for field (optional - defaults to name)

name

string

Name of field in data source, e.g. 'rowId', 'parentObject.childObject.value'

queryVariables entries are a QueryVariable:

evaluateAdaptableQLExternally receives an EvaluateExpressionExternallyContext:

isColumnQueryable receives a QueryableColumnContext:

isExpressionFunctionAvailable receives a GlobalExpressionFunctionAvailabilityContext:


Expression API

ExpressionApi

Functions related to Expressions in AdapTableQL (the Adaptable Query Language)

Evaluates an Aggregation Expression (e.g. SUM{[price]},
MAX{[price], GROUP_BY([make])}, RANK{OVER([price])}, SUM{[price]} > 1000)
and returns a materialized snapshot: the global value, per-group values
(for GROUP_BY) and a per-row projection (getValueForRow).

When the Expression is a condition, matches is whether at least one
aggregation group satisfies it.

Default target is all loaded grid rows. Pass dataSet to aggregate a
caller-supplied array, or rowScope / rowFilter to narrow the grid
set. The snapshot does not update on data changes — re-evaluate when needed.

Under the server-side row model only currently loaded rows are aggregated;
inspect rowCount to detect partial data.

Evaluates a Standard Expression against a row.
Requires a row target (rowNode, primaryKeyValue, or data) on the request.
Never throws — returns a result envelope with success / errorMessage.

The Expression decides the return value: a condition such as [price] > 100
yields true / false; [price] * 1.19 yields a number.

Direct API evaluation ignores expressionOptions.evaluateAdaptableQLExternally
(that option only skips evaluation inside AdapTable features).

filterDataSet(request)
returns

ExpressionEvaluationResult<Record<string, unknown>[]>

Returns the subset of dataSet matching a boolean Expression, in original
order and with the same object references. Validation runs once; a
per-row evaluation error fails the whole call.

Returns the grid rows matching a boolean Expression, scoped by rowScope
and optionally pre-narrowed by rowFilter. Validation runs once; a
per-row evaluation error fails the whole call. Matching IRowNodes are
returned in source order.

AST for remote / SSRM evaluation. Emits a normalized contract-v2 tree
when expressionOptions.supportedAstContractVersions includes 2;
otherwise the raw parse tree (v1).

Returns all Columns referenced in an Expression

Infers the kind of an Expression from its text: aggregated when it contains an
aggregation (e.g. SUM{[col]}), scalar otherwise — observable reads such as
CHANGE_COUNT{[col], WITHIN(5m)} are scalar. Empty or unparseable text yields scalar.

Returns the Expression with Column Headers in place of Column IDs

Whether a column can be used in an AdapTableQL expression.

Whether the given AggregatedExpression is valid

Whether the given Expression is valid as a boolean predicate (Alert / Format Column /
Grid Filter / etc.). Root QUERY("x") is accepted only when the named query's
declared ReturnType is boolean (or absent).

Whether the given Expression is a valid value-producing scalar expression
(any return type — used by Calculated Column and non-boolean Named Queries).

migratePreV24Expression(expression, options)
returns

{ expression: string; changed: boolean; error?: string; }

Convert a leftover (pre-v24) AdaptableQL string to the v24 greenfield
syntax. Unparseable input is returned unchanged with error set.

v24 introduced brace aggregations (SUM{[price]}), named operands
(CUMULATIVE([d]), WITHIN(5m)), and dropped wrappers such as
CUMUL(...) and TIMEFRAME(...). Persisted state is rewritten on
load by VersionUpgrade24 when autoMigrateState is on. Use this for
a single programmatic / external-config string that has not gone
through that upgrade. The runtime does not accept leftover spellings.

expressionKind is the stored module kind. Required for dual-name
paren calls (SUM([x]) scalar vs aggregation). Omit only when the
leftover is shape-proven (GROUP_BY / CUMUL / TIMEFRAME / …).

Whether date comparisons use the full timestamp (exact instant) rather than
the calendar day for the given column — governs the IN operator on date
columns and the date Column Filter's distinct-value tree granularity.

useCaseSensitivity()
returns

boolean

Whether Expressions are evaluated using Case Sensitivity

See Evaluating Expressions via the API for how to call evaluateStandardExpression / evaluateAggregatedExpression / filter*, including external data sets, row narrowing, what-if overrides and the SSRM partial-data caveat.