Skip to content

Expressions - Go

For the complete documentation index see: llms.txt

All documentation pages available in markdown.

Jump to the Code block for a combined complete example.

This page describes how to use expressions in single record commands.

Aerospike expressions are a strongly typed, functional, domain-specific language for manipulating and comparing bins and record metadata.

AEL text authoring

Starting with Aerospike Database 8.2.0, the server accepts Aerospike Expression Language (AEL) text on the wire. Instead of sending a compiled expression tree from the client, you can pass a readable string such as "$.status == 'active' and $.age >= 21". The database parses that string and evaluates it with the same expression engine used for filter, read, and write operations.

The Developer SDK (Java and Python) is designed for this text-first workflow. You can attach AEL strings to fluent builders—for example .where(...) for filters and operation-expression builders such as selectFrom and upsertFrom for server-side compute.

This page documents builder authoring for the classic client using Exp.* and related APIs. Those APIs remain the supported path for the classic clients. They compile expressions on the client and send the wire format those clients have always used.

If you use Java or Python and want readable filter and operation-expression strings, see the AEL overview. For other languages, use the Exp.* builder APIs documented on this page. For canonical grammar (paths, operators, let, when, and CDT selectors), see AEL reference.

For expression usage within multi-record requests, see Batch operations and Queries.

Setup

The examples on this page use the following setup and record structure to illustrate the use of expressions in single record commands.

Setup and record structure examples
import (
"fmt"
"log"
"github.com/aerospike/aerospike-client-go/v8"
)
// Establishes a connection to the server
client, err := aerospike.NewClient("127.0.0.1", 3000)
if err != nil {
log.Fatal(err)
}
defer client.Close()
// Creates a key with the namespace "sandbox", set "ufodata", and user key 5001
key, err := aerospike.NewKey("sandbox", "ufodata", 5001)
if err != nil {
log.Fatal(err)
}

The record structure:

+------+----------+----------+----------+------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+------------------------------------------------------------+
| PK | occurred | reported | posted | report | location |
+------+----------+----------+----------+------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+------------------------------------------------------------+
| 5001 | 20220531 | 20220601 | 20220601 | MAP('{"shape":["circle", "flash", "disc"], "summary":"Large flying disc flashed in the sky above the student union. Craziest thing I've ever seen!", "city":"Ann Arbor", "state":"Michigan", "duration":"5 minutes"}') | GeoJSON('{"type":"Point","coordinates":[42.2808,83.743]}') |
+------+----------+----------+----------+------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+------------------------------------------------------------+

AEL text in Go

Go client 8.9.0 and later can send AEL source text to Aerospike Database 8.2.0 and later with ExpFromAEL. The server compiles the text and rejects invalid AEL with PARAMETER_ERROR, reporting the line and column of the first error. The result is a complete filter expression. Assign it directly to a policy’s FilterExpression, and don’t nest it inside ExpAnd, ExpOr, ExpNot, or other expressions. The Developer SDK provides fluent AEL builders for Java and Python.

import (
"log"
"github.com/aerospike/aerospike-client-go/v8"
)
exp, err := aerospike.ExpFromAEL("$.status == 'active'")
if err != nil {
log.Fatal(err)
}
policy := aerospike.NewPolicy()
policy.FilterExpression = exp

See the AEL reference for grammar and path syntax.

Filter expressions

Record filtering expressions select records that satisfy a boolean expression and work with all single record commands (reads, writes, operations, and record UDFs), batch reads, and queries. Filters are only executed when a record exists. Filters are not executed when a record is created or is not found.

Read

When using a filter expression on a read command, the expression is defined within the read policy.

The following example creates a filter expression that checks the length of the shape list in the report map and only returns if there are more than two shapes.

// Create the policy
policy := aerospike.NewPolicy()
// Build the expression
policy.FilterExpression = aerospike.ExpGreater(
aerospike.ExpListSize(
aerospike.ExpMapGetByKey(aerospike.MapReturnType.VALUE, aerospike.ExpTypeLIST, aerospike.ExpStringVal("shape"), aerospike.ExpMapBin("report"))),
aerospike.ExpIntVal(2))
// Read the record
record, err := client.Get(policy, key)
if err != nil {
log.Fatal(err)
}
// Do something
fmt.Printf("Record: %v", record.Bins)

Write

When using a filter expression on a write command, the expression is defined within the write policy.

The following example creates a filter expression that checks if occurred is later than 20211231 and posted exists. If the filter returns true, a recent key with the value true will be added to the report map.

// Create the policy
writePolicy := aerospike.NewWritePolicy(0,0)
// Build the expression
writePolicy.FilterExpression = aerospike.ExpAnd(
aerospike.ExpGreater(aerospike.ExpIntBin("occurred"), aerospike.ExpIntVal(20211231)),
aerospike.ExpBinExists("posted"))
// Update the record
_, err = client.Operate(writePolicy, key, aerospike.MapPutOp(aerospike.DefaultMapPolicy(), "report", aerospike.NewValue("recent"), aerospike.NewValue(true)))
if err != nil {
log.Fatal(err)
}

Operation expressions

Operation expressions are bin operations that atomically compute a value using information in the record or from data supplied by the expression itself.

The result is either returned to the client, in a read expression, or written to a specified bin, in a write expression.

You can define a filter expression in the write policy of the operate method to determine the execution of a bin operation using an operation expression.

Read

The read expression operation computes an expression, and returns that value. A defined name in the operation can be used as the computed bin name when retrieving results.

The following example takes the Read filter expression example from above and changes the scenario slightly. This command computes the length of the shape list in the report map and returns the value in a computed bin called numShapes.

// Build the expression
exp := aerospike.ExpListSize(
aerospike.ExpMapGetByKey(aerospike.MapReturnType.VALUE, aerospike.ExpTypeLIST, aerospike.ExpStringVal("shape"), aerospike.ExpMapBin("report")))
// Read the record
record, err := client.Operate(nil, key, aerospike.ExpReadOp("numShapes", exp, aerospike.ExpReadFlagDefault))
if err != nil {
log.Fatal(err)
}
// Do something
fmt.Printf("Record: %v", record.Bins)

Write

The write expression operation computes an expression and writes that value to a bin.

The following example takes the Write filter expression example from above and changes the scenario slightly. Using the same criteria to compute a recent value, reported bin value and posted bin exists, this command updates the report map with the recent value, true or false.

// Build the expression
exp := aerospike.ExpMapPut(aerospike.DefaultMapPolicy(), aerospike.ExpStringVal("recent"),
aerospike.ExpAnd(
aerospike.ExpGreater(aerospike.ExpIntBin("occurred"), aerospike.ExpIntVal(20211231)),
aerospike.ExpBinExists("posted")),
aerospike.ExpMapBin("report"))
// Update the record
_, err = client.Operate(nil, key, aerospike.ExpWriteOp("report", exp, aerospike.ExpWriteFlagDefault))
if err != nil {
log.Fatal(err)
}

Code block

Expand this section for a single code block to create an operation expression
import (
"fmt"
"log"
"github.com/aerospike/aerospike-client-go/v8"
)
func main() {
// Establishes a connection to the server
client, err := aerospike.NewClient("127.0.0.1", 3000)
if err != nil {
log.Fatal(err)
}
defer client.Close()
// Creates a key with the namespace "sandbox", set "ufodata", and user key 5001
key, err := aerospike.NewKey("sandbox", "ufodata", 5001)
if err != nil {
log.Fatal(err)
}
// Build the expression
exp := aerospike.ExpMapPut(aerospike.DefaultMapPolicy(), aerospike.ExpStringVal("recent"),
aerospike.ExpAnd(
aerospike.ExpGreater(aerospike.ExpIntBin("occurred"), aerospike.ExpIntVal(20211231)),
aerospike.ExpBinExists("posted")),
aerospike.ExpMapBin("report"))
// Update the record
_, err = client.Operate(nil, key, aerospike.ExpWriteOp("report", exp, aerospike.ExpWriteFlagDefault))
if err != nil {
log.Fatal(err)
}
}

History of expressions in Aerospike Database

  • Secondary index expressions introduced in Database 8.1.0
  • Operation expressions introduced in Database 5.6.0
  • XDR filter expressions introduced in Database 5.3.0
  • Record filter expressions introduced in Database 5.2.0