Linter for dangerous Postgres migration patterns in Diesel and SQLx. Prevents downtime caused by unsafe schema changes.
✓ Detects operations that lock tables or cause downtime
✓ Provides safe alternatives for each blocking operation
✓ Works with both Diesel and SQLx migration frameworks
✓ Supports safety-assured blocks for verified operations
✓ Extensible with custom checks
Uses PostgreSQL's own parser. diesel-guard embeds libpg_query — the C library compiled into Postgres itself. What diesel-guard flags is exactly what Postgres sees. If your SQL has a syntax error, diesel-guard reports that too.
Scriptable custom checks. Write project-specific rules in Rhai with full access to the SQL AST. No forking required.
Version-aware. Configure postgres_version to suppress checks that don't apply
to your version (e.g., constant defaults are safe on PG 11+).
No database connection required. Works on SQL files directly — no running Postgres instance needed in CI.
Via Cargo:
cargo install diesel-guardVia Homebrew:
brew install ayarotsky/tap/diesel-guardVia shell script (macOS/Linux):
curl --proto '=https' --tlsv1.2 -LsSf https://github.com/ayarotsky/diesel-guard/releases/latest/download/diesel-guard-installer.sh | shVia PowerShell (Windows):
powershell -ExecutionPolicy Bypass -c "irm https://github.com/ayarotsky/diesel-guard/releases/latest/download/diesel-guard-installer.ps1 | iex"Via pre-commit:
repos:
- repo: https://github.com/ayarotsky/diesel-guard
rev: v0.8.0
hooks:
- id: diesel-guarddiesel-guard init # creates diesel-guard.toml
diesel-guard check # checks ./migrations/ by defaultWhen it finds an unsafe migration:
❌ Unsafe migration detected in migrations/20240101_add_admin/up.sql
❌ ADD COLUMN with DEFAULT
Problem:
Adding column 'admin' with DEFAULT on table 'users' requires a full table
rewrite on Postgres < 11, acquiring an ACCESS EXCLUSIVE lock.
Safe alternative:
1. Add the column without a default:
ALTER TABLE users ADD COLUMN admin BOOLEAN;
2. Backfill data in batches (outside migration):
UPDATE users SET admin = false WHERE admin IS NULL;
3. Add default for new rows only:
ALTER TABLE users ALTER COLUMN admin SET DEFAULT false;
Add to your GitHub Actions workflow:
- uses: actions/checkout@v6
- uses: ayarotsky/diesel-guard-action@v1Pin the diesel-guard binary version for reproducible builds:
- uses: ayarotsky/diesel-guard-action@v1
with:
version: '0.10.0'Built-in checks cover locking, rewrites, and schema safety. See the full list of checks.
When you've reviewed an operation and confirmed it's safe, wrap it in a safety-assured block to suppress the check:
-- safety-assured:start
ALTER TABLE users DROP COLUMN legacy_field;
-- safety-assured:end- Your Diesel Migrations Might Be Ticking Time Bombs
- Postgres Locks Explained
- Zero-downtime Postgres migrations: the hard parts
- Zero-downtime Postgres migrations: a little help
- Seven tips for dealing with Postgres locks
- Move fast and migrate things: how we automated migrations in Postgres
- PostgreSQL at scale: database schema changes without downtime
- PostgreSQL Explicit Locking
- Adding a Scripting Engine to a Rust CLI with Rhai
Inspired by strong_migrations by Andrew Kane.
If this looks useful, a star helps more developers find it ⭐
