Oihana PHP Arango

FilterTrait uses trait:short, trait:short, trait:short, trait:short, trait:short, trait:short, trait:short, trait:short, trait:short, trait:short

Defines the 'filtering' strategy property in the models (AQL Documents) definition.

Models::APIS => fn( ContainerInterface $container ) => new Documents
(
    $container ,
    [
        AQL::COLLECTION => Collections::APIS ,
        ...
        AQL::FILTERS =>
        [
             Prop::ACTIVE     => FilterType::BOOL ,
             Prop::CREATED    => FilterType::DATE ,
             Prop::IDENTIFIER => FilterType::STRING ,
             Prop::NAME       => FilterType::STRING ,
        ]
        ...

Usage in the routes parameters

?filter={ "key":"key", "val":"value" , "op":"operator" , "alt":"func" , ...options }

Conditions filters (group)

?filter=[ condition1 , condition2 ]
-> FILTER (condition1 && condition2)

?filter=[ "and" , condition1 , condition2 ]
-> FILTER (condition1 && condition2)

?filter=[ "or"  , condition1 , condition2 ]
-> FILTER (condition1 || condition2)

?filter=[ "and" , ["or",condition1,condition2],["or",condition3,condition4]]
-> FILTER ( (condition1 || condition2) && (condition3 || condition4) )

?filter=[ "not" , condition]
-> FILTER !(condition)

Example :

?filter=["or",{"key":"name","val":"marc"},{"key":"identifier","val":"xyz"}]
-> FILTER (doc.name=="marc" || doc.identifier=="xyz")

Basic operators

equals

?filter={ "key":"name" , "op":"eq" , "val":"xyz" }
-> FILTER doc.name == "xyz"

not equals

?filter={ "key":"name" , "op":"ne" , "val":"xyz" }
-> FILTER doc.name != "xyz"

greater than

?filter={ "key":"name" , "op":"gt" , "val":"xyz" }
-> FILTER doc.name > "xyz"

greater than or equals

?filter={ "key":"name" , "op":"ge" , "val":"xyz" }
-> FILTER doc.name >= "xyz"

less than

?filter={ "key":"name" , "op":"lt" , "val":"xyz" }
-> FILTER doc.name < "xyz"

less than or equals

?filter={ "key":"name" , "op":"le" , "val":"xyz" }
-> FILTER doc.name <= "xyz"

like

?filter={ "key":"name" , "op":"like" , "val":"xyz%" }
-> FILTER doc.name LIKE "xyz%"

not like

?filter={ "key":"name" , "op":"nlike" , "val":"%xyz" }
-> FILTER doc.name NOT LIKE "%xyz"

in

?filter={ "key":"category" , "op":"in" , "val":["xyz","abc"] }
-> FILTER doc.category IN ["xyz","abc"]

not in

?filter={ "key":"name" , "op":"nin" , "val":["xyz","abc"] }
-> FILTER doc.name NOT IN ["xyz","abc"]

match (regex)

?filter={ "key":"name" , "op":"match" , "val":"^f[o].$" }
-> FILTER doc.name =~ "^f[o].$"

not match (regex)

?filter={ "key":"name" , "op":"nmatch" , "val":"[a-z]+bar$" }
-> FILTER doc.name !~ "[a-z]+bar$"

Boolean filters

?filter={ "key":"active" , "val":true  }
-> FILTER doc.active == true

?filter={ "key":"active" , "val":false }
-> FILTER doc.active == false

Number filters

?filter={ "key":"price" , "val":25 }
-> FILTER doc.price == 25

?filter={ "key":"price" , "val":25 , "op":"ge" }
-> FILTER doc.price >= 25

?filter={ "key":"price" , "val":25 , "op":"ge" , "alt":"abs" }
-> FILTER ABS(doc.price) >= 25

String filters

?filter={ "key":"name" , "val":"ekameleon" }
-> FILTER doc.name == "ekameleon"

?filter={ "key":"name" , "val":9 , "alt":"length" }
-> FILTER LENGTH(doc.name) == 9

?filter={ "key":"name" , "val":"ekameleon" , "alt":"lower" }
-> FILTER LOWER(doc.name) == "ekameleon"

?filter={ "key":"name" , "val":"ekameleon" , "alt":"trim" , "type":0 }
-> FILTER TRIM(doc.name, 0) == "ekameleon"

?filter={ "key":"name" , "val":"EKAMELEON" , "alt":"upper" }
-> FILTER UPPER(doc.name) == "EKAMELEON"

Date filters

?filter={ "key":"created" , "val":"2024-01-01" , "op":"ge" }
-> FILTER doc.created >= "2024-01-01"

?filter={ "key":"created" , "val":"2024-01-01" , "op":"between" , "max":"2024-12-31" }
-> FILTER doc.created >= "2024-01-01" && doc.created <= "2024-12-31"

Array filters with functions

?filter={ "key":"values" , "op":"ge" , "val":10 , "alt":"avg" }
-> FILTER AVERAGE(doc.values) >= 10

?filter={ "key":"values" , "op":"ge" , "val":10 , "alt":"count" }
-> FILTER LENGTH(doc.values) >= 10

?filter={ "key":"values" , "op":"ge" , "val":10 , "alt":"max" }
-> FILTER MAX(doc.values) >= 10

?filter={ "key":"values" , "op":"ge" , "val":10 , "alt":"sum" }
-> FILTER SUM(doc.values) >= 10

Array filters with comparators (ALL, ANY, NONE)

?filter={ "key":"values" , "op":"all.eq" , "val":4 }
-> FILTER doc.values ALL == 4

?filter={ "key":"values" , "op":"any.gt" , "val":100 }
-> FILTER doc.values ANY > 100

?filter={ "key":"values" , "op":"none.in" , "val":[1,2,3] }
-> FILTER doc.values NONE IN [1,2,3]

Hierarchical filters - Nested documents

?filter={ "key":"address.email" , "val":"john@doe.com" }
-> FILTER doc.address.email == "john@doe.com"

?filter={ "key":"address.postalCode" , "val":"75001" }
-> FILTER doc.address.postalCode == "75001"

Hierarchical filters - Array expansion

?filter={ "key":"contactPoint[*].email" , "op":"ne" , "val":null }
-> FILTER LENGTH(doc.contactPoint[* FILTER CURRENT.email != null]) > 0

?filter={ "key":"contactPoint[*].email" , "val":"admin@acme.com" }
-> FILTER LENGTH(doc.contactPoint[* FILTER CURRENT.email == "admin@acme.com"]) > 0

?filter={ "key":"contactPoint[*].telephone" , "op":"like" , "val":"06%" }
-> FILTER LENGTH(doc.contactPoint[* FILTER CURRENT.telephone LIKE "06%"]) > 0

Hierarchical filters - Array expansion with combined conditions (match)

Simple syntax (all fields use "eq" operator, combined with AND logic):

?filter={ "key":"additionalProperty[*]" , "match":{ "propertyID":"generateReceipt" , "value":true } }
-> FILTER LENGTH(doc.additionalProperty[* FILTER CURRENT.propertyID == "generateReceipt" && CURRENT.value == true]) > 0

Explicit syntax with ALL logic (AND - all conditions must be true):

?filter={
  "key":"additionalProperty[*]",
  "match":{
    "all":[
      {"key":"propertyID","op":"eq","val":"generateReceipt"},
      {"key":"value","op":"eq","val":false}
    ]
  }
}
-> FILTER LENGTH(doc.additionalProperty[* FILTER CURRENT.propertyID == "generateReceipt" && CURRENT.value == false]) > 0

ANY logic (OR - at least one condition must be true):

?filter={
  "key":"contactPoint[*]",
  "match":{
    "any":[
      {"key":"email","op":"ne","val":null},
      {"key":"telephone","op":"ne","val":null}
    ]
  }
}
-> FILTER LENGTH(doc.contactPoint[* FILTER CURRENT.email != null || CURRENT.telephone != null]) > 0

NONE logic (NOT - no condition must be true):

?filter={
  "key":"additionalProperty[*]",
  "match":{
    "none":[
      {"key":"propertyID","op":"eq","val":"archived"},
      {"key":"propertyID","op":"eq","val":"deleted"}
    ]
  }
}
-> FILTER LENGTH(doc.additionalProperty[* FILTER !(CURRENT.propertyID == "archived" || CURRENT.propertyID == "deleted")]) > 0

Hierarchical filters - Edges (single level)

?filter={ "key":"employee[*].givenName" , "val":"John" }
-> FILTER LENGTH(FOR v IN OUTBOUND doc edge FILTER v.givenName == "John" LIMIT 1 RETURN 1) > 0

?filter={ "key":"employee[*].familyName" , "op":"like" , "val":"Do%" }
-> FILTER LENGTH(FOR v IN OUTBOUND doc edge FILTER v.familyName LIKE "Do%" LIMIT 1 RETURN 1) > 0

Hierarchical filters - Edges (nested multi-level)

?filter={ "key":"employee[*].workLocation.address.email" , "val":"office@acme.com" }
-> FILTER LENGTH(FOR v1 IN OUTBOUND doc edge1
     FILTER LENGTH(FOR v2 IN OUTBOUND v1 edge2
       FILTER v2.address.email == "office@acme.com"
       LIMIT 1 RETURN 1) > 0
     LIMIT 1 RETURN 1) > 0

?filter={ "key":"employee[*].workLocation.name" , "op":"like" , "val":"%Paris%" }
-> FILTER LENGTH(FOR v1 IN OUTBOUND doc edge1
     FILTER LENGTH(FOR v2 IN OUTBOUND v1 edge2
       FILTER v2.name LIKE "%Paris%"
       LIMIT 1 RETURN 1) > 0
     LIMIT 1 RETURN 1) > 0

Hierarchical filters - Array expansion within edges

?filter={ "key":"employee[*].contactPoint[*].email" , "op":"ne" , "val":null }
-> FILTER LENGTH(FOR v IN OUTBOUND doc edge
     FILTER LENGTH(v.contactPoint[* FILTER CURRENT.email != null]) > 0
     LIMIT 1 RETURN 1) > 0

?filter={ "key":"employee[*].contactPoint[*].email" , "op":"like" , "val":"%@gmail.com" }
-> FILTER LENGTH(FOR v IN OUTBOUND doc edge
     FILTER LENGTH(v.contactPoint[* FILTER CURRENT.email LIKE "%@gmail.com"]) > 0
     LIMIT 1 RETURN 1) > 0

Hierarchical filters - Joins

?filter={ "key":"assignedSeller.name" , "val":"John Doe" }
-> FILTER LENGTH(FOR j IN collection FILTER j.id == doc.assignedSeller && j.name == "John Doe" LIMIT 1 RETURN 1) > 0

?filter={ "key":"assignedSeller.id" , "val":"300" }
-> FILTER LENGTH(FOR j IN collection FILTER j.id == doc.assignedSeller && j.id == "300" LIMIT 1 RETURN 1) > 0

Complex hierarchical examples

// Multiple conditions on different arrays (separate elements can satisfy each condition)
?filter=[
  {"key":"additionalProperty[*].propertyID","val":"generateReceipt"},
  {"key":"additionalProperty[*].value","val":true}
]
-> FILTER LENGTH(doc.additionalProperty[* FILTER CURRENT.propertyID == "generateReceipt"]) > 0
   AND LENGTH(doc.additionalProperty[* FILTER CURRENT.value == true]) > 0

// Same element must satisfy all conditions (use match)
?filter={
  "key":"additionalProperty[*]",
  "match":{
    "propertyID":"generateReceipt",
    "value":true
  }
}
-> FILTER LENGTH(doc.additionalProperty[* FILTER CURRENT.propertyID == "generateReceipt" && CURRENT.value == true]) > 0

// Complex nested traversal with multiple levels
?filter={ "key":"location[*].address.email" , "val":"site@acme.com" }
-> FILTER LENGTH(FOR v IN OUTBOUND doc edge FILTER v.address.email == "site@acme.com" LIMIT 1 RETURN 1) > 0

Table of Contents

Constants

FILTERS  : string = 'filters'
The 'filters' parameter constant.

Properties

$filters  : array<string|int, mixed>|null
Defines all valid filtering conditions for queries used in the list() and count() methods.

Methods

bind()  : string
Bind a value to an AQL query variable.
bindCollection()  : string
Bind a collection name to an AQL query variable.
bindView()  : string
Bind the model's declared View name (`AQL::VIEW` block, {@see Search::NAME}) to an AQL query variable — collection bind parameters (`@@view`) are valid for View names as well.
documentFilterPaths()  : array<string|int, mixed>
Generate documentation of all supported filter paths
initializeFilters()  : static
Initialize the 'filters' property.
prepareFilter()  : string|null
Prepare the AQL query filtering with specific definitions.
prepareFilterConditions()  : string|null
Prepares the filter clause with a collection of conditions.
alterFilterKey()  : string
Apply the key-side (left) `alt` transformation to a key expression.
prepareFilterArray()  : string
Prepares the filter clause with a string attribute.
prepareFilterArrayComparator()  : string
Prepares the filter clause with a specific operator.
prepareFilterArrayKey()  : string
Prepares the filter clause of a string attribute with a specific key and document.
prepareFilterAtLeast()  : string
Builds an `AT LEAST (n)` array quantifier filter: at least `n` elements of the array satisfy the comparison.
prepareFilterBetween()  : string
Prepares an inclusive `between` (range) clause: `key >= @min && key <= @max`.
prepareFilterBoolean()  : string
Prepares the filter clause with a boolean attribute.
prepareFilterBooleanValue()  : mixed
Prepare the filter clause with a specific boolean value to evaluates.
prepareFilterComparator()  : string
Prepares the filter clause with a specific operator.
prepareFilterDate()  : string
Prepares the filter clause with a Date attribute.
prepareFilterDateBound()  : string
Resolves a single date bound (value or `between` min/max) to AQL.
prepareFilterDateValue()  : string
Prepares the value of a date attribute in a filter clause.
prepareFilterEndsWith()  : string
Builds an `ew` (ends with) string filter.
prepareFilterGeo()  : string
Prepares the filter clause for a geospatial attribute.
prepareFilterKey()  : string
Prepares the filter clause with a specific key and document, with optional function transformations via 'alt' parameter.
prepareFilterNumber()  : string
Prepares the filter clause with a string attribute.
prepareFilterQuantified()  : string
Builds a quantified comparison on a scalar array via the `quant` key: how many elements satisfy the comparison.
prepareFilterString()  : string
Prepares the filter clause with a string attribute.
prepareFilterValue()  : string
Prepare the filter clause with a specific value to evaluates.
prepareHierarchicalFilter()  : string|null
Prepare hierarchical filter from declarative configuration
buildArrayTraversal()  : string|null
Build array expansion traversal.
buildDocumentTraversal()  : string|null
Build document traversal (nested object)
buildEdgeTraversal()  : string|null
Build edge traversal
buildFilterPathsRecursive()  : void
Recursively build filter paths documentation
buildFilterRecursive()  : string|null
Build filter condition recursively through path segments.
buildJoinTraversal()  : string|null
Build join traversal
buildLeafCondition()  : string|null
Build leaf condition by delegating to existing filter logic

Constants

FILTERS

The 'filters' parameter constant.

public string FILTERS = 'filters'

Properties

$filters

Defines all valid filtering conditions for queries used in the list() and count() methods.

public array<string|int, mixed>|null $filters = []

Methods

bind()

Bind a value to an AQL query variable.

public bind(mixed $value[, array<string|int, mixed> &$binds = [] ][, string|null $to = null ]) : string
Parameters
$value : mixed

The value to bind to the query.

$binds : array<string|int, mixed> = []

Reference to the array of existing bind variables.

$to : string|null = null

Optional name of the bind variable. If null, a unique name is generated.

Tags
throws
BindException

If the provided bind variable name is invalid.

Return values
string

The formatted bind variable (including the "@" prefix as needed) for use in the query.

bindCollection()

Bind a collection name to an AQL query variable.

public bindCollection([array<string|int, mixed> &$binds = [] ][, array<string|int, mixed> $init = [] ]) : string

Prepares a bind variable for a collection name. Uses the collection defined in $init or falls back to $this->collection if none is provided.

Parameters
$binds : array<string|int, mixed> = []

Reference to the array of existing bind variables. If null, a new array is used.

$init : array<string|int, mixed> = []

Optional initialization array with keys:

  • Arango::COLLECTION => the collection name to bind
  • Arango::NAME => optional bind variable name
Tags
throws
BindException

If the bind variable name is invalid.

Return values
string

The formatted bind variable representing the collection.

bindView()

Bind the model's declared View name (`AQL::VIEW` block, {@see Search::NAME}) to an AQL query variable — collection bind parameters (`@@view`) are valid for View names as well.

public bindView([array<string|int, mixed> &$binds = [] ]) : string
Parameters
$binds : array<string|int, mixed> = []

Reference to the array of existing bind variables.

Tags
throws
BindException

If the bind variable name is invalid.

Return values
string

The formatted bind variable representing the View.

documentFilterPaths()

Generate documentation of all supported filter paths

public documentFilterPaths([bool $includeTypes = true ][, bool $includeRelations = false ]) : array<string|int, mixed>
Parameters
$includeTypes : bool = true

Include filter types in output

$includeRelations : bool = false

Include relation references

Tags
example
$customersModel = $container->get(Models::CUSTOMERS);

$filterPaths = $customersModel->documentFilterPaths();

foreach ( $filterPaths as $path )
{
    echo $path['path'] . "\n";
}

Output :

name
id
status
created
modified
address
address.email
address.street
address.city
address.postalCode
additionalProperty[*]
additionalProperty[*].propertyID
additionalProperty[*].value
contactPoint[*]
contactPoint[*].email
contactPoint[*].telephone
employee[*]
employee[*].givenName
employee[*].familyName
employee[*].contactPoint[*]
employee[*].contactPoint[*].email
employee[*].workLocation
employee[*].workLocation.name
employee[*].workLocation.address
employee[*].workLocation.address.email
assignedSeller
assignedSeller.name
assignedSeller.givenName
category[*]
category[*].id
category[*].name
location[*]
location[*].name
location[*].address
location[*].address.email
Return values
array<string|int, mixed>

Array of supported filter paths with metadata

initializeFilters()

Initialize the 'filters' property.

public initializeFilters([array<string|int, mixed> $init = [] ]) : static
Parameters
$init : array<string|int, mixed> = []
Return values
static

prepareFilter()

Prepare the AQL query filtering with specific definitions.

public prepareFilter([array<string|int, mixed>|null $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $docRef = AQL::DOC ]) : string|null
Parameters
$init : array<string|int, mixed>|null = []
$binds : array<string|int, mixed>|null = null
$docRef : string = AQL::DOC
Tags
throws
BindException
ConstantException
ContainerExceptionInterface
DependencyException
NotFoundException
NotFoundExceptionInterface
ReflectionException
UnsupportedOperationException
ValidationException
Return values
string|null

prepareFilterConditions()

Prepares the filter clause with a collection of conditions.

public prepareFilterConditions([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $docRef = AQL::DOC ]) : string|null
Parameters
$init : array<string|int, mixed> = []
$binds : array<string|int, mixed>|null = null
$docRef : string = AQL::DOC
Tags
throws
BindException
ConstantException
ContainerExceptionInterface
NotFoundExceptionInterface
ReflectionException
UnsupportedOperationException
Return values
string|null

alterFilterKey()

Apply the key-side (left) `alt` transformation to a key expression.

protected alterFilterKey(string $key[, array<string|int, mixed> $init = [] ]) : string

Thin wrapper over static::alterExpression(): it resolves the alt parameter into its key/value sides via static::resolveAltSides() and applies the key-side chain. The three legacy alt forms (string, list of functions, function-with-params) keep transforming the key only, unchanged.

Parameters
$key : string

The key expression to transform.

$init : array<string|int, mixed> = []

Filter initialization array containing the 'alt' parameter.

Tags
throws
UnsupportedOperationException
ValidationException
Return values
string

The transformed key expression.

prepareFilterArray()

Prepares the filter clause with a string attribute.

protected prepareFilterArray([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $docRef = AQL::DOC ]) : string
Parameters
$init : array<string|int, mixed> = []
$binds : array<string|int, mixed>|null = null
$docRef : string = AQL::DOC
Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterArrayComparator()

Prepares the filter clause with a specific operator.

protected prepareFilterArrayComparator([array<string|int, mixed> $init = [] ]) : string
Parameters
$init : array<string|int, mixed> = []
Return values
string

prepareFilterArrayKey()

Prepares the filter clause of a string attribute with a specific key and document.

protected prepareFilterArrayKey([string|array<string|int, mixed>|null $init = [] ][, string $docRef = AQL::DOC ]) : string
Parameters
$init : string|array<string|int, mixed>|null = []
$docRef : string = AQL::DOC
Tags
throws
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterAtLeast()

Builds an `AT LEAST (n)` array quantifier filter: at least `n` elements of the array satisfy the comparison.

protected prepareFilterAtLeast(array<string|int, mixed> $init[, array<string|int, mixed>|null &$binds = null ][, string $docRef = AQL::DOC ]) : string

The operator is the array form ["atLeast.<cmp>", n] (element 0 is the atLeast.<cmp> code, element 1 the threshold, defaulting to 1). The <cmp> suffix reuses FilterComparator (eq, ne, gt, ge, lt, le, in, nin). The threshold is cast to an int and inlined (injection-safe); the value is bound. The compared key stays alt-aware.

doc.scores AT LEAST (2) >= @value
Parameters
$init : array<string|int, mixed>

The filter init (op = ["atLeast.<cmp>", n]).

$binds : array<string|int, mixed>|null = null

The bind variables, populated by reference.

$docRef : string = AQL::DOC

The document reference.

Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterBetween()

Prepares an inclusive `between` (range) clause: `key >= @min && key <= @max`.

protected prepareFilterBetween(array<string|int, mixed> $init, array<string|int, mixed>|null &$binds, string $docRef, callable $resolve, bool $defaultBounds) : string

The compared key is alt-aware (it flows through static::alterFilterKey()). Each bound is resolved by $resolve, which differs per filter type — a raw bind for numbers/strings, the date machinery (now / timezone) for dates.

Bound omission is type-driven:

  • $defaultBounds = false (number/string): an omitted bound drops its side, yielding a one-sided range (key >= @min or key <= @max).
  • $defaultBounds = true (date): an omitted bound still emits a clause; the resolver maps the null value to "now", so the range is always two-sided.
Parameters
$init : array<string|int, mixed>

The filter init (reads min / max).

$binds : array<string|int, mixed>|null

The bind variables, populated by reference.

$docRef : string

The document reference.

$resolve : callable

fn(mixed $value, ?array &$binds): string — resolves a bound to AQL.

$defaultBounds : bool

Whether an omitted bound still emits a clause (dates) or is dropped.

Tags
throws
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterBoolean()

Prepares the filter clause with a boolean attribute.

protected prepareFilterBoolean([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $doc = AQL::DOC ]) : string
Parameters
$init : array<string|int, mixed> = []
$binds : array<string|int, mixed>|null = null
$doc : string = AQL::DOC
Tags
throws
BindException
UnsupportedOperationException
Return values
string

prepareFilterBooleanValue()

Prepare the filter clause with a specific boolean value to evaluates.

protected prepareFilterBooleanValue([array<string|int, mixed>|null $init = [] ][, array<string|int, mixed>|null &$binds = null ]) : mixed
Parameters
$init : array<string|int, mixed>|null = []
$binds : array<string|int, mixed>|null = null
Tags
throws
BindException

prepareFilterComparator()

Prepares the filter clause with a specific operator.

protected prepareFilterComparator([array<string|int, mixed> $init = [] ]) : string
Parameters
$init : array<string|int, mixed> = []
Return values
string

prepareFilterDate()

Prepares the filter clause with a Date attribute.

protected prepareFilterDate([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $doc = AQL::DOC ]) : string
Parameters
$init : array<string|int, mixed> = []
$binds : array<string|int, mixed>|null = null
$doc : string = AQL::DOC
Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterDateBound()

Resolves a single date bound (value or `between` min/max) to AQL.

protected prepareFilterDateBound(mixed $value, array<string|int, mixed> $init[, array<string|int, mixed>|null &$binds = null ]) : string

The magic values resolve to AQL date functions (now/null → DATE_ISO8601(DATE_NOW()), cts → DATE_NOW(), tomorrow/yesterday); any other value is bound, and converted from the request timezone (tz) to UTC when one is supplied.

Parameters
$value : mixed

The bound value (null means "now").

$init : array<string|int, mixed>

The filter init (reads tz).

$binds : array<string|int, mixed>|null = null

The bind variables, populated by reference.

Tags
throws
BindException
Return values
string

prepareFilterDateValue()

Prepares the value of a date attribute in a filter clause.

protected prepareFilterDateValue([string|array<string|int, mixed>|null $init = [] ][, array<string|int, mixed>|null &$binds = null ]) : string
Parameters
$init : string|array<string|int, mixed>|null = []
$binds : array<string|int, mixed>|null = null
Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterEndsWith()

Builds an `ew` (ends with) string filter.

protected prepareFilterEndsWith([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $doc = AQL::DOC ]) : string

AQL has no ENDS_WITH function, so the suffix is matched literally with RIGHT(key, CHAR_LENGTH(value)) == value — no LIKE pattern, nothing to escape, symmetric to the literal sw / STARTS_WITH form. The value is bound once and reused; alt stays available on both sides (e.g. the {key:lower, val:true} mirror yields RIGHT(LOWER(doc.x), …) == LOWER(@v), a case-insensitive ends-with).

RIGHT(doc.name, CHAR_LENGTH(@value)) == @value
Parameters
$init : array<string|int, mixed> = []

The filter init (op = ew).

$binds : array<string|int, mixed>|null = null

The bind variables, populated by reference.

$doc : string = AQL::DOC

The document reference.

Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterGeo()

Prepares the filter clause for a geospatial attribute.

protected prepareFilterGeo([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $doc = AQL::DOC ]) : string
Parameters
$init : array<string|int, mixed> = []
$binds : array<string|int, mixed>|null = null
$doc : string = AQL::DOC
Tags
throws
BindException
Return values
string

prepareFilterKey()

Prepares the filter clause with a specific key and document, with optional function transformations via 'alt' parameter.

protected prepareFilterKey([string|array<string|int, mixed>|null $init = [] ][, string $docRef = AQL::DOC ]) : string

Supports function chaining:

  • Single function: "alt":"lower"
  • Multiple functions: "alt":["trim","lower"]
  • Functions with params: "alt":[["trim",1],"lower"]
Parameters
$init : string|array<string|int, mixed>|null = []

Filter initialization array

$docRef : string = AQL::DOC

Document reference (default: AQL::DOC)

Tags
throws
UnsupportedOperationException
ValidationException
example
// Simple key
prepareFilterKey(['key' => 'name'], 'doc')
// Returns: "doc.name"

// With single function
prepareFilterKey(['key' => 'name', 'alt' => 'lower'], 'doc')
// Returns: "LOWER(doc.name)"

// With function chain
prepareFilterKey(['key' => 'name', 'alt' => ['trim', 'lower']], 'doc')
// Returns: "LOWER(TRIM(doc.name))"

// With parameters
prepareFilterKey(['key' => 'code', 'alt' => [['substring', 0, 3]]], 'doc')
// Returns: "SUBSTRING(doc.code, 0, 3)"
Return values
string

The transformed key expression

prepareFilterNumber()

Prepares the filter clause with a string attribute.

protected prepareFilterNumber([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $doc = AQL::DOC ]) : string
Parameters
$init : array<string|int, mixed> = []
$binds : array<string|int, mixed>|null = null
$doc : string = AQL::DOC
Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterQuantified()

Builds a quantified comparison on a scalar array via the `quant` key: how many elements satisfy the comparison.

protected prepareFilterQuantified(array<string|int, mixed> $init[, array<string|int, mixed>|null &$binds = null ][, string $docRef = AQL::DOC ]) : string

The comparator stays in op (a plain FilterComparator code such as ge); the element-axis quantifier comes from quant and is resolved by resolveQuantifier() into ANY / ALL / NONE / AT LEAST (n). This is the unified, recommended form; the legacy op:"all.ge" and op:["atLeast.ge", n] notations remain valid aliases.

doc.scores ALL >= @value
doc.scores AT LEAST (2) >= @value
Parameters
$init : array<string|int, mixed>

The filter init (op = comparator code, quant = quantifier).

$binds : array<string|int, mixed>|null = null

The bind variables, populated by reference.

$docRef : string = AQL::DOC

The document reference.

Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterString()

Prepares the filter clause with a string attribute.

protected prepareFilterString([array<string|int, mixed> $init = [] ][, array<string|int, mixed>|null &$binds = null ][, string $doc = AQL::DOC ]) : string
Parameters
$init : array<string|int, mixed> = []
$binds : array<string|int, mixed>|null = null
$doc : string = AQL::DOC
Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareFilterValue()

Prepare the filter clause with a specific value to evaluates.

protected prepareFilterValue([array<string|int, mixed>|null $init = [] ][, array<string|int, mixed>|null &$binds = null ]) : string

Binds the raw value, then applies the value-side (right) alt chain when one is set (object form alt:{ key:.. , val:.. } or val:true mirror):

  • scalar value → the chain wraps the bind placeholder, e.g. LOWER(@value).
  • array value (e.g. op:in) → the chain is mapped over each element via an inline projection, e.g. @value[* RETURN LOWER(CURRENT)]. The single bind still holds the whole array, so existing binding behavior is preserved.
Parameters
$init : array<string|int, mixed>|null = []
$binds : array<string|int, mixed>|null = null
Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string

prepareHierarchicalFilter()

Prepare hierarchical filter from declarative configuration

protected prepareHierarchicalFilter(array<string|int, mixed> $init, array<string|int, mixed> &$binds[, string $docRef = AQL::DOC ]) : string|null
Parameters
$init : array<string|int, mixed>
$binds : array<string|int, mixed>
$docRef : string = AQL::DOC
Tags
throws
BindException
ConstantException
ContainerExceptionInterface
DependencyException
NotFoundException
NotFoundExceptionInterface
ReflectionException
UnsupportedOperationException
ValidationException
Return values
string|null

buildArrayTraversal()

Build array expansion traversal.

private buildArrayTraversal(array<string|int, mixed> $remainingSegments, FilterPath $segmentInfo, array<string|int, mixed> $init, array<string|int, mixed> &$binds, string $docRef) : string|null
Parameters
$remainingSegments : array<string|int, mixed>
$segmentInfo : FilterPath
$init : array<string|int, mixed>
$binds : array<string|int, mixed>
$docRef : string
Tags
throws
BindException
UnsupportedOperationException
ValidationException
Return values
string|null

buildDocumentTraversal()

Build document traversal (nested object)

private buildDocumentTraversal(array<string|int, mixed> $remainingSegments, FilterPath $segmentInfo, array<string|int, mixed> $init, array<string|int, mixed> &$binds, string $docRef) : string|null
Parameters
$remainingSegments : array<string|int, mixed>
$segmentInfo : FilterPath
$init : array<string|int, mixed>
$binds : array<string|int, mixed>
$docRef : string
Tags
throws
BindException
ConstantException
ContainerExceptionInterface
DependencyException
NotFoundException
NotFoundExceptionInterface
ReflectionException
UnsupportedOperationException
ValidationException
Return values
string|null

buildEdgeTraversal()

Build edge traversal

private buildEdgeTraversal(array<string|int, mixed> $remainingSegments, FilterPath $segmentInfo, array<string|int, mixed> $init, array<string|int, mixed> &$binds, string $docRef[, array<string|int, mixed> $availableEdges = [] ]) : string|null
Parameters
$remainingSegments : array<string|int, mixed>

The remaining path segments to process.

$segmentInfo : FilterPath

The current segment information with nested relations.

$init : array<string|int, mixed>

The original filter parameters.

$binds : array<string|int, mixed>

The bind variables array.

$docRef : string

The current document reference.

$availableEdges : array<string|int, mixed> = []
Tags
throws
BindException
ConstantException
ContainerExceptionInterface
DependencyException
NotFoundException
NotFoundExceptionInterface
ReflectionException

If edge configuration is invalid or not found.

UnsupportedOperationException
ValidationException
Return values
string|null

The AQL condition for edge traversal, or null on failure.

buildFilterPathsRecursive()

Recursively build filter paths documentation

private buildFilterPathsRecursive(string $key, mixed $config, array<string|int, mixed> $parentPath, array<string|int, mixed> &$paths, bool $includeTypes, bool $includeRelations) : void
Parameters
$key : string

Current segment key

$config : mixed

Current segment configuration

$parentPath : array<string|int, mixed>

Accumulated parent path

$paths : array<string|int, mixed>

Reference to paths accumulator

$includeTypes : bool

Include type information

$includeRelations : bool

Include relation references

buildFilterRecursive()

Build filter condition recursively through path segments.

private buildFilterRecursive(array<string|int, mixed> $segments, array<string|int, mixed> $filters, array<string|int, mixed> $init, array<string|int, mixed> &$binds, string $docRef[, array<string|int, mixed> $parentPath = [] ][, array<string|int, mixed> $currentEdges = [] ][, array<string|int, mixed> $currentJoins = [] ]) : string|null
Parameters
$segments : array<string|int, mixed>

Remaining segments to process.

$filters : array<string|int, mixed>

Current level filter configuration.

$init : array<string|int, mixed>

Original filter parameters.

$binds : array<string|int, mixed>

Bind variables array.

$docRef : string

Current document reference.

$parentPath : array<string|int, mixed> = []

Accumulated path from parent segments.

$currentEdges : array<string|int, mixed> = []

The current edges definitions.

$currentJoins : array<string|int, mixed> = []

The current joins definitions.

Tags
throws
BindException
ConstantException
ContainerExceptionInterface
DependencyException
NotFoundException
NotFoundExceptionInterface
ReflectionException
UnsupportedOperationException
ValidationException
Return values
string|null

buildJoinTraversal()

Build join traversal

private buildJoinTraversal(array<string|int, mixed> $remainingSegments, FilterPath $segmentInfo, array<string|int, mixed> $init, array<string|int, mixed> &$binds, string $docRef[, array<string|int, mixed> $availableJoins = [] ]) : string|null
Parameters
$remainingSegments : array<string|int, mixed>

The remaining path segments to process.

$segmentInfo : FilterPath

The current segment information with nested relations.

$init : array<string|int, mixed>

The original filter parameters.

$binds : array<string|int, mixed>

The bind variables array.

$docRef : string

The current document reference.

$availableJoins : array<string|int, mixed> = []
Tags
throws
BindException
ConstantException
ContainerExceptionInterface
DependencyException
NotFoundException
NotFoundExceptionInterface
ReflectionException
UnsupportedOperationException
ValidationException
Return values
string|null

The AQL condition for join traversal, or null on failure.

buildLeafCondition()

Build leaf condition by delegating to existing filter logic

private buildLeafCondition(FilterPath $segmentInfo, array<string|int, mixed> $init, array<string|int, mixed> &$binds, string $docRef) : string|null
Parameters
$segmentInfo : FilterPath

The segment information with type and path.

$init : array<string|int, mixed>

The original filter parameters.

$binds : array<string|int, mixed>

The bind variables array.

$docRef : string

The current document reference.

Return values
string|null

The AQL condition string, or null on failure.

On this page

Search results