Event sets
The event search API endpoint provides you a programmatic way to query the events recorded during a test run. You describe the events you want using “event sets”, send it to the API, and get back the matching events as NDJSON.
The event sets used in the event search request are conceptually the same as those in Querying with event sets but are used slightly differently. This is a reference for constructing event sets for the event search request.
What is an event set
An event set is a query over the events Antithesis recorded during a test run. Event sets are a pipeline of operations separated by a ., applied left to right to the underlying event stream. These operations are called “verbs”.
Let’s look at a simple example of an event set before looking at all available verbs for creating an event set.
Example
Imagine you ran a test run with 5 containers in your system, and you want to get the first two events from a specific conatiner in your system. Here’s how you’d construct the request body to fetch exactly what you want:
{ "query": "matches({container: \"fdb-workload-1\"})", "limit": 2,}The API responds with NDJSON of Event objects:
{"moment":{"input_hash":"4536913169440939055","vtime":"750.6794897380751"},"AtomicMutations":"0 -1 0","BatchPriorityReadVersions":"0 -1 0","BatchPriorityReadVersionsCompleted":"0 -1 0","BlobGranuleLocationRequests":"0 -1 0","BlobGranuleLocationRequestsCompleted":"0 -1 0","BytesRead":"0 -1 0","ClearMutations":"0 -1 0","ClientDescription":"external-7.3.75-2083768936062727749","Cluster":"docker","CommitCompleted":"0 -1 0","CommitStarted":"0 -1 3","CommitVersionNotFoundForSS":"0 -1 0","CommittedMutationBytes":"0 -1 0","CommittedMutations":"0 -1 0","DateTime":"2026-07-02T01:53:41Z","DefaultPriorityReadVersions":"0 -1 3","DefaultPriorityReadVersionsCompleted":"0 -1 0","Elapsed":"6.56977","ExpensiveClearCostEstCount":"0 -1 0","FutureVersions":"0 -1 0","GetAddressesForKeyRequests":"0 -1 0","GetKeyRequests":"0 -1 0","GetMappedRangeRequests":"0 -1 0","GetRangeRequests":"0 -1 0","GetRangeStreamRequests":"0 -1 0","GetValueRequests":"0 -1 0","ID":"088520088d239923","IPT_bytes_out":1023814952,"ImmediatePriorityReadVersions":"0 -1 0","ImmediatePriorityReadVersionsCompleted":"0 -1 0","Internal":"0","KeyServerLocationRequests":"0 -1 0","KeyServerLocationRequestsCompleted":"0 -1 0","KeysRead":"0 -1 0","Latency90":"0","Latency98":"0","LocationCacheEntryCount":"1","LogGroup":"default","LogicalUncachedReads":"0 -1 0","Machine":"10.89.0.6:80","MaxBytesPerCommit":"-1.79769e+308","MaxCommitLatency":"-1.79769e+308","MaxGRVLatency":"-1.79769e+308","MaxLatency":"-1.79769e+308","MaxMutationsPerCommit":"-1.79769e+308","MaxRowReadLatency":"-1.79769e+308","MaybeCommitted":"0 -1 0","MeanBytesPerCommit":"0","MeanCommitLatency":"0","MeanGRVLatency":"0","MeanLatency":"0","MeanMutationsPerCommit":"0","MeanRowReadLatency":"0","MedianBytesPerCommit":"0","MedianCommitLatency":"0","MedianGRVLatency":"0","MedianLatency":"0","MedianMutationsPerCommit":"0","MedianRowReadLatency":"0","MetadataVersionReads":"0 -1 0","NotCommitted":"0 -1 0","NumGrvFullBatches":"0 -1 0","NumGrvTimedOutBatches":"0 -1 3","NumLocalityCacheEntries":"1","OutstandingWatches":"0","PhysicalReadRequests":"0 -1 0","PhysicalReadRequestsCompleted":"0 -1 0","ProcessBehind":"0 -1 0","ReadVersionBatches":"0 -1 3","ReadVersions":"0 -1 3","ReadVersionsCompleted":"0 -1 0","ReadVersionsThrottled":"0 -1 0","ResourceConstrained":"0 -1 0","SetMutations":"0 -1 3","Severity":"10","StatusRequests":"0 -1 8","TenantLookupRequests":"0 -1 0","TenantLookupRequestsCompleted":"0 -1 0","ThreadID":"13587819877422497627","Throttled":"0 -1 0","Time":"1782957221.228375","TooOld":"0 -1 0","Type":"TransactionMetrics","WatchMapSize":"0","WatchRequests":"0 -1 0","source":{"container":"fdb-workload-1","name":"antithesis/pods/fdb-workload-1/trace.10.89.0.6.80.1782956528.pdw76G.0.2.json","pid":85}}{"moment":{"input_hash":"6572773276055372305","vtime":"503.44814017694443"},"ClientDescription":"external-7.1.67-1285091599831140879","DateTime":"2026-07-02T01:49:51Z","ID":"0000000000000000","IPT_bytes_out":182368408,"LogGroup":"default","Machine":"10.89.0.6:139","PeerAddr":"10.89.0.9:4500(fromHostname)","Severity":"10","SuppressedEventCount":"6","ThreadID":"1285091599831140879","Time":"1782956991.856739","Type":"ConnectionTimedOut","source":{"container":"fdb-workload-1","name":"antithesis/pods/fdb-workload-1/trace.10.89.0.6.139.1782956560.xcUgXo.0.1.json","pid":195}}Key points about the response:
- Each event carries a
momentfield that identifies when the event happened within the run. Specifically,vtimeidentifies the time of event. - At most
limitevents are returned.
Verbs
These are all the operations you can request in the API query. All of these operations can be chained together by a . and are evaluated left to right.
matches
Filter events whose fields exactly match the given values.
matches({field_1: "exact value 1", field_2: "exact value 2", ...})contains
Filter events whose fields contain the given substrings.
contains({field_1: "substring 1", field_2: "substring 2", ...})not_matches
Exclude events whose fields exactly match the given values.
not_matches({field_1: "exact value 1", field_2: "exact value 2", ...})excludes
Exclude events whose fields contain the given substrings.
excludes({field_1: "substring 1", field_2: "substring 2", ...})map
Transforms the event fields as per the given expression.
map(row => expr)filter
Filter events where the predicate is truthy.
filter(row => expr)To filter events with vtime after 20:
filter((event) => event.moment.vtime > 20)flatmap
Transform and flatten the result by one level.
flatmap(row => expr)fold
A higher-order function that processes a complex data structure and iteratively computes a set of values to attach to each event.
fold((state, event) => expr, initial_state)narrow
Restrict events to the listed fields (plus a small set of fields that can’t be dropped).
narrow(["field1", "field2"])union
Takes arbitrarily many event sets and performs a logical OR on all of them. This operation will deduplicate events with the same fields and same values.
union(pipeline, pipeline, ...)When you want events from either container A or container B:
union(matches({container: "con-A"}), matches({container: "con-B"}))intersect
Takes arbitrarily many event sets and performs a logical AND on all of them.
intersect(pipeline, pipeline, ...)when you want only the error events from a specific container:
intersect(matches({container: "con-A"}), filter((event) => event.stream == "error"))difference
Takes arbitrarily many event sets and performs a logical XOR on all of them. It’ll remove the events that are common between the supplied events sets.
difference(pipeline, ...)distinct_by_moment
Takes arbitrarily many event sets and performs a union but deduplicates events by only the moment field.
distinct_by_moment(pipeline, ...)with_last
Annotates each event in the caller event set with additional fields. For each event, it’ll look back at it’s own execution history to find the closest event that’s in the named event sets supplied in the arguments. If multiple named event sets are supplied in the arguments, it’ll add a field for each named argument. The added field is last_{name}, where {name} is the label of the event sent supplied in the arguments.
with_last({name: pipeline, ...})with_next
Annotates each event in the event sets supplied in the arguments with additional fields. For each event in the caller event set, it’ll look ahead at the events in the timeline after itself to find the closest event that’s in the named event sets supplied in the arguments. If multiple named event sets are supplied in the arguments, it’ll find the next event in any of the named event sets. The look-ahead can be bounded by passing a timeout in the arguments. If the timeout is set to 10, the fields are set only if there is a match within 10 seconds after the event itself. This operation adds two fields, last_event which is the caller event, and with_next_type which is the label of the named event set it belongs to.
with_next({name: pipeline, ...}, timeout_sec)Event
An event represents anything that happened within the simulation.
Event emitters
The following will emit events:
- stdout/stderr: Standard output of processes inside your containers will emit events
- SDK events: Our SDK assertions communicate with the rest of our system using events. You may also generate custom events using the SDK’s
send_event()method. - SDK capture directory: Files written to a special location will emit events.
- Antithesis environment: Systems like our fault injector, journald, and others will emit events. See their documentation for details.
Event fields
Events have the following fields (optional where noted):
-
event.moment: The moment at which an event happened. -
event.moment.vtime: The time that passed within the simulation along this timeline, measured in seconds. -
event.source: The source that emitted an event. -
event.source.name: The human-readable name of the system or process that emitted the event.- For
stdout/stderrand SDK assertion events it is your container name. - For the SDK capture directory, it is effectively the path into that directory and is documented here.
- For Environment event emitters
fault_injector,journal, andbackground_monitorit is the that emitter name.
- For
-
event.source.pid: Optional. The Linux process ID of the process that generated this event. PIDs are available for events emitted by the Antithesis SDK, or via writes to the SDK capture directory. -
event.source.container: Optional. The hostname of the container that generates this event, if any. -
event.source.stream: Optional. Current values include"error","info","internal". Forstdout/stderrthis maps to"info"and"error"respectively. -
event.output_text: Optional. The text-payload of the event. Forstdoutevents this will be the verbatim text, with one event per newline. -
event.exit_code: Optional. If present, means that the Antithesis environment has terminated with an exit code. This is an error in the Antithesis platform, please emailsupport@antithesis.comto let us know.