pg_write_all_data#
What is pg_write_all_data?#
pg_write_all_data allows a role to write (INSERT, UPDATE, DELETE, TRUNCATE) to ALL tables in ALL schemas in a database — without owning them.
- In plain words:
“I can modify every table’s data, even if it’s not mine.”
This is one of the most powerful non-superuser roles in PostgreSQL.
What this role ALLOWS#
A role with pg_write_all_data can:
- Data modification (EVERYWHERE)
INSERT into any table
UPDATE any row
DELETE any row
TRUNCATE any table
- Across:
All schemas
All tables
All databases it can connect to
- Even if:
The table owner is different
Explicit privileges were never granted
What it does NOT allow#
Capability |
Allowed |
|---|---|
Read table data |
❌ (needs pg_read_all_data) |
Change table structure |
❌ |
Drop tables |
❌ |
Execute OS commands |
❌ |
Read/write server files |
❌ |
This role is write-only, not read or admin.
Mental model
pg_write_all_data = “Universal data editor”
- Think:
Global UPDATE access
Global DELETE access
Data corruption potential
Why this role is dangerous#
Accidental damage
DELETE FROM orders;
→ wipes all orders, even if you don’t own the table.
- Bypasses permission design
Ignores schema-based isolation
Breaks multi-tenant safety if misused
- Audit nightmare
Hard to track which app/user modified what
🔐 Security level#
🔴 HIGH RISK
Environment |
Recommendation |
|---|---|
Production |
❌ Avoid |
Development |
⚠️ Temporary only |
Debugging |
⚠️ Short-lived |
Admin tasks |
❌ Prefer ownership |
Real-world usage (VERY LIMITED)#
- Sometimes used for:
Emergency data correction
DBA hotfix scripts
Data migration tools (short-lived)
- Never for:
App users
API services
Background workers
BI tools
Relationship with other roles
Role |
Capability |
|---|---|
pg_read_all_data |
Read everything |
pg_write_all_data |
Write everything |
pg_monitor |
Observe |
superuser |
Everything |
Read + Write = almost superuser-level damage potential
Example
UPDATE customers SET balance = 0;
- Even if:
You didn’t create the table
You weren’t granted privileges
Schema is locked down
Best practice (IMPORTANT)
❌ Do NOT do this
GRANT pg_write_all_data TO app_user;
✅ Do this instead
GRANT INSERT, UPDATE, DELETE
ON ALL TABLES IN SCHEMA public
TO app_user;
- Or even better:
Use schema ownership
Use role-based schema isolation
Use migrations for changes
Grant / Revoke
GRANT pg_write_all_data TO dangerous_user;
Revoke immediately after use:
REVOKE pg_write_all_data FROM dangerous_user;
Summary
Feature |
Value |
|---|---|
Write any table |
✅ |
Bypass ownership |
✅ |
Safe for apps |
❌ |
Production use |
🚫 |
Risk level |
🔴 VERY HIGH |
Big picture (critical insight)
pg_write_all_data destroys the principle of least privilege.
- If you’re designing:
Multi-tenant systems
Enterprise schemas
Secure APIs
Never use this role