Common Expression Language (CEL) API Reference

This document serves as the unified API Doc reference for the Common Expression Language (CEL). It lists all macros, operators, and standard functions, indicating their signatures, behaviors, and support status across the official CEL stacks.

For more details on language behavior and specifications, refer to the CEL Language Definition.

Stack Versions

This reference document is based on the following versions of the CEL stacks:

  • CEL Go: v0.29.2 (and newer)
  • CEL C++: v0.15.0
  • CEL Java: v0.13.1
  • CEL Python: v0.1.3
  • CEL C: Development snapshot (unreleased)

GitHub Mirrors

The official implementations of CEL are mirrored on GitHub under the cel-expr organization:


1. Core Macros

These are built-in macros that are expanded at compile time.

Macro Description Go C++ Java Python C
has(container.field) Tests whether a field is present in a message, or a key in a map.

Signatures:
has(container.field) -> bool

Examples:
has(request.auth.claims.email)
list.all(var, predicate) Tests whether all elements in a list satisfy a predicate.

Signatures:
list.all(var, predicate) -> bool

Examples:
[1, 2, 3].all(x, x > 0) // true
¹
list.exists(var, predicate) Tests whether at least one element in a list satisfies a predicate.

Signatures:
list.exists(var, predicate) -> bool

Examples:
[1, 2, 3].exists(x, x > 2) // true
¹
list.exists_one(var, predicate) Tests whether exactly one element in a list satisfies a predicate.

Signatures:
list.exists_one(var, predicate) -> bool

Examples:
[1, 2, 3].exists_one(x, x == 2) // true
¹
list.filter(var, predicate) Filters elements of a list according to a predicate.

Signatures:
list.filter(var, predicate) -> list

Examples:
[1, 2, 3].filter(x, x > 1) // [2, 3]
¹
list.map(var, transform) Transforms each element of a list using an expression.

Signatures:
list.map(var, transform) -> list

Examples:
[1, 2, 3].map(x, x * 2) // [2, 4, 6]
¹
list.map(var, filter, transform) Transforms elements of a list that satisfy a filter predicate.

Signatures:
list.map(var, filter, transform) -> list

Examples:
[1, 2, 3].map(x, x > 1, x * 2) // [4, 6]
¹

¹ Supported in C runtime because macros are expanded into comprehensions during compilation by the host compiler.


2. Core Operators

Operator Description Go C++ Java Python C
Arithmetic (+, -, *, /, %) Standard arithmetic operations. Negation (-x) and Identity (+x). List concatenation (list + list) is supported in Go, C++, Java, and Python.

Signatures:
T + T -> T
T - T -> T
T * T -> T
T / T -> T
T % T -> T
-T -> T
+T -> T
list + list -> list

Examples:
1 + 2 * 3 // 7
[1] + [2] // [1, 2]
²
Comparison (==, !=, <, <=, >, >=) Standard comparison. Numeric comparisons are heterogeneous (e.g. 1 == 1.0).

Signatures:
T == T -> bool
T != T -> bool
T < T -> bool
T <= T -> bool
T > T -> bool
T >= T -> bool

Examples:
x < 42.0
1 == 1.0 // true
Logical (!, &&, ||, ? :) Logical NOT, AND, OR, and Ternary Conditional. AND/OR use short-circuit evaluation.

Signatures:
!bool -> bool
bool && bool -> bool
bool || bool -> bool
bool ? T : T -> T

Examples:
x > 0 ? "positive" : "non-positive"
Indexing ([]) Access element of a list by index, or lookup key in a map.

Signatures:
list[int] -> T
map[K] -> V

Examples:
tags[0]
users['john']
Membership (in) Check if element is in a list, or key is in a map.

Signatures:
T in list -> bool
K in map -> bool

Examples:
'admin' in roles

² List concatenation (list + list) is not supported in the C runtime, though other arithmetic operators are supported.


3. Core Functions

General & String Functions

Function Description Go C++ Java Python C
size Returns the size of a string (characters), bytes, list, or map.

Signatures:
size(T) -> int (where T is string, bytes, list, or map)<br /><br />**Examples:**<br />size("hello") // 5`
contains Returns whether string contains substring.

Signatures:
string.contains(string) -> bool

Examples:
"hello".contains("ell") // true
startsWith Returns whether string starts with prefix.

Signatures:
string.startsWith(string) -> bool

Examples:
"hello".startsWith("he") // true
endsWith Returns whether string ends with suffix.

Signatures:
string.endsWith(string) -> bool

Examples:
"hello".endsWith("lo") // true
matches Returns whether string matches RE2 regular expression.

Signatures:
string.matches(string) -> bool

Examples:
"123".matches(r"^\d+$") // true

Date and Time Selector Functions

These functions extract components from google.protobuf.Timestamp or google.protobuf.Duration.

Function Description Go C++ Java Python C
getFullYear Returns the 4-digit year.

Signatures:
timestamp.getFullYear([tz]) -> int

Examples:
timestamp("2026-07-23T00:00:00Z").getFullYear() // 2026
getMonth Returns the month (0-11).

Signatures:
timestamp.getMonth([tz]) -> int

Examples:
timestamp("2026-07-23T00:00:00Z").getMonth() // 6
getDayOfMonth Returns the day of the month (1-31).

Signatures:
timestamp.getDayOfMonth([tz]) -> int

Examples:
timestamp("2026-07-23T00:00:00Z").getDayOfMonth() // 23
getDayOfWeek Returns the day of the week (0 = Sunday).

Signatures:
timestamp.getDayOfWeek([tz]) -> int

Examples:
timestamp("2026-07-23T00:00:00Z").getDayOfWeek() // 4
getDayOfYear Returns the day of the year (0-365).

Signatures:
timestamp.getDayOfYear([tz]) -> int

Examples:
timestamp("2026-07-23T00:00:00Z").getDayOfYear() // 203
getHours Returns the hours (0-23).

Signatures:
timestamp.getHours([tz]) -> int
duration.getHours() -> int

Examples:
duration("1h30m").getHours() // 1
getMinutes Returns the minutes (0-59).

Signatures:
timestamp.getMinutes([tz]) -> int
duration.getMinutes() -> int

Examples:
duration("1h30m").getMinutes() // 30
getSeconds Returns the seconds (0-59).

Signatures:
timestamp.getSeconds([tz]) -> int
duration.getSeconds() -> int

Examples:
duration("1h30m45s").getSeconds() // 45
getMilliseconds Returns the milliseconds (0-999).

Signatures:
timestamp.getMilliseconds([tz]) -> int
duration.getMilliseconds() -> int

Examples:
duration("1.5s").getMilliseconds() // 500

Type Conversions

Target Type Description Go C++ Java Python C
bool Converts to boolean.

Signatures:
bool(bool) -> bool
bool(string) -> bool

Examples:
bool("true") // true
bytes Converts to bytes.

Signatures:
bytes(bytes) -> bytes
bytes(string) -> bytes

Examples:
bytes("hello") // b"hello"
double Converts to double-precision float.

Signatures:
double(double) -> double
double(int) -> double
double(uint) -> double
double(string) -> double

Examples:
double(1) // 1.0
duration Converts to duration.

Signatures:
duration(duration) -> duration
duration(string) -> duration

Examples:
duration("1.5s") // 1.5s duration
int Converts to 64-bit signed integer.

Signatures:
int(int) -> int
int(uint) -> int
int(double) -> int (rounds to zero)
int(string) -> int
int(timestamp) -> int (seconds since epoch)

Examples:
int(1.5) // 1
string Converts to string.

Signatures:
string(T) -> string (supports bool, int, uint, double, bytes, timestamp, duration)<br /><br />**Examples:**<br />string(1.5) // "1.5"`
timestamp Converts to timestamp.

Signatures:
timestamp(timestamp) -> timestamp
timestamp(string) -> timestamp (RFC3339)

Examples:
timestamp("2026-07-23T00:00:00Z")
uint Converts to 64-bit unsigned integer.

Signatures:
uint(uint) -> uint
uint(int) -> uint
uint(double) -> uint
uint(string) -> uint

Examples:
uint(1) // 1u
dyn Casts value to dynamic type for type-checking.

Signatures:
dyn(T) -> dyn

Examples:
dyn([1, "two"])
type Returns the type of the value.

Signatures:
type(T) -> type

Examples:
type(1) // int

4. Extensions (Libraries)

Bindings Library

Function Description Go C++ Java Python C
cel.bind Binds a local variable to avoid duplicate evaluation.

Signatures:
cel.bind(varName, initExpr, resultExpr) -> T

Examples:
cel.bind(x, a + b, x * x)
(v0.15.0) (v0.10.0) (v0.2.0) (v0.1.1)

How to Enable

Encoders Library

Function Description Go C++ Java Python C
base64.encode Encodes bytes to base64 string.

Signatures:
base64.encode(bytes) -> string

Examples:
base64.encode(b"hello") // "aGVsbG8="
(v0.6.0) (v0.10.0) (v0.2.0) (v0.1.1)
base64.decode Decodes base64 string to bytes. Throws error on invalid input.

Signatures:
base64.decode(string) -> bytes

Examples:
base64.decode("aGVsbG8=") // b"hello"
(v0.6.0) (v0.10.0) (v0.2.0) (v0.1.1)
json.encode Serializes a CEL value to JSON string.

Signatures:
json.encode(dyn) -> string

Examples:
json.encode([1, 2]) // "[1,2]"
(v0.29.0)

How to Enable

Math Library

Function Description Go C++ Java Python C
math.greatest Returns greatest of numeric arguments (or list of numerics).

Signatures:
math.greatest(arg, ...) -> T

Examples:
math.greatest(1, 3, 2) // 3
(v0.13.0) (v0.10.0) (v0.2.0) (v0.1.1)
math.least Returns least of numeric arguments (or list of numerics).

Signatures:
math.least(arg, ...) -> T

Examples:
math.least([1, 3, 2]) // 1
(v0.13.0) (v0.10.0) (v0.2.0) (v0.1.1)
math.abs Absolute value.

Signatures:
math.abs(T) -> T (supports int, uint, double)<br /><br />**Examples:**<br />math.abs(-1) // 1`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.sqrt Square root.

Signatures:
math.sqrt(T) -> double (supports int, uint, double)<br /><br />**Examples:**<br />math.sqrt(9) // 3.0`
(v0.25.1) (v0.12.0) (v0.11.0) (v0.1.1)
math.bitAnd Bitwise AND.

Signatures:
math.bitAnd(T, T) -> T (supports int, uint)<br /><br />**Examples:**<br />math.bitAnd(5, 3) // 1`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.bitOr Bitwise OR.

Signatures:
math.bitOr(T, T) -> T (supports int, uint)<br /><br />**Examples:**<br />math.bitOr(5, 3) // 7`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.bitXor Bitwise XOR.

Signatures:
math.bitXor(T, T) -> T (supports int, uint)<br /><br />**Examples:**<br />math.bitXor(5, 3) // 6`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.bitNot Bitwise NOT.

Signatures:
math.bitNot(T) -> T (supports int, uint)<br /><br />**Examples:**<br />math.bitNot(1) // -2`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.bitShiftLeft Bitwise shift left.

Signatures:
math.bitShiftLeft(T, int) -> T (supports int, uint)<br /><br />**Examples:**<br />math.bitShiftLeft(1, 2) // 4`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.bitShiftRight Bitwise shift right.

Signatures:
math.bitShiftRight(T, int) -> T (supports int, uint)<br /><br />**Examples:**<br />math.bitShiftRight(4, 2) // 1`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.ceil Ceiling rounding.

Signatures:
math.ceil(double) -> double

Examples:
math.ceil(1.2) // 2.0
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.floor Floor rounding.

Signatures:
math.floor(double) -> double

Examples:
math.floor(1.8) // 1.0
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.round Nearest integer rounding.

Signatures:
math.round(double) -> double

Examples:
math.round(1.5) // 2.0
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.trunc Truncation rounding (towards zero).

Signatures:
math.trunc(double) -> double

Examples:
math.trunc(-1.8) // -1.0
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.isInf Checks if double is positive or negative infinity.

Signatures:
math.isInf(double) -> bool

Examples:
math.isInf(1.0/0.0) // true
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.isNaN Checks if double is NaN.

Signatures:
math.isNaN(double) -> bool

Examples:
math.isNaN(0.0/0.0) // true
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.isFinite Checks if double is finite.

Signatures:
math.isFinite(double) -> bool

Examples:
math.isFinite(1.2) // true
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)
math.sign Returns sign of value (-1, 0, or 1).

Signatures:
math.sign(T) -> T (supports int, uint, double)<br /><br />**Examples:**<br />math.sign(-42) // -1`
(v0.21.0) (v0.11.0) (v0.10.1) (v0.1.1)

How to Enable

Protos Library

Function Description Go C++ Java Python C
proto.getExt Gets proto2 extension field, or default if unset.

Signatures:
proto.getExt(msg, extName) -> T

Examples:
proto.getExt(msg, google.api.expr.test.int32_ext)
(v0.13.0) (v0.10.0) (v0.2.0) (v0.1.1)
proto.hasExt Checks if proto2 extension field is set.

Signatures:
proto.hasExt(msg, extName) -> bool

Examples:
proto.hasExt(msg, google.api.expr.test.int32_ext)
(v0.13.0) (v0.10.0) (v0.2.0) (v0.1.1)

How to Enable

Lists Library

Function Description Go C++ Java Python C
distinct Returns distinct elements.

Signatures:
list.distinct() -> list

Examples:
[1, 2, 2].distinct() // [1, 2]
(v0.22.0) (v0.11.0) (v0.11.0) (v0.1.1)
flatten Flattens nested lists.

Signatures:
list.flatten([depth]) -> list

Examples:
[[1], [2, 3]].flatten() // [1, 2, 3]
(v0.22.0) (v0.11.0) (v0.7.1) (v0.1.1)
lists.range Returns list of integers [0, ..., n-1].

Signatures:
lists.range(int) -> list(int)

Examples:
lists.range(3) // [0, 1, 2]
(v0.22.0) (v0.11.0) (v0.10.1) (v0.1.1)
reverse Reverses the list.

Signatures:
list.reverse() -> list

Examples:
[1, 2].reverse() // [2, 1]
(v0.22.0) (v0.11.0) (v0.11.0) (v0.1.1)
slice Returns sub-list (start inclusive, end exclusive).

Signatures:
list.slice(start, end) -> list

Examples:
[1, 2, 3].slice(1, 3) // [2, 3]
(v0.17.0) (v0.11.0) (v0.11.0) (v0.1.1)
sort Sorts list of comparable elements.

Signatures:
list.sort() -> list

Examples:
[3, 1, 2].sort() // [1, 2, 3]
(v0.22.0) (v0.11.0) (v0.11.0) (v0.1.1)
sortBy Sorts list by key evaluated from expression.

Signatures:
list.sortBy(var, expr) -> list

Examples:
[{"val": 2}, {"val": 1}].sortBy(x, x.val) // [{"val": 1}, {"val": 2}]
(v0.22.0) (v0.11.0) (v0.11.0) (v0.1.1)
first Returns first element as optional. Requires the Optional extension.

Signatures:
list.first() -> optional

Examples:
[1, 2].first() // optional(1)
(v0.23.0) (v0.15.0) (v0.11.0) (v0.1.2)
last Returns last element as optional. Requires the Optional extension.

Signatures:
list.last() -> optional

Examples:
[1, 2].last() // optional(2)
(v0.23.0) (v0.15.0) (v0.11.0) (v0.1.2)

How to Enable

Sets Library

Function Description Go C++ Java Python C
sets.contains Checks if list1 contains all elements of list2.

Signatures:
sets.contains(list1, list2) -> bool

Examples:
sets.contains([1, 2], [1]) // true
(v0.15.0) (v0.10.0) (v0.6.0) (v0.1.1)
sets.equivalent Checks if lists are set-equivalent (contain same unique elements).

Signatures:
sets.equivalent(list1, list2) -> bool

Examples:
sets.equivalent([1, 2], [2, 1, 1]) // true
(v0.15.0) (v0.10.0) (v0.6.0) (v0.1.1)
sets.intersects Checks if lists share at least one element.

Signatures:
sets.intersects(list1, list2) -> bool

Examples:
sets.intersects([1, 2], [2, 3]) // true
(v0.15.0) (v0.10.0) (v0.6.0) (v0.1.1)

How to Enable

Strings Library

Function Description Go C++ Java Python C
charAt Returns character at index.

Signatures:
string.charAt(int) -> string

Examples:
"hello".charAt(1) // "e"
(v0.4.0) (v0.10.0) (v0.2.0) (v0.1.1)
indexOf Returns index of first occurrence of substring, or -1.

Signatures:
string.indexOf(substr, [start]) -> int

Examples:
"hello".indexOf("l") // 2
(v0.4.0) (v0.10.0) (v0.2.0) (v0.1.1)
lastIndexOf Returns index of last occurrence of substring, or -1.

Signatures:
string.lastIndexOf(substr, [end]) -> int

Examples:
"hello".lastIndexOf("l") // 3
(v0.4.0) (v0.10.0) (v0.2.0) (v0.1.1)
join Concatenates strings.

Signatures:
list(string).join([separator]) -> string

Examples:
["a", "b"].join("-") // "a-b"
(v0.10.0) (v0.10.0) (v0.2.0) (v0.1.1)
split Splits string by separator.

Signatures:
string.split(separator, [limit]) -> list(string)

Examples:
"a-b".split("-") // ["a", "b"]
(v0.4.0) (v0.10.0) (v0.2.0) (v0.1.1)
substring Returns substring (start inclusive, end exclusive).

Signatures:
string.substring(start, [end]) -> string

Examples:
"hello".substring(1, 3) // "el"
(v0.4.0) (v0.10.0) (v0.2.0) (v0.1.1)
trim Trims Unicode whitespace.

Signatures:
string.trim() -> string

Examples:
" hello ".trim() // "hello"
(v0.4.0) (v0.10.0) (v0.2.0) (v0.1.1)
replace Replaces occurrences of old with new.

Signatures:
string.replace(old, new, [limit]) -> string

Examples:
"hello".replace("l", "w") // "hewwo"
(v0.4.0) (v0.10.0) (v0.2.0) (v0.1.1)
reverse Reverses Unicode code points.

Signatures:
string.reverse() -> string

Examples:
"abc".reverse() // "cba"
(v0.18.0) (v0.14.0) (v0.13.0) (v0.1.1)
lowerAscii Converts ASCII characters to lowercase.

Signatures:
string.lowerAscii() -> string

Examples:
"Hello".lowerAscii() // "hello"
(v0.6.0) (v0.11.0) (v0.2.0) (v0.1.1)
upperAscii Converts ASCII characters to uppercase.

Signatures:
string.upperAscii() -> string

Examples:
"Hello".upperAscii() // "HELLO"
(v0.6.0) (v0.11.0) (v0.2.0) (v0.1.1)
quote Escapes string for safe printing.

Signatures:
strings.quote(string) -> string

Examples:
strings.quote("a\tb") // "\"a\\tb\""
(v0.14.0) (v0.14.0) (v0.13.0) (v0.1.1)

How to Enable

Regular Expression Library

Function Description Go C++ Java Python C
regex.replace Replaces matches with replacement string (supports backreferences).

Signatures:
regex.replace(target, pat, repl, [limit]) -> string

Examples:
regex.replace("123-456", r"(\d+)-(\d+)", r"\2-\1") // "456-123"
(v0.25.1) (v0.13.0) (v0.10.1) (v0.1.1)
regex.extract Returns first match of pattern (must have one capture group).

Signatures:
regex.extract(target, pat) -> optional(string)

Examples:
regex.extract("a123b", r"(\d+)") // optional("123")
(v0.25.1) (v0.13.0) (v0.10.1) (v0.1.1)
regex.extractAll Returns all matches of pattern (must have one capture group).

Signatures:
regex.extractAll(target, pat) -> list(string)

Examples:
regex.extractAll("a1b2", r"(\d+)") // ["1", "2"]
(v0.25.1) (v0.13.0) (v0.10.1) (v0.1.1)

How to Enable

Two-Variable Comprehensions

Macro Description Go C++ Java Python C
all Short-circuiting logical AND over key/index and value.

Signatures:
list.all(i, v, pred) -> bool
map.all(k, v, pred) -> bool

Examples:
[1, 2].all(i, v, v > 0) // true
(v0.22.0) (v0.14.0) (v0.11.0) (v0.1.1)
exists Short-circuiting logical OR over key/index and value.

Signatures:
list.exists(i, v, pred) -> bool
map.exists(k, v, pred) -> bool

Examples:
[1, 2].exists(i, v, v == 2) // true
(v0.22.0) (v0.14.0) (v0.11.0) (v0.1.1)
existsOne Checks if exactly one pair satisfies predicate.

Signatures:
list.existsOne(i, v, pred) -> bool
map.existsOne(k, v, pred) -> bool

Examples:
[1, 2].existsOne(i, v, v == 2) // true
(v0.22.0) (v0.14.0) (v0.11.0) (v0.1.1)
transformList Transforms/filters list/map into a list.

Signatures:
list.transformList(i, v, [filter], transform) -> list
map.transformList(k, v, [filter], transform) -> list

Examples:
[1, 2].transformList(i, v, v * 2) // [2, 4]
(v0.22.0) (v0.14.0) (v0.11.0) (v0.1.1)
transformMap Transforms values of list/map into a map (keys remain fixed).

Signatures:
list.transformMap(i, v, [filter], transform) -> map
map.transformMap(k, v, [filter], transform) -> map

Examples:
[1, 2].transformMap(i, v, v * 2) // {0: 2, 1: 4}
(v0.22.0) (v0.14.0) (v0.11.0) (v0.1.1)
transformMapEntry Transforms into a map.

Signatures:
list.transformMapEntry(i, v, [filter], transform_entry) -> map
map.transformMapEntry(k, v, [filter], transform_entry) -> map

Examples:
[1, 2].transformMapEntry(i, v, {string(v): v * 2}) // {"1": 2, "2": 4}
(v0.22.0) (v0.14.0) (v0.11.0) (v0.1.1)

How to Enable

Native Types Library

Feature Description Go C++ Java Python C
Native Structs Registering and instantiating host native types (Go structs / Java POJOs) in CEL.

Examples:
Account{id: 123} (Java POJO instanced in CEL)
(v0.13.0) (v0.13.0)

How to Enable

Network Library

The Network library provides functions for parsing, validating, and manipulating IP addresses and CIDR blocks.

Function Description Go C++ Java Python C
ip Parses a string into an IP address, or extracts the IP from a CIDR.

Signatures:
ip(string) -> IP
CIDR.ip() -> IP

Examples:
ip("192.168.0.1")
cidr("192.168.0.0/24").ip()
(v0.29.0)
isIP Checks if a string is a valid IP address.

Signatures:
isIP(string) -> bool

Examples:
isIP("192.168.0.1") // true
(v0.29.0)
ip.isCanonical Checks if an IP address string is in its canonical format.

Signatures:
ip.isCanonical(string) -> bool

Examples:
ip.isCanonical("192.168.0.1") // true
(v0.29.0)
cidr Parses a string into a CIDR block.

Signatures:
cidr(string) -> CIDR

Examples:
cidr("192.168.0.0/24")
(v0.29.0)
isCIDR Checks if a string is a valid CIDR block.

Signatures:
isCIDR(string) -> bool

Examples:
isCIDR("192.168.0.0/24") // true
(v0.29.0)
containsIP Checks if a CIDR block contains an IP address.

Signatures:
CIDR.containsIP(IP) -> bool
CIDR.containsIP(string) -> bool

Examples:
cidr("192.168.0.0/24").containsIP(ip("192.168.0.1")) // true
(v0.29.0)
containsCIDR Checks if a CIDR block contains another CIDR block.

Signatures:
CIDR.containsCIDR(CIDR) -> bool
CIDR.containsCIDR(string) -> bool

Examples:
cidr("192.168.0.0/16").containsCIDR(cidr("192.168.1.0/24")) // true
(v0.29.0)
family Returns the IP family (4 for IPv4, 6 for IPv6).

Signatures:
IP.family() -> int

Examples:
ip("192.168.0.1").family() // 4
(v0.29.0)
isGlobalUnicast Checks if the IP is a global unicast address.

Signatures:
IP.isGlobalUnicast() -> bool

Examples:
ip("192.168.0.1").isGlobalUnicast() // true
(v0.29.0)
isLinkLocalMulticast Checks if the IP is a link-local multicast address.

Signatures:
IP.isLinkLocalMulticast() -> bool

Examples:
ip("224.0.0.1").isLinkLocalMulticast() // true
(v0.29.0)
isLinkLocalUnicast Checks if the IP is a link-local unicast address.

Signatures:
IP.isLinkLocalUnicast() -> bool

Examples:
ip("169.254.0.1").isLinkLocalUnicast() // true
(v0.29.0)
isLoopback Checks if the IP is a loopback address.

Signatures:
IP.isLoopback() -> bool

Examples:
ip("127.0.0.1").isLoopback() // true
(v0.29.0)
isMask Checks if the CIDR is a valid subnet mask.

Signatures:
CIDR.isMask() -> bool

Examples:
cidr("255.255.255.0/24").isMask() // true
(v0.29.0)
isUnspecified Checks if the IP is an unspecified address (e.g. 0.0.0.0).

Signatures:
IP.isUnspecified() -> bool

Examples:
ip("0.0.0.0").isUnspecified() // true
(v0.29.0)
masked Returns the masked CIDR block.

Signatures:
CIDR.masked() -> CIDR

Examples:
cidr("192.168.0.1/24").masked() // 192.168.0.0/24
(v0.29.0)
prefixLength Returns the prefix length of the CIDR block.

Signatures:
CIDR.prefixLength() -> int

Examples:
cidr("192.168.0.0/24").prefixLength() // 24
(v0.29.0)
string Converts IP or CIDR to string.

Signatures:
string(IP) -> string
string(CIDR) -> string

Examples:
string(ip("192.168.0.1")) // "192.168.0.1"
(v0.29.0)

How to Enable

  • Go: Pass ext.Network() to cel.NewEnv().
  • C++: Not supported.
  • Java: Not supported.
  • Python: Not supported.

5. Advanced Features

Advanced Features Summary

Feature Description Go C++ Java Python C
Partial Evaluation Evaluate with missing inputs; returns unknowns or a simplified expression. ³
Async Evaluation Non-blocking concurrent execution of extension functions.
AST Validators Static analysis checks on the Checked AST after type-checking.
AST Optimizers AST rewrites (constant folding, inlining, CSE) to improve performance.
CEL Policy Compiler Compiles YAML-based policy structures into standard CEL ASTs.

³ Go supports generating a Residual AST (pruned AST). ⁴ C++ and Java support returning UnknownSet / CelUnknownSet at runtime, but do not expose public APIs for residual AST generation. ⁵ Go uses AsyncBinding / AsyncOp returning channels. ⁶ Java uses CelAsyncRuntime returning ListenableFuture.

Partial Evaluation (Unknowns)

Partial evaluation allows evaluating an expression when only a subset of the input variables (arguments) are known. Instead of failing, the evaluation produces a result that indicates what is missing, or a simplified expression.

  • Go: Full support. Allows defining a PartialActivation with patterns of unknown attributes. Evaluation returns a types.Unknown value. Go supports generating a Residual AST (Env.ResidualAst) which is a pruned, simplified AST containing only the parts of the expression that could not be evaluated.
  • C++: Supports Unknown values. Unknown attribute patterns are configured via Activation::set_unknown_attribute_patterns. Evaluation returns an UnknownSet. Public API does not currently expose residual AST generation.
  • Java: Supports partial evaluation via PartialVars passed to Program.eval(). Evaluation returns a CelUnknownSet. Public API does not currently expose residual AST generation.
  • Python / C: No native support.

Async Evaluation

Async evaluation allows CEL expressions to call functions that execute asynchronously (e.g., making RPCs or database queries) and block evaluation until the results are available, without blocking the main execution thread.

  • Go: Supports asynchronous function overloads via AsyncBinding and AsyncOp. Async functions return a Go channel (<-chan ref.Val), and the interpreter manages the concurrent execution and synchronization.
  • Java: Supports async evaluation via CelAsyncRuntime and AsyncProgram. It uses ListenableFuture to represent pending values and automatically drives evaluation to completion as futures resolve.
  • C++ / Python / C: No built-in support.

AST Validators

Validators perform static analysis on the Checked AST after type-checking to enforce domain-specific constraints before the program is executed.

  • Go: Supports ASTValidator interface. Canonical validators include cel.validator.duration, cel.validator.timestamp, cel.validator.matches (regex), cel.validator.homogeneous_literals, and cel.validator.comprehension_nesting_limit.
  • C++: Supports cel::Validator. Canonical validations include AstDepthValidator, ComprehensionNestingLimitValidator, DurationLiteralValidator, HomogeneousLiteralValidator, MatchesValidator, and TimestampLiteralValidator.
  • Java: Supports CelValidator and CelAstValidator. Canonical validators include AstDepthLimitValidator, ComprehensionNestingLimitValidator, DurationLiteralValidator, HomogeneousLiteralValidator, RegexLiteralValidator, and TimestampLiteralValidator.
  • Python / C: No direct support.

AST Optimizers

Optimizers rewrite the AST to improve execution performance. Optimizers fall into one of two categories: static and runtime optimizers. C++, Java, and Go support runtime optimization. CEL Java and Go also support static optimizers. Typical optimizations include constant folding (pre-evaluating sub-expressions with constant inputs) and common subexpression elimination (CSE).

  • Go: Supports AST folding during compilation/planning.
  • C++: Supports constant folding via the cel::extensions::EnableConstantFolding extension at plan time.
  • Java: Supports CelOptimizer interface. Canonical optimizers include ConstantFoldingOptimizer (which can fold short-circuiting branches by simulating partial evaluation), InliningOptimizer, and SubexpressionOptimizer (CSE).
  • Python / C: No direct support.

CEL Policy Compiler

CEL Policy is a YAML-based format for composing multiple CEL expressions together with variables, match blocks, conditional outputs, and nested rules. It is designed for complex policy engines (like Kubernetes Admission Control) where single CEL expressions would become unreadable.

The Policy Compiler compiles these YAML policies into a single standard CEL AST, meaning they are fully compatible with standard CEL runtimes and inherit all performance and safety guarantees.

  • Go: Supported via third_party/cel/go/policy.
  • C++: Supported via third_party/cel/cpp/policy.
  • Java: Supported via third_party/java/cel/policy.
  • Python / C: Not directly supported.