Technical Report
Cloud-Native Security  ·  2026

Zero-Day: Attack Detection & Mitigation for Kubernetes

A production-grade framework that models how containers interact over time with a Temporal Graph Neural Network, explains every alert, and contains threats through a safe, human-approved Kubernetes operator — signature-less by design.

0.92
ROC-AUC
<1 s
Mean time to detect
4 + 1
Models + ensemble
85%
Containment success
v1.0.0  ·  PyTorch + PyTorch Geometric  ·  Go / controller-runtime  ·  Prometheus + Grafana  ·  Strimzi Kafka
01

Executive Summary

Zero-Day is a six-layer security framework for detecting and mitigating zero-day attacks in Kubernetes clusters. Because zero-day exploits have no known signature, the system abandons rule matching entirely and instead learns the normal shape of container behaviour — who talks to whom, on what ports, with what volume, in what sequence — then flags deviations in real time.

It ingests multi-source telemetry (audit logs, network flows, eBPF syscalls), builds overlapping temporal graph windows, scores them with a four-model ensemble anchored by a Temporal Graph Neural Network, attaches an explainable reason to every alert, and routes high-confidence detections to a Kubernetes-native containment operator that acts only after a human approval token is supplied.

Detection
Graph-basedTGNN with graph attention + sinusoidal temporal encoding captures lateral movement flat models miss
Explainability
SHAP + gradientsFeature attributions and suspicious-neighbour isolation on every alert
Response
Safe by defaultDry-run mode, confidence ≥ 0.7 gate, and approval-token workflow before enforcement
Operations
Full stack8-panel Grafana dashboard, Docker Compose PoC, Helm production chart
02

Why This Project — The Zero-Day Problem

In cloud-native environments, Kubernetes clusters are under constant threat, and the most dangerous threats are the ones with no patch and no signature. Without an intelligent detection system, teams face five compounding failures:

  • Invisible attacks — container breakouts and supply-chain compromises are virtually undetectable by static rules.
  • Delayed response — breaches go unnoticed for weeks, allowing lateral movement across the cluster (MITRE ATT&CK T1021).
  • Blast radius — a compromised pod escalates privileges (T1548), reads secrets, and spreads before anyone intervenes.
  • Operational blindness — thousands of flows, syscalls, and audit events per second with no way to separate normal from malicious.
  • No explainability — even when an anomaly fires, SOC teams cannot see why, producing alert fatigue.
Design goal

Detect unknown attacks from behaviour alone, explain each decision to an analyst, and contain the threat automatically — while keeping a human in the loop for every enforcement action.

03

Six-Layer System Architecture

The system separates concerns into six independently deployable layers. Docker Compose orchestrates the local proof-of-concept; Helm charts and Kubernetes manifests handle production. A single telemetry event travels the full path below.

1 — Data Ingestion Layer K8s Audit Logs API server events ISO-8601 / epoch parse Cilium / Hubble Flows 5-tuple network flows bytes in / out eBPF Syscalls container-level Kafka (Strimzi) / JSONL unified event stream 2 — Stream Processing Layer · Temporal Graph Builder sessionize by container_id & 5-tuple · sliding windows (60 s window, 30 s step) NetworkX directed graphs → Parquet snapshots · background auto-flush thread window_<ts>.nodes.parquet + .edges.parquet 3 — ML Inference Layer · parallel scoring ensemble Autoencoder node features LSTM-AE temporal volume DeepLog log sequences TGNN graph + time ensemble vote → anomaly score 0.0–1.0 if score > threshold → Containment CR + XAI report 4 — Containment & Response Layer · Go operator actions: deny-all NetworkPolicy · Eviction API · Istio blackhole safety: confidence ≥ 0.7 · dry-run default · approval tokens 5 — Observability & Alerting Layer Prometheus 5 s scrape · Grafana 8-panel Elasticsearch logs · Jaeger tracing 6 — UI & SaaS Management Layer Flask Web UI · port 5000 SaaS API · multi-tenant billing · JWT
Figure 1 — End-to-end telemetry path. The accent boxes mark the core contribution: a TGNN that scores temporal graph windows, and a Kubernetes operator that enforces containment only behind a confidence gate and a human approval token.

Architecture highlights

04

Temporal Graph Construction Engine

The Graph Builder service converts raw telemetry into temporal graph windows suitable for ML processing.

FeatureDetail
SessionizationGroups events by container_id, pod_name, and 5-tuple network flows
Sliding windows60-second windows with a 30-second step — overlapping, so an attack straddling a boundary still appears whole
Graph structureNetworkX directed graphs with node and edge feature vectors
Output formatApache Parquet via the fastparquet engine (no C-extension conflicts in containers)
Dual modeFile-based JSONL input (local) or Kafka consumer (production)
Auto-flushBackground flusher wakes every step seconds; generates synthetic fallback events when real traffic is quiet

Input event schema

{
  "timestamp": 1704282000,
  "event_type": "network_flow",
  "src_pod": "frontend-abc123",
  "dst_pod": "backend-xyz789",
  "src_ip": "10.0.1.5",
  "dst_ip": "10.0.2.15",
  "dst_port": 8080,
  "bytes_out": 1024,
  "bytes_in": 2048
}

Window outputs

# File mode (local PoC)
python -m graph_builder.main file --input-file events.jsonl \
  --out-dir ./graphs --window-size 60 --step 30

# Kafka mode (production)
python -m graph_builder.main kafka --topic telemetry.logs \
  --servers kafka:9092 --out-dir /data/graphs
05

ML-Based Anomaly Detection — 4 Models + Ensemble

The inference layer runs four anomaly detectors in parallel, each with a different strength, and combines them by ensemble vote.

ModelArchitectureBest forThreshold
AutoencoderFC MLP 16→64→32→64→16, MSE lossNode-level static feature anomalies0.5
LSTM-AELSTM encoder (H=64, T=50) → latent → LSTM decoderTemporal flow-volume anomalies0.6
DeepLogEmbedding(64) → LSTM(H=128) → Linear(vocab)Syscall & log-sequence anomalieslow next-token p
TGNNGraphSAGE / GATConv (4 heads) + temporal LSTM aggregationLateral movement & multi-pod attacks0.5

5.1 TGNN architecture deep dive

INPUT: Parquet window files
├─ nodes: (pod_name, cpu, memory, network_in, network_out, syscall_count) → 6-D
└─ edges: (flow_count, bytes_in, bytes_out, latency, duration)             → 5-D

NODE ENCODER (MLP)
└─ Linear(6, 64) → ReLU → Linear(64, 32)     → 32-D embedding per node

EDGE ENCODER (with temporal encoding)
├─ Sinusoidal positional time encoding (64-D)
│    PE(t, 2k)   = sin(t / 10000^(2k/d))
│    PE(t, 2k+1) = cos(t / 10000^(2k/d))
├─ concat [edge_features(5-D), time_encoding(64-D)] = 69-D
└─ MLP projection                            → 16-D edge embedding

ATTENTION LAYERS (Graph Attention, 4 heads)
├─ Head 1: port-based communication patterns
├─ Head 2: volume-based anomalies (unusual byte counts)
├─ Head 3: temporal sequence anomalies (timing deviations)
├─ Head 4: unusual peer connections (lateral movement)
├─ attention[i→j] = softmax(LeakyReLU(wᵀ[hᵢ ‖ hⱼ]))
└─ output[i]      = σ(Σⱼ attention[i→j] · W · hⱼ)   → (num_nodes, 64)

DUAL ANOMALY SCORING HEADS
├─ Node head: Linear(64→32)→ReLU→Linear(32→8)→ReLU→Linear(8→1)→Sigmoid
├─ Edge head: Linear(192→64)→ReLU→Linear(64→16)→ReLU→Linear(16→1)→Sigmoid
└─ Composite: final = 0.6 · node_anomaly + 0.4 · edge_anomaly

Training strategy — contrastive triplet loss

ℒ(a, p, n) = max ( ‖f(a) − f(p)‖2 − ‖f(a) − f(n)‖2 + α,  0 ) anchor / positive drawn from benign windows, negative from attack windows · margin α

Feature standardisation (TGNN preprocessing)

xnorm = x − μσ + 10−6 per-feature mean and standard deviation, with an epsilon guard against zero variance
Best practice

Run the baseline models (Autoencoder, LSTM-AE) for speed and the TGNN for accuracy. If PyTorch Geometric is unavailable, a lightweight IsolationForest baseline acts as a final safety net.

06

Explainable AI (XAI) Integration

Every alert carries an explanation so SOC analysts can understand why it fired.

XAI methodWhat it does
SHAP DeepExplainerFeature-level attributions over Autoencoder inputs — which features drove the score
Gradient graph attributionsEvaluates ∇xℒ w.r.t. node features to isolate top influential features and suspicious neighbours
Feature deviation analysisLightweight production explainer — absolute percentage deviation from baseline mean μf, no heavy SHAP dependency

Example explanation output

{
  "score": 0.85,
  "anomaly": true,
  "model": "tgnn",
  "explanation": "High outbound traffic to unusual port",
  "top_features": ["bytes_out: +340% above baseline", "dst_port: 22 (unusual)"],
  "suspicious_nodes": ["admin-pod-4", "db-pod-7"]
}
07

Red-Team Attack Playbooks — MITRE ATT&CK Mapped

The project ships realistic adversary simulations used to generate attack windows for training and evaluation.

PlaybookMITRE IDWhat it simulates
Container EscapeT1610Accesses /var/run/docker.sock, runs docker run --privileged, escalates CAP_SYS_ADMIN
Privilege EscalationT1548.001Suspicious setuid binary, prctl(PR_SET_DUMPABLE), spawns a root shell (UID 0)
Lateral MovementT1021Internal DNS enumeration of *.default.svc.cluster.local, TCP RPC to :8080, credential POST to /api/admin/credentials
Data ExfiltrationT1041500,000-byte outbound burst to an external IP, rapid concurrent connections to unknown public subnets
08

Safe Automated Containment — Kubernetes Operator

The Containment Operator (Go + controller-runtime) watches for Containment custom resources and enforces policy behind multiple safety layers.

ActionMechanismRiskRollback
Isolate podDeny-all NetworkPolicy (empty ingress/egress)mediumDelete the NetworkPolicy
Evict podGraceful termination via Eviction API (30 s grace)highPod auto-restarts via its Deployment
Blackhole trafficIstio VirtualService, 100% fault delay (1000 s)lowDelete the VirtualService

Containment CRD — security.example.com/v1alpha1

spec:
  alertID: "alert-frontend-123"
  confidence: 0.92
  suggestedAction: "isolate_pod"   # isolate_pod | evict_pod | blackhole_traffic
  explanation: "Unusual outbound traffic pattern"
  dryRun: true
  approvalToken: ""
status:
  state: "pending"     # pending → approved → applied → failed
  appliedAction: ""
  result: ""

Operator reconciliation loop

Reconcile(ctx, req)
  ├── Fetch Containment CR
  ├── If State == "applied" || "failed"        → return (no-op)
  ├── If Confidence < 0.7                       → UpdateStatus("pending", "confidence_too_low")
  ├── If !DryRun && ApprovalToken == ""         → requeue every 30s ("awaiting_approval")
  └── Execute action
        ├── "isolate_pod"       → create deny-all NetworkPolicy
        ├── "evict_pod"         → delete pod, 30s GracePeriod
        └── "blackhole_traffic" → Istio VirtualService fault delay
        → UpdateStatus("applied", action)

Approval workflow

kubectl describe containment alert-frontend-123
kubectl patch containment alert-frontend-123 \
  -p '{"spec":{"approvalToken":"approved-by-analyst"}}'
kubectl get containment alert-frontend-123 -o json | jq '.status'
09

Real-Time Monitoring & Visualization

A colour-coded Grafana dashboard with eight panels, refreshing every 5 seconds.

PanelPromQLGreenYellowRed
Events/sec (1m)rate(zero_day_events_total[1m])< 100/s100–500/s> 500/s
Active Alerts (5m)increase(zero_day_attack_alerts_total[5m])01–5> 5
Attack Scorezero_day_attack_score0–3940–6970–100
Latency (p95)histogram_quantile(0.95, …)< 50 ms50–200 ms> 200 ms
Four of the eight dashboard panels; the remainder track event-volume, alert, and attack-score trends over time.

Key Prometheus metrics

MetricTypePurpose
zero_day_events_totalCounterTotal events received, labelled by source
zero_day_attack_alerts_totalCounterAlerts triggered, labelled by severity
zero_day_attack_scoreGaugeCurrent score 0–100, decays 1/sec after 30 s of inactivity
graph_builder_processing_duration_secondsHistogramWindow construction latency distribution
inference_duration_secondsHistogramInference latency per model
10

Multi-Tenant SaaS Management Layer

A production SaaS layer (saas-management-api/) provisions an isolated Kubernetes namespace per tenant, with ResourceQuotas and LimitRanges applied automatically.

TierRPSConnectionsStoragePrice/mo
Free10510 GB$0
Starter10020100 GB$99
Professional500100500 GB + custom rules$499
Enterprise2,0005005 TB + SSO + dedicated SLA$2,000
POST /api/v1/auth/register        onboard tenant, generate API key, create K8s namespace
GET  /api/v1/tenants/<id>          retrieve tenant profile & subscription state
GET  /api/v1/tenants/<id>/usage    aggregate requests, inference calls, storage over N days
POST /api/v1/tenants/<id>/upgrade  dynamic tier upgrade with audit logging
GET  /api/v1/admin/tenants         multi-tenant administrative overview
11

Experimental Results

End-to-end test suite — all 7 passed

[TEST 1] Docker Compose Services   ✅ all services running
[TEST 2] Metrics Exporter Health   ✅ 15 zero_day metrics exposed
[TEST 3] Prometheus Scraping       ✅ scraping metrics
[TEST 4] Grafana Authentication    ✅ login successful
[TEST 5] Dashboard Import          ✅ imported and accessible
[TEST 6] Demo Execution            ✅ 7,746 events, metrics updated
[TEST 7] Attack Demo               ✅ alerts incremented (400)

ML validation & performance

MetricActualTarget
ROC-AUC0.92> 0.90
Mean time to detect (MTTD)< 1 s< 100 ms goal
Inference latency50 ms< 100 ms
Containment success rate85%> 80%
Dashboard load< 200 ms< 500 ms
Startup time< 30 s< 1 min

False positives are minimised by the ≥ 0.7 confidence gate before any containment CR is acted on. The IEEE proof-of-concept paper reports 120+ graph windows generated on Minikube with attack-to-dashboard latency verified under one second.

12

Key Design Decisions

Why a Temporal GNN?
Lateral movement lives in graph topology — pod1 suddenly reaching admin-pod4 on port 22 — not in any single metric. A TGNN models the relationships flat-feature models discard.
Why four models?
Autoencoder is fast but relationship-blind; LSTM-AE reads sequences; DeepLog reads logs; TGNN reads topology + time. Ensemble voting gives the best precision–recall trade-off.
Why a Kubernetes operator?
A CRD-based operator follows the reconciliation pattern — idempotent, retryable, and native to kubectl approval workflows. Far more reliable than scripts.
Why dry-run by default?
A false positive that auto-contains can outdamage the attack. dryRun: true plus an approval token ensures a human validates before enforcement.
Why Parquet + fastparquet?
Columnar, compressed, fast analytical reads. fastparquet avoids C-extension conflicts in containers; a PersistentVolume shares windows between writer and reader with no database.
Why dual-mode (file + Kafka)?
File mode demos the whole system with no Kafka, Zookeeper, or Strimzi. Kafka mode handles production throughput with 3-broker resilience.
13

Challenges Faced & Solutions

#ChallengeSolution
1TGNN training complexity — converting Parquet windows into PyG Data objects with correct edge_index, edge_attr, and 64-D sinusoidal encodingsCareful tensor construction, a graceful fallback when PyG is missing, and an IsolationForest safety net
2Safe containment design — automated responses that must not take down productionConfidence threshold ≥ 0.7, dry-run default, approval workflow, and a graduated NetworkPolicy → Eviction → Blackhole hierarchy
3Multi-source telemetry normalization — audit logs, Cilium flows, and eBPF syscalls all differ in schemaUnified event format with schema mapping, ISO-8601/epoch parsing, and window-boundary handling
4Sliding-window graph construction across window boundaries with Kafka lagBackground flusher with synthetic fallback events and explicit buffer cleanup after processing
5Operator reconciliation edge cases — unregistered CRDs, already-evicted pods, out-of-order approval tokensIdempotent reconcile with 30-second requeue on retryable failures
6XAI in resource-constrained containers — SHAP is heavyLightweight xai_explain.py computes feature deviations from baseline means, always available
14

Tech Stack & Deployment

ML & backend
Python 3.11+, PyTorch 2.0+, PyTorch Geometric, scikit-learn, SHAP, NetworkX, pandas, PyArrow / fastparquet, Flask, prometheus_client, kafka-python, SQLite
Containment
Go 1.21+, controller-runtime v0.16 (Kubebuilder), client-go v0.28, Zap structured logging
Infrastructure
Kubernetes / Minikube / GKE / EKS / AKS, Istio (mTLS), Cilium / Hubble, Apache Kafka (Strimzi, 3 brokers), Docker Compose, Helm 3, Velero backups
Observability
Prometheus (5 s scrape, 15-day retention), Grafana (8-panel), OpenTelemetry Collector, Fluent Bit, Jaeger, Elasticsearch / ClickHouse
Namespaces
ml, quarantine, monitoring, kafka, prod, dev — default-deny-all NetworkPolicy on prod, Pod Security Standards enforced
Quick start
Docker Compose: bash scripts/start_local_stack.sh → Grafana :3000, Prometheus :9090, Metrics :8000

Helm production install

helm install zero-day ./helm/zero-day-saas \
  --set highAvailability.replicas.inferenceService=3 \
  --set autoscaling.hpa.maxReplicas=15 \
  --set security.mtls.enabled=true \
  --set backup.velero.enabled=true

Zero-Day · Kubernetes Attack Detection & Mitigation Framework · Technical Report · 2026