
Now that pgpro-otel-collector has had its public release, I’m excited to start sharing more about the tool — and to kick things off, I’m launching a blog series focused entirely on the Collector.
In this series, I’ll dive deeper into how the collector works, walk through hands-on examples, and explore real-world use cases. Along the way, I’ll also touch on broader topics around Postgres monitoring and configuration.
The content should be especially useful for Linux admins, PostgreSQL DBAs, and anyone looking to step up their Postgres monitoring game.
The first post is an intro — a practical guide to installing, configuring, and launching the collector. We’ll also take our first look at what kind of data the collector exposes, starting with good old Postgres metrics.
What you’ll need
To follow along, you’ll need:
A running PostgreSQL instance — either a VM or a Docker container will do. We'll install the collector there and wire it up to pull metrics from Postgres.
Prometheus + Grafana — I personally prefer spinning these up via Docker Compose, but you can use whatever you're comfortable with (VMs, bare metal, etc.).
I’ll assume you’re already familiar with spinning up VMs or containers, so I won’t go into setup boilerplate. In my case, I’m using a VM deployed through our internal automation system.
Installing the Collector
The installation is pretty straightforward. We’ll grab the repository setup script from Postgres Pro and install the collector via your package manager. For Debian-based systems, here’s how it goes:
wget https://repo.postgrespro.ru/otelcol/otelcol/keys/pgpro-repo-add.sh
sudo sh ./pgpro-repo-add.sh
sudo apt install pgpro-otel-collector
Creating a dedicated DB user
While technically optional (especially in a test setup), it’s best practice to create a dedicated database user for monitoring. Assign the pg_monitor role so the Collector can access all the necessary system views.
sudo -u postgres createuser --member-of=pg_monitor --pwprompt otelcol
Verify that the user can connect:
sudo -u postgres psql -U otelcol -d postgres -c 'select version()'
version
-------------------------------------------------------------------------------------------
PostgreSQL 17.2 on x86_64-pc-linux-gnu, compiled by gcc (Debian 12.2.0-14) 12.2.0, 64-bit
If you hit connection errors, it probably means you need to tweak your pg_hba.conf and reload the config. The official docs have the details related to installing pg_hba.conf .
Configuring the Collector
The config lives in /etc/pgpro-otel-collector/basic.yml. You’ll need to set up:
Connection info for your Postgres instance.
A list of plugins (i.e., which metrics to collect).
Example connection config:
receivers:
postgrespro:
transport: tcp
endpoint: localhost:5432
database: postgres
username: otelcol
password: secret_password
Now let’s talk plugins. The collector comes with a basic set enabled out of the box (activity, locks, WAL stats, etc.). You can expand this by enabling additional plugins. Here’s a snippet with a few extras turned on:
plugins:
activity:
enabled: true
bgwriter:
enabled: true
databases:
enabled: true
io:
enabled: true
locks:
enabled: true
version:
enabled: true
wal:
enabled: true
cache:
enabled: true
Be mindful when enabling all plugins — metric collection isn’t free. It’ll cost you in terms of DB load and Prometheus storage. Be smart about what you really need to track.
You can find the full list of plugins in the collector’s docs. There are also sample configs under /usr/share/doc/pgpro-otel-collector/examples/.
Starting the Collector
Once everything’s configured, fire it up with:
sudo systemctl start pgpro-otel-collector.service
Check the service status:
pgpro-otel-collector.service - PostgresPro OpenTelemetry Collector
Loaded: loaded (/lib/systemd/system/pgpro-otel-collector.service; disabled; preset: enabled)
Active: active (running) since Mon 2025-02-17 19:52:00 MSK; 10h ago
Main PID: 25501 (pgpro-otel-coll)
Tasks: 7 (limit: 3512)
Memory: 14.3M
CPU: 15.942s
CGroup: /system.slice/pgpro-otel-collector.service
└─25501 /usr/bin/pgpro-otel-collector --config /etc/pgpro-otel-collector/basic.yml
Look for active (running) and keep an eye out for any errors in the logs — especially around DB connectivity.
Let’s make sure the collector is doing its thing. It exposes metrics on port 8889 in Prometheus format. You can check the endpoint with:
curl -s 127.0.0.1:8889/metrics | grep -c HELP
This should return the number of metric types exposed. In my case, I saw 49. Want to see the full list? Just remove the grep and scroll through — there are around 200 lines of raw metric goodness.
Hooking it up to Prometheus
Here’s a barebones Prometheus config:
scrape_configs:
- job_name: "pgpro-otel-collector"
static_configs:
- targets: ["localhost:8889"]
If Prometheus and the collector are on different hosts, update the target accordingly. Don’t forget to reload Prometheus after making config changes. Once that's done, metrics will start flowing, and you can explore them via Prometheus' UI or Grafana (via Explore or pre-built dashboards).
Here are a few key metrics to look for:
postgresql_activity_connections — active DB connections
postgresql_activity_wait_events — current wait events
postgresql_locks_all — lock details
postgresql_cache_hit_ratio — cache hit stats
postgresql_io_read_bytes_total / ...write_bytes_total — I/O metrics
postgresql_wal_bytes_total — WAL write volume
Sample dashboards & queries
Connections by State
sum by (state) (postgresql_activity_connections)

Total Connections Over Time
Track how many are idle, active, or stuck in limbo.
sum by (type) (postgresql_activity_wait_events{type!~"Activity|Client|Extension|Timeout"})

This helps isolate expensive wait types like IO and heavyweight locks.
Read/Write IO per Instance
sum(rate(postgresql_io_read_bytes_total{instance="$instance"}))
sum(rate(postgresql_io_write_bytes_total{instance="$instance"}))

Use Grafana variables or just hardcode the instance you want to inspect.
Total WAL Write Volume
sum(rate(postgresql_wal_bytes_total))

Great for benchmarking or diagnosing WAL-heavy operations.
That’s it for now! We’ve gone through the essentials of setting up pgpro-otel-collector, wiring it to Postgres, and pulling some real metrics out. As you can see, it’s pretty painless to get started — and incredibly powerful once it's up.
But this is just the beginning. There’s more to this collector than just metrics, and in future posts, I’ll cover other features and advanced use cases.
Thanks for reading — and stay tuned!
Let me know if you'd like a shorter version for social media sharing, or a follow-up post template!