Before you begin
Terraform reads AWS credentials from the environment, so select a profile with
AWS_PROFILE rather than a command line flag. If AWS_ACCESS_KEY_ID is exported it takes priority over AWS_PROFILE, so run unset AWS_ACCESS_KEY_ID AWS_SECRET_ACCESS_KEY AWS_SESSION_TOKEN first.Two prerequisites Terraform will not change for you
Both carry consequences for a running database, so they stay yours to make. Terraform checks them and tells you, and never edits them.IAM database authentication
Required for the agent to authenticate without a password. It is a dynamic change and needs no reboot:aws_db_instance data source does not expose the flag at all. Check it yourself:
The parameter group
Database Monitoring reads its query data frompg_stat_statements, and a few
parameters control how much of it you get. Set these in your RDS or Aurora
parameter group, or in postgresql.conf on a self hosted server:
The two marked static do nothing until the database is restarted. The rest
take effect on the next parameter group refresh.
Check what is actually running:
pg_stat_statements, so
check before you plan any downtime.
This is the failure that looks like success.
CREATE EXTENSION pg_stat_statements succeeds whether or not the library is loaded, so a parameter group edited without a reboot gives you an agent that connects, reports metrics, and shows an empty query list, with nothing saying why. The agent host checks the running value at boot and writes a notice to its journal if it is missing.Get the Terraform
Store the license key
Keeping the key in Parameter Store means it never lands inuser_data, in a saved plan file, or in state:
Configure
A PostgreSQL only setup, withdocumentdb_clusters left empty:
Monitoring several databases
databases is a map, and one agent host collects from every entry. There is no reason to run this stack twice for two databases in the same VPC:
aws block, so each token is signed for its own endpoint, and its own rds-db:connect policy, because the resource id differs per database. Databases that share a security group and port share one ingress rule.
The map key names the database in the UI, which matters once one agent reports several of them.
Create the database role
The agent authenticates as a PostgreSQL role that has to exist before it starts. There are two ways to create it.Automatically, at first boot
Point the entry at an SSM parameter holding the database master password and the agent host creates the role itself. The host is inside the VPC, so it reaches a database with no public access, which your laptop cannot:CREATE ROLE, GRANT pg_monitor, CREATE EXTENSION pg_stat_statements, GRANT rds_iam, and creates the atatus schema and the atatus.explain_statement() function that execution plans need. Every statement is guarded, so a rebuilt host re-runs all of it without error, and the rds_iam grant is skipped on a server that has no such role.
By hand
Connect as your master user and run the bootstrap SQL once per cluster:atatus schema and the atatus.explain_statement() function, which is what the agent calls to collect execution plans. Both are per database, so run it in every database you want plans from.
If your database has no public access, your laptop cannot reach it. Tunnel through the agent host with Session Manager, or use the automatic path above:
Apply
Verify
Monitoring both engines from one host
The agent readsconf.d/postgresql.d/ and conf.d/mongodb.d/ independently, so one machine covers PostgreSQL and Amazon DocumentDB together. Add a documentdb_clusters map alongside databases:
Removing it
atatus role and the SSM parameters are not Terraform’s and stay behind:
Keep the role if you plan to redeploy. It holds
rds_iam, dropping it is the only way to undo that grant, and you would have to recreate and re grant on the next run.