Cilium Hubble Agent: Real-Time Network Topology Monitoring
Cilium Hubble Agent: Real-Time Network Topology Monitoring
cillium-hubble-agent monitors network link states in real time and exposes the topology via REST and WebSocket APIs. It supports two discovery modes: reading from Linux sysfs directly, or querying Cilium’s Hubble observability layer.
Overview
In containerized and Kubernetes environments, network topology is dynamic — links come up and down as pods are scheduled, interfaces are created, and Cilium endpoints change. This agent tracks that state continuously and makes it queryable and streamable.
Discovery Modes
Linux sysfs Mode
Reads link state directly from /sys/class/net/*/operstate for local interface monitoring.
import os
from pathlib import Path
class SysfsDiscovery:
NET_PATH = Path("/sys/class/net")
def get_links(self) -> list[dict]:
links = []
for iface in self.NET_PATH.iterdir():
operstate = (iface / "operstate").read_text().strip()
carrier = self._read_int(iface / "carrier")
speed = self._read_int(iface / "speed")
links.append({
"name": iface.name,
"state": operstate,
"carrier": carrier,
"speed": speed,
})
return links
def _read_int(self, path: Path) -> int | None:
try:
return int(path.read_text().strip())
except (OSError, ValueError):
return NoneCilium Hubble Mode
Queries Hubble’s gRPC observer API to discover active flows and derive topology from real traffic.
import grpc
from hubble.proto import observer_pb2, observer_pb2_grpc
class HubbleDiscovery:
def __init__(self, hubble_addr: str = "localhost:4245"):
self.channel = grpc.insecure_channel(hubble_addr)
self.stub = observer_pb2_grpc.ObserverStub(self.channel)
def stream_flows(self, follow: bool = True):
req = observer_pb2.GetFlowsRequest(
follow=follow,
whitelist=[observer_pb2.FlowFilter(
verdict=[flow_pb2.Verdict.FORWARDED]
)]
)
for flow in self.stub.GetFlows(req):
yield {
"src": flow.flow.source.pod_name,
"dst": flow.flow.destination.pod_name,
"protocol": flow.flow.l4.WhichOneof("protocol"),
"namespace": flow.flow.source.namespace,
"timestamp": flow.flow.time.ToDatetime().isoformat(),
}REST API
from fastapi import FastAPI
from .discovery import SysfsDiscovery, HubbleDiscovery
app = FastAPI(title="Hubble Agent")
@app.get("/topology")
async def get_topology():
"""Return current network topology snapshot."""
return {"links": agent.get_current_topology()}
@app.get("/links")
async def get_links():
"""Return all monitored link states."""
return {"links": agent.get_links()}
@app.get("/health")
async def health():
return {"status": "ok", "mode": agent.discovery_mode}WebSocket Streaming
Clients can subscribe to live topology updates over WebSocket:
from fastapi import WebSocket
import asyncio
@app.websocket("/ws/topology")
async def topology_stream(websocket: WebSocket):
await websocket.accept()
try:
async for update in agent.topology_updates():
await websocket.send_json(update)
except Exception:
await websocket.close()Example client:
const ws = new WebSocket("ws://agent:8080/ws/topology");
ws.onmessage = (event) => {
const update = JSON.parse(event.data);
graph.updateLink(update.src, update.dst, update.state);
};Deployment
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: hubble-agent
spec:
selector:
matchLabels:
app: hubble-agent
template:
spec:
hostNetwork: true
containers:
- name: agent
image: hubble-agent:latest
env:
- name: DISCOVERY_MODE
value: "hubble"
- name: HUBBLE_ADDR
value: "$(NODE_IP):4245"
ports:
- containerPort: 8080
volumeMounts:
- name: sys
mountPath: /sys/class/net
readOnly: true
volumes:
- name: sys
hostPath:
path: /sys/class/netConfiguration
# config.yaml
discovery:
mode: hubble # or "sysfs"
hubble_addr: "localhost:4245"
poll_interval: 5 # seconds (sysfs mode)
api:
host: "0.0.0.0"
port: 8080
websocket:
max_clients: 100
heartbeat_interval: 30Conclusion
cillium-hubble-agent provides a lightweight, dual-mode approach to network topology monitoring in Kubernetes. Whether you need low-level sysfs polling or rich Cilium Hubble flow data, the REST and WebSocket APIs make it easy to build real-time visualization dashboards on top.
Source: GitHub