OCI Standards (The Truce)
[!NOTE] This module explores the core principles of OCI Standards (The Truce), deriving solutions from first principles and hardware constraints to build world-class, production-ready expertise.
1. The Container Wars (2013-2015)
In the beginning, Docker was the only game in town. But as it grew, companies like CoreOS (creating rkt) and Google (Kubernetes) wanted standardization. They feared vendor lock-in.
The Open Container Initiative (OCI) was formed in 2015 to create open standards.
The Two Specs
- Image Spec: Defines the “shipping container”. What’s inside the tarball? (Manifest, Layers, Config).
- Runtime Spec: Defines the “crane”. How do you unpack and run it? (
config.json, rootfs).
Because of OCI, you can build with Docker, push to Amazon ECR, and run with Kubernetes (CRI-O) or Podman.
2. Interactive: OCI Bundle Inspector
An OCI Bundle is just a directory with a config.json and a rootfs folder.
{
"ociVersion": "1.0.2",
"process": {
"user": { "uid": 0, "gid": 0 },
"args": ["sh"],
"env": ["PATH=/usr/local/sbin..."],
"cwd": "/"
},
"root": {
"path": "rootfs",
"readonly": true
},
"mounts": [
{
"destination": "/proc",
"type": "proc",
"source": "proc"
}
],
"linux": {
"namespaces": [
{ "type": "pid" },
{ "type": "network" },
{ "type": "mount" }
]
}
}
3. Code Examples
1. Go Implementation (OCI Runtime Spec)
This is the actual Go struct used by runc to parse config.json.
package main
import (
"encoding/json"
"fmt"
"os"
"github.com/opencontainers/runtime-spec/specs-go"
)
func main() {
// 1. Create a minimal OCI Spec
spec := specs.Spec{
Version: specs.Version,
Process: &specs.Process{
Args: []string{"sh"},
Env: []string{"PATH=/bin"},
Cwd: "/",
},
Root: &specs.Root{
Path: "rootfs",
Readonly: true,
},
Linux: &specs.Linux{
Namespaces: []specs.LinuxNamespace{
{Type: specs.PIDNamespace},
{Type: specs.NetworkNamespace},
},
},
}
// 2. Marshal to JSON (config.json)
data, err := json.MarshalIndent(spec, "", " ")
if err != nil {
panic(err)
}
// 3. Write config.json
os.WriteFile("config.json", data, 0644)
fmt.Println("Generated OCI config.json!")
}
2. Java Implementation (Parsing OCI)
Java tools can inspect OCI bundles (e.g., for security scanning) by parsing the standard JSON format.
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import java.io.File;
import java.io.IOException;
public class OciInspector {
public static void main(String[] args) throws IOException {
ObjectMapper mapper = new ObjectMapper();
// 1. Read config.json
JsonNode root = mapper.readTree(new File("config.json"));
// 2. Inspect Process Args
JsonNode argsNode = root.path("process").path("args");
System.out.println("Container Command: " + argsNode.toString());
// 3. Check for Privileged Mode (Security Check)
// If namespaces are missing, it might be running on host!
JsonNode namespaces = root.path("linux").path("namespaces");
boolean hasPidNS = false;
for (JsonNode ns : namespaces) {
if (ns.get("type").asText().equals("pid")) {
hasPidNS = true;
}
}
if (!hasPidNS) {
System.out.println("WARNING: Container shares Host PID namespace!");
} else {
System.out.println("PID Namespace isolation: Active");
}
}
}
[!TIP] Try it yourself:
- Run
docker export $(docker create busybox) | tar -C rootfs -xvf -- Run
runc spec- Run
sudo runc run mycontainerYou just ran a container without the Docker daemon!