Run it on your machine
The command-line checkup is the whole checkup, run from your own computer: every check, the findings read together, and what to fix first, why, and how. Your connection string and password never reach pgcheckup.com. Nothing is uploaded unless you run the upload command yourself.
npx pg-checkup@latest postgres://[email protected]/app
npx downloads and runs it without installing. To keep it: npm install -g pg-checkup, then run pg-checkup instead. Needs Node 18 or newer.
In a project directory with DATABASE_URL in .env or .env.local, as Prisma and Drizzle projects have, npx pg-checkup with no arguments uses it and says so. Otherwise it connects the same ways psql does: a URL, -h HOST -p PORT -U USER -d DBNAME, --service NAME, or the PGHOST, PGUSER, PGDATABASE and PGSERVICE variables. The password comes from the URL, PGPASSWORD, the service file, ~/.pgpass, or a hidden prompt.
The login it expects
Run these statements as your database administrator:
create role checkup_reader login password 'choose-a-password';
grant pg_monitor to checkup_reader;
-- Some hosts keep extensions in their own schema (Supabase: "extensions"). This grants usage only if that schema exists.
do $$ begin if exists (select 1 from pg_namespace where nspname = 'extensions') then execute 'grant usage on schema extensions to checkup_reader'; end if; end $$;
If the login can read application tables, or is a superuser, the checkup stops before reading anything and prints these statements. --allow-privileged-role overrides that. The check covers effective privileges in the connected database, including what PUBLIC grants.
What it prints and saves
Findings grouped as fix now, fix next, watch and safe to ignore, each with why it matters and what to do. When one finding causes another, the cause is listed first with a note, for example an idle transaction before the dead rows it is holding in place. Then the count of checks that passed, and the ones that could not run and why. -v lists every check.
The saved file holds statistics, settings, and schema and role names. It never holds table rows or the connection string. SQL text is left out unless you pass --include-query-text. Files are created with mode 0600 and never overwritten.
npx pg-checkup doctor # how it would connect and what the login can do, then stop
npx pg-checkup show FILE # run the checkup again on a saved file
npx pg-checkup show FILE --all # every collected row
npx pg-checkup sql # every query the checkup runs
A database on localhost can be checked with any login. A remote database needs the statistics-only login above; --allow-privileged-role overrides that.
The shareable report and the fix SQL
To share the findings, upload the saved file:
npx pg-checkup upload FILE
The command shows what is in the file and asks before sending it. It sends that file and nothing else. The server returns the file's hash, which the CLI compares, and a receipt. npx pg-checkup delete RECEIPT removes the report. Free reports are kept for 7 days; anyone with the link can read them.
The web report shows every finding, why it matters and the fix, and opens only for you. Free accounts keep reports for 30 days; anonymous reports last 7 days.
Workspace ($12 a month) adds the SQL to review, comparison with an earlier checkup, PDF, a share link, scheduled uploads with a token, and email alerts. File-size and rate limits still apply. Reports retained during your paid period remain available after cancellation. Create a token in Settings → Billing and set PGCHECKUP_TOKEN to save CLI uploads to your account. Paystack renews Workspace monthly; cancel from “Manage Subscription” in your Paystack email. Our pricing promise.
Send it to the page that is waiting
On pgcheckup.com/scan the page shows one command that ends in --send CODE. Run it and the page opens your report when the checkup finishes: no file to find and no upload step. --send counts as your consent to upload, so it does not ask. The code works once and expires after 15 minutes. Without --send, the command saves a file and asks before uploading anything.
Scripts and CI
--json: the statistics and findings as JSON on stdout; messages on stderr.--md: the report as Markdown on stdout, for a wiki page or a pull request.--fail-on critical|warning|info: exit 1 when such a finding exists. Without it a completed checkup exits 0.-o FILE: choose the file name. An existing file is never overwritten.--no-input: no prompts.-wnever asks for a password.--provider generic|supabase|neon: override host detection behind a tunnel.- Exit code 3 means a remote login had more access than a checkup needs.