Workspace API reference
These are the endpoints of your workspace that accept API keys. Everything else in the workspace serves the browser. There is no public API yet for querying telemetry or for managing organizations and workspaces.
Conventions
| Convention | Detail |
|---|---|
| Base URL | Your workspace's address, such as https://production-a7k3p2q9.app.tracix.io. The examples call it TRACIX_URL |
| Authentication | X-API-Key: txk_... on every request, over HTTPS |
| Bodies | JSON, with Content-Type: application/json |
| Errors | A status code and a JSON body with an error message |
| Times | UTC, in ISO 8601 |
| Status | Meaning |
|---|---|
401 | The key is missing, unknown, expired or revoked |
403 | The key doesn't carry the permission the endpoint needs |
Detection content
These endpoints take a CI key. They back the tracix-detections CLI; see Monitors, dashboards and detections as code for the repository format.
Validate, plan or apply
POST /api/security/detections takes the files of a detection repository at one commit, or a reference the workspace fetches itself, and validates, plans or applies them.
| Field | Type | Description |
|---|---|---|
action | string | Required. validate, plan or apply |
files | object | The repository's files as {"path": "content"}. Send files or archiveRef, not both |
revision | string | Required with files: the commit the files were taken at, up to 128 characters |
subdir | string | The folder that holds the detections, when it isn't the repository root |
archiveRef | object | {"credentialId", "repo", "ref", "subdir"}: the workspace fetches this commit from GitHub or GitLab with a credential stored in the workspace. subdir is optional |
package | string | Refuse the request unless the manifest publishes this package |
partial | boolean | validate only: the files are one batch of a larger repository |
planHash | string | Required for apply: the planHash of the plan you reviewed |
replace | boolean | apply only: confirm the plan's conflicts, replacing the rules they name |
validate and plan need security.read; apply needs security.manage. Request bodies are limited to 10 MB: for a larger repository, send archiveRef.
curl -fsS -X POST "$TRACIX_URL/api/security/detections" \
-H "X-API-Key: $TRACIX_API_KEY" \
-H "Content-Type: application/json" \
-d @request.json{
"action": "plan",
"revision": "4f2c9e1",
"files": {
"tracix-detections.yaml": "package: acme-soc\nprune: true\n",
"lists/service-accounts.yaml": "name: service-accounts\nitems:\n - svc_backup\n"
}
}Responses
| Action | Status | Body |
|---|---|---|
validate | 200 | package, revision, valid, summary (counts of files, rules, lists, YARA rulesets, disabled rules, errors, warnings and fixture results), diagnostics, files, fixtures, ignored and source |
plan | 200 | Everything validate returns, plus planHash (null when the plan can't be applied), blocking, planWarnings, counts, resources (one row per object, with its action: create, update, delete, unchanged or conflict) and hiddenResources |
apply | 200 | applied: true, package, revision, planHash, counts (created, updated, deleted, unchanged, replaced), results, postApply and source |
apply | 202 | More than 200 writes run in the background: {"job": {"jobId", "status", "total"}, "source"}. Follow the job with the next endpoint |
valid is false when a file doesn't compile or a fixture fails. source says where the files came from: {"kind": "files"}, or the code host, repository and commit for archiveRef.
Errors
| Status | When |
|---|---|
400 | The body isn't valid JSON, an unknown action, partial outside validate, a missing or malformed planHash, a package that doesn't match the manifest, or a plan that compile errors block |
404 | archiveRef: the credential, the repository or the commit can't be found or read |
409 | The content or the workspace changed since the plan, so plan again; the plan has conflicts you haven't confirmed; or another apply is running |
413 | The body is larger than 10 MB, or the repository exceeds 5,000 detection files or 50 MB |
502 | The code host refused the request, or the change wasn't accepted. Try again |
Follow a background apply
GET /api/security/detections?job=<jobId> returns the progress of an apply that runs in the background. It needs security.read.
The response is {"job": {...}} with jobId, package, revision, planHash, status (running, succeeded, failed or interrupted), total, done, counts, results, startedAt, updatedAt and, once finished, finishedAt. A job that failed or was interrupted also has an error, and a failed one the failedResource it stopped at. It answers 400 without a valid job ID and 404 for an unknown one.
Download the CLI
GET /api/security/detections/cli returns the tracix-detections CLI that matches this workspace, as tracix-detections.mjs. It needs security.read. The X-Tracix-Cli-Sha256 response header carries the file's SHA-256, so a pipeline can check it before running it.
curl -fsS -H "X-API-Key: $TRACIX_API_KEY" -D cli.headers \
"$TRACIX_URL/api/security/detections/cli" -o tracix-detections.mjsExport detection content
GET /api/security/detections/export returns detection content as repository files. It needs security.read, and a key sees every rule and list.
| Query | Description |
|---|---|
package | Required. The package to export, or for source=ui, the package name for the new files |
source | package (the default) exports the rules and lists a package publishes. ui exports rules authored in the UI as a new repository |
ids, tag, technique | source=ui only: which rules. Repeat a parameter or separate values with commas; ids takes up to 500 |
pack | source=ui: include adds rules installed from the Sigma pack to a tag or technique selection |
lists | source=ui: include also writes the value lists the rules use |
format | zip returns a ZIP archive instead of JSON |
A package export returns package, revision, files ({"path": "content"}), resources (each with exact: true when compiling the file reproduces what the workspace runs), summary and notes. Fixtures aren't stored in the workspace, so they aren't exported. It answers 404 when nothing is published under the package; a source=ui export answers 404 when no rules match and 422 when none of them can be exported.
External alerts
These endpoints take an API key of the ingest type, with any write: permission. Alerts they receive open and resolve alert episodes alongside your own monitors'.
Receive Alertmanager alerts
POST /api/ingest/alertmanager takes the payload Prometheus Alertmanager sends to a webhook receiver. Send the API key in the X-API-Key header.
| From the Alertmanager alert | Becomes |
|---|---|
status | firing opens or re-asserts an episode; resolved recovers it |
fingerprint | The identity of the alert stream |
The first of the labels instance, host, hostname, service, pod, alertname | The entity |
The severity label | critical for critical, page, p1, error or fatal; warning for warning, warn, p2 or p3; info otherwise |
The summary or description annotation | The reason |
The response is {"ok": true, "opened", "reasserted", "resolved", "ignored"}.
Send alert events
POST /api/ingest/events takes events from your own scripts, relays and third-party systems.
| Field | Type | Description |
|---|---|---|
events | array | Required. Up to 100 events per request; more are ignored |
events[].dedupeKey | string | Required. Identifies the alert stream: events with the same source and dedupeKey update one episode |
events[].status | string | Required. firing or resolved |
events[].entity | string | Required. What the alert is about, such as a host or service name |
events[].source | string | Up to 32 letters, digits, _ or -. Defaults to webhook |
events[].title | string | Defaults to <source>: <entity> |
events[].reason | string | Defaults to external alert |
events[].severity | string | Mapped the same way as Alertmanager's severity label |
events[].labels | object | Up to 10 string labels |
Events missing a required field are dropped. Long values are cut to fit: 256 characters for dedupeKey and entity, 300 for title and 1,000 for reason.
curl -fsS -X POST "$TRACIX_URL/api/ingest/events" \
-H "X-API-Key: $TRACIX_API_KEY" \
-H "Content-Type: application/json" \
-d '{"events": [{"dedupeKey": "backup-nightly", "status": "firing", "entity": "db-01", "source": "backup", "severity": "warning", "reason": "Nightly backup did not finish"}]}'{ "ok": true, "received": 1, "dropped": 0, "opened": 1, "reasserted": 0, "resolved": 0, "ignored": 0 }It answers 400 when the body has no events array or no valid event.