Objective. Students perform and schedule routine PostgreSQL maintenance tasks including manual and autovacuum tuning, logical backups with pg_dump, and server health monitoring using built-in views.
This lesson, its worked examples and its practice questions has not yet been verified by an industry-certified professional or by a certification or approval body. It is a study draft and may contain errors. Do not use it as instructions for work on a job site or on live equipment. Always follow your instructor, your supervising professional, and current official references and regulations.
VoTechWorks program approval and accreditation are still in progress. Credentials are issued only by the certifying bodies named in each program, after their own exams.
PostgreSQL does not silently clean up after itself the way some database engines do. Two core maintenance operations — VACUUM and ANALYZE — must run regularly, either manually or through the built-in autovacuum daemon. Understanding what each one does, how to tune it, and how to monitor the results is a foundational DBA skill that appears on the EDB PostgreSQL CE and Oracle DBA CA exams alike.
When you UPDATE or DELETE a row in PostgreSQL, the old row version is not immediately removed. It is marked as dead and left in place until VACUUM reclaims the space. These dead tuples waste disk space, bloat indexes, and slow sequential scans.
`VACUUM` alone reclaims dead tuple space and marks pages as reusable. `VACUUM VERBOSE` prints a detailed report showing how many dead tuples were removed per page, which is useful when you are diagnosing bloat. `VACUUM ANALYZE` does both the cleanup pass and a statistics update in one command — usually the better choice for routine maintenance.
The system view pg_stat_user_tables tracks the column `n_dead_tup` (dead tuple count) per table. Check it before and after a VACUUM run to confirm the operation actually reclaimed tuples.
The autovacuum daemon fires automatically when dead tuples exceed a threshold:
> threshold = autovacuum_vacuum_threshold + autovacuum_vacuum_scale_factor × reltuples
For a large table, the default scale factor of 0.2 (20 % of rows) means autovacuum may wait until millions of dead tuples accumulate. Lower the scale factor for high-churn tables. You can override server-wide settings at the individual table level with `ALTER TABLE`:
```sql
ALTER TABLE orders
SET (autovacuum_vacuum_scale_factor = 0.05,
autovacuum_vacuum_cost_delay = 2);
```
`autovacuum_vacuum_cost_delay` (in milliseconds) throttles how aggressively autovacuum uses I/O. A lower value lets it run faster; a higher value protects OLTP workloads from I/O contention.
`ANALYZE` collects column-level statistics — value distributions, most common values, null fractions — and stores them in `pg_statistic`. The query planner uses these statistics to choose join strategies and index paths. Stale statistics after a large bulk load are a common cause of suddenly poor query plans. Running `VACUUM ANALYZE` after any significant data change is good practice.
`pg_dump` exports a single database into a self-contained backup. It is a logical backup — it captures SQL-level objects (tables, indexes, sequences, constraints), not raw disk blocks. Three commonly used output formats are:
| Format flag | Description | Restore tool |
|---|---|---|
| (none / plain) | Plain SQL script | psql |
| `-Fc` (custom) | Compressed, selective restore | pg_restore |
| `-Fd` (directory) | One file per object, parallelizable | pg_restore |
Custom format is the most flexible for production use: it supports parallel restore (`-j` flag), selective object restore, and reordering. Directory format adds the benefit of parallel dump (`-j` on pg_dump as well).
To back up and then restore:
```bash
pg_dump -Fc -d inventory_db -f inventory_db.dump
createdb inventory_restore
pg_restore -Fc -d inventory_restore inventory_db.dump
```
Always verify restores. Use `\dt`, `\di`, or count objects in `information_schema.tables` to confirm row and object counts match.
PostgreSQL exposes rich runtime statistics through the `pg_stat_*` family of views. Four views every DBA should know:
To catch slow queries, enable `log_min_duration_statement` in `postgresql.conf` (for example, set it to `1000` for queries longer than 1 second). This is PostgreSQL's equivalent of MySQL's slow-query log; note that the parameter is `log_min_duration_statement`, not `long_query_time` — that term belongs to MySQL.
Answer each question, then check it. Nothing is recorded; this is your own practice.
A free tech program — complimentary, as our commitment to get America working. Help us build VoTechWorks. Tell us what works, what doesn’t, and what you want to learn.