Parent guide: AGENTS.md — product overview, architecture, domain model, global conventions Related: managed/AGENTS.md (server backend) · api/AGENTS.md (API definitions) · admin/AGENTS.md (CLI)
pmm-agent is the client-side monitoring agent for PMM. It runs on every monitored host, managing metric exporters as child processes, running built-in QAN and Real-Time Analytics (RTA) collectors in-process, executing on-demand actions (explain, PT summary), and performing backup/restore jobs. It communicates with pmm-managed on the PMM Server over a persistent bidirectional gRPC stream.
The agent receives a desired state (SetStateRequest) from pmm-managed describing which agents should be running. The Supervisor computes a diff (toStart, toRestart, toStop) and reconciles actual state to match.
-
Process agents (exporters) — external binaries run as child processes via
agents/process/. Each has a state machine:STARTING → RUNNING(orFAILINGwith backoff). Includes node_exporter, mysqld_exporter, mongodb_exporter, postgres_exporter, proxysql_exporter, rds_exporter, azure_exporter, valkey_exporter, VMAgent, Nomad. -
Built-in agents — Go code implementing the
BuiltinAgentinterface, run in-process. Includes QAN collectors (perfschema, slowlog, pg_stat_statements, pg_stat_monitor, MongoDB profiler, mongolog) and RTA agents (MongoDB realtimeanalytics).
The client package maintains a persistent bidirectional gRPC stream (Agent.Connect) with reconnect/backoff:
- Server → Agent:
SetStateRequest,StartAction,StopAction,CheckConnection,StartJob,StopJob,Ping,GetVersions,PBMSwitchPITR,AgentLogs - Agent → Server:
StateChanged,QanCollect,ActionResult,JobResult,Pong - A separate RTA channel streams
CollectRequestdata via client-streaming RPC
agentlocal exposes a local gRPC + JSON API for status, Prometheus metrics, pprof debug endpoints, and config reload.
| Package | Responsibility |
|---|---|
commands |
CLI commands: run (main event loop), setup (registration with server) |
config |
YAML + CLI flags + env vars configuration; thread-safe Storage for runtime access |
client |
gRPC client managing persistent connection to pmm-managed, message routing |
client/channel |
Bidirectional gRPC stream abstraction with request/response correlation |
agentlocal |
Local API server: status, reload, debug endpoints |
agents/supervisor |
Central lifecycle manager: start/stop/restart agents, port allocation |
agents/process |
External process wrapper: FSM (STARTING→RUNNING→FAILING), backoff, logging |
agents/mysql, postgres, mongodb |
Built-in QAN and RTA collectors |
runner/actions |
Short-lived actions: MySQL/PostgreSQL/MongoDB explain, show create table, PT summary |
runner/jobs |
Long-lived jobs: MySQL backup/restore (mysqldump, xtrabackup), MongoDB backup/restore (PBM) |
connectionchecker |
Verifies connectivity to MySQL, PostgreSQL, MongoDB, ProxySQL |
serviceinfobroker |
Discovers service metadata (versions, tables, databases) |
utils/templates |
Renders exporter args/env/config files from server-provided Go templates |
pmm-agent has no direct database access. All state comes from pmm-managed via gRPC:
SetStateRequestcontains the desired set of agents with their configurationsAgentProcess/BuiltinAgentare the runtime representations managed by the Supervisor- Exporter configuration (args, env, text files) is templated from server-provided data using
listen_port,paths_base, and other variables - VMAgent receives a Prometheus scrape config rendered by pmm-managed
- Sources: YAML file (
pmm-agent.yaml), CLI flags, environment variables (PMM_AGENT_*) - Runtime access:
config.Storageprovides thread-safeGet()andReload() - Key settings:
server.address,server.username,server.password— PMM Server connectionpaths.exporters_base— base directory for exporter binariespaths.tempdir— temporary directory for rendered config filesports.min,ports.max— port range for exporter listen addresses- Per-exporter paths:
paths.node_exporter,paths.mysqld_exporter, etc.
- Use
config.Storagefor thread-safe config access - Implement
BuiltinAgentinterface for new in-process collectors (methods: Run, Changes, Describe, Collect) - Use
process.Processfor new external exporters - Use table-driven tests with golden files for parsers
- Use
utils/templatesto render exporter args from server-provided templates - Follow the supervisor pattern — let the supervisor manage all agent lifecycle
- Don't hardcode exporter binary paths — use
config.Paths - Don't bypass the supervisor for agent lifecycle management
- Don't use raw SQL — the agent has no database; all data comes via gRPC
- Don't modify exporter args directly — they come from server templates
- Unit tests:
make test(with race detector, sequential-p 1) - Integration environment:
make env-upstarts docker-compose with MySQL, MongoDB, PostgreSQL, Valkey - Database shells:
make env-mysql,make env-mongo,make env-psql - Fuzz tests:
make fuzz-slowlog-parser,make fuzz-postgres-parser - Benchmarks:
make benchfor slowlog and postgres parsers - Coverage:
maincover_test.gowithmaincoverbuild tag - Golden files: parser tests use golden files in
testdata/directories - Linting:
make check-allbefore submitting PRs
- reform: not used (agent has no DB)
- mockery: generates mocks for supervisor, connectionChecker, serviceInfoBroker interfaces
- protobuf: agent consumes types from
/api; runmake genfrom repo root if proto files change
agent/main.go— entry point, CLI setupagent/commands/run.go— main event loop wiring client, supervisor, runneragent/agents/supervisor/supervisor.go— central agent lifecycle manageragent/agents/process/process.go— external process state machineagent/client/client.go— gRPC client and message routingagent/config/config.go— configuration structure and loadingagent/docker-compose.yml— integration test environmentagent/Makefile— build, test, and development targets