Skip to main content
Docs / Evidence Format

Evidence Format

Public fields for SIEM integration and log analysis.

When PandoCore detects anomalous behavior, it emits a structured JSON record. This page documents the public fields your SIEM or incident pipeline can rely on.

Stable vs. internal fields

Evidence envelopes may contain additional fields that are internal to PandoCore's detection engine. These are not documented here and may change between releases without notice. Build your integrations against the fields listed on this page only.

Delivery Channels

Channel Format
The controller Records are delivered to it over mTLS and written to a durable spool before it acknowledges them. It owns every outbound destination from there
Your webhook HTTP POST of Evidence JSON, configured on the controller
stdout One JSON record per line
Kubernetes Event K8s Event object, survives pod deletion
SIEM Splunk, Elastic, Datadog or syslog, configured on the controller
Slack Formatted message, configured on the controller

Webhook headers

Header Description
Content-Type application/json
X-Pando-Evidence-ID UUID of the evidence record
X-Pando-Event-Type Event type, currently collapse
X-Pando-Schema-Version Schema version of the payload

Delivery is retried with exponential backoff, configured on the controller. No workload pod holds a destination credential: the sensor delivers to the controller and the controller delivers onward, which is why these are controller settings rather than per-workload ones. See Controller.

A record is externalized before any action is taken

Evidence is sealed, signed and shipped before the response chain is even resolved, and a failed externalization aborts the response. That ordering is deliberate: there is no action without a durable record first. The consequence for a consumer is that a trip record carries intent rather than outcome, which is why there is a second record type for what actually happened.

Three event types

event_type Meaning
pando.evidence A detection. Carries the intended response
pando.response What the response chain actually did. Correlated to the trip by trip_evidence_id, not by sharing its id
pando.heartbeat Periodic liveness, so a consumer can tell silence from health
Two wire names still say "sidecar"

metadata.sidecar_version and the action_taken value sidecar_absent keep their names although the component is now the node sensor. They are a wire contract: renaming them would break every parser, dashboard and SIEM rule written against them, so they are deliberately unchanged. Read both as referring to whatever is reporting, which on the supported install is the sensor.

JSON Example

{
  "version": "3.3",
  "event_type": "pando.evidence",
  "id": "550e8400-e29b-41d4-a716-446655440000",
  "timestamp": "2026-03-16T14:30:00.123Z",
  "pod": {
    "name": "my-app-7d4f9b8c5-x2kl9",
    "namespace": "production",
    "uid": "f3b2c1d4-...",
    "node": "gke-cluster-pool-1-abc123"
  },
  "trip_reason": "drift_threshold_exceeded",
  "action_taken": "collapse",
  "hash": "a1b2c3d4e5f6...",
  "previous_hash": "9f8e7d6c5b4a...",
  "sequence": 42,
  "metadata": {
    "sidecar_version": "0.1.0",
    "mode": "isolate",
    "customer_id": "cust_abc123"
  }
}

Field Reference

Top-Level

Field Type Description
version string Schema version of the payload.
id UUID Unique evidence record ID.
timestamp ISO 8601 When the detection occurred.
trip_reason string Short machine-readable label for the detection category (e.g., drift_threshold_exceeded, integrity_violation, deadman_timeout).
action_taken string The intended response at the moment the record was sealed, which is before any action runs. One of alert_only (benign, no response chain), monitor_collapse (collapse-grade, but the mode or the learning window meant nothing acted), collapse (a containment action was attempted), sidecar_absent (the controller noticed a sensor that should be reporting has stopped) or absence_detection_degraded (absence detection itself could not run). The last two are stamped by the controller rather than by a sensor.
hash string SHA-256 hash of this record. Used for the tamper-evident chain.
previous_hash string Hash of the previous record in the chain.
sequence integer Monotonically increasing record counter.

pod

Field Description
pod.name Full pod name.
pod.namespace Kubernetes namespace.
pod.uid Pod UID, when available.
pod.node Node the pod was scheduled on, when available.

response_chain

Array of response actions attempted, in order, with whether each succeeded and when it ran. This appears on the pando.response receipt rather than on the trip record, because the trip record is sealed before the chain resolves. Correlate the two by trip_evidence_id.

Field Description
action alert or isolate. Isolate is the ceiling of the supported install
success Whether the action completed successfully
timestamp ISO 8601 timestamp when the action ran

metadata

Field Description
metadata.sidecar_version Version of the component that emitted the record, which on the supported install is the node sensor. The field name is retained for wire compatibility, so a parser written against it keeps working.
metadata.mode Operating mode at the time: monitor, alert, isolate or debug.
metadata.customer_id Your customer identifier, derived from the license.

Tamper-evident chain

Evidence records form a SHA-256 hash chain. Each record's previous_hash links to the prior record, producing an audit log that downstream consumers can verify for tampering.

Slack Alerts

When a Slack destination is configured on the controller and the workload's mode is alert or isolate, PandoCore sends formatted messages colour-coded by severity.

Severity Trigger
Critical A containment action was attempted
High Significant anomaly detected
Warning Detection below the response threshold
Info Low-severity detection

Kubernetes Events

# View PandoCore events
kubectl get events -n YOUR_NAMESPACE --field-selector reason=PandoCollapse

Next Steps