Skip to content

0.12.0

Released 2026-08-11.

The pod. A thirteenth entity type, and the first vocabulary addition since the type set became something producers import rather than retype.

No wire-contract break, no data migration. Adding a type is additive: nothing about existing types, relations or events changes.

Why a pod is not a container

A Kubernetes pod is the unit of scheduling and of failure: one or more containers sharing a network namespace and a lifetime. It is none of the twelve existing types — not a container, not a machine, not a service instance.

The obvious alternative was to leave it out and keep the pod's name as an attribute on each container. It does not hold, for a reason this project has met before: an attribute you have to string-match on is not a join. Answering what else runs in this pod would mean scanning every container and comparing strings — the same shape that made IP addresses untraversable until network.address became a node of its own.

The argument that settles it is telemetry. The network namespace is shared per pod, so pod-scoped network measurements describe the pod and nothing else. A type that owns telemetry needs an entity to attach it to, or those measurements have no subject.

Secondary, and still real: the pod is the unit of failure. A node draining evicts pods, and pods take their containers with them. Without it, a blast radius reads as N containers with no grouping — which is not how anyone, human or model, reasons about a cluster.

Shape

Type pod
Identity the UID Kubernetes assigns, never namespace/name
Relations containerruns_onpodruns_onhost

Identity is the UID for the same reason a workload's is: namespace/name is mutable and reused, so a deployment deleted and recreated under the same name would silently look like the same thing. The UID says otherwise.

No new relation type was needed. runs_on's From/To pairing is advisory, so the chain composes without inventing anything, and its impact flows from target to source — a node failing takes its pods, which take their containers, transitively and with no extra code. impact_of answers correctly the day the first pod arrives.

For producers

pod ships in pkg/emit/v0.7.0 as wire.TypePod, and Toise's registry derives from that same constant.

Two versions matter, and they are not interchangeable:

  • pkg/emit/v0.7.0 lets a producer compile against the type;
  • Toise 0.12.0 lets it emit — the boundary refuses unknown types under the default strict vocabulary, so pods sent to an older instance are rejected per-record.

That split is not an accident of packaging. The root module resolves the SDK from its published version, so a constant cannot be registered in the engine before it is tagged. It is the same ordering the vocabulary export followed.

Upgrading

Nothing to do. A deployment with no pods is unaffected; existing types, relations and stored events are untouched.