# psql CLI Options, Variables & Environment Complete reference for psql command-line flags, configuration variables, and environment variables. ## Table of Contents - [CLI Options](#cli-options) - [Connection Parameters](#connection-parameters) - [Input/Output Options](#inputoutput-options) - [Output Format Options](#output-format-options) - [psql Variables](#psql-variables) - [Environment Variables](#environment-variables) - [Configuration Files](#configuration-files) - [Tab Completion](#tab-completion) - [Editor Integration](#editor-integration) --- ## CLI Options ### Synopsis ``` psql [option...] [dbname [user]] ``` When `dbname` is the first non-option argument, it specifies the database. The second non-option argument specifies the user. ### General Options | Flag | Description | |------|-------------| | `-a` / `--echo-all` | Print all nonempty input lines to stdout as they are read. Equivalent to `ECHO=all`. | | `-b` / `--echo-errors` | Print failed SQL commands to stderr. Equivalent to `ECHO=errors`. | | `-c command` / `--command=command` | Execute one or more SQL commands, then exit. Commands can be separated by semicolons. Each `-c` string is sent as a single request — multiple SQL commands within it execute in one transaction (unless explicit `BEGIN`/`COMMIT`). Cannot mix SQL and meta-commands in one `-c`. Returns 0 on success, 1 on error, 2 if connection fails. | | `-d dbname` / `--dbname=dbname` | Database name to connect to | | `-e` / `--echo-queries` | Copy all SQL commands sent to the server to standard output as well | | `-E` / `--echo-hidden` | Echo hidden queries (the SQL generated by \d commands and other meta-commands) to stderr. Useful for learning how psql works internally. | | `-f filename` / `--file=filename` | Execute commands from file, then exit. Use `-` for stdin (reads until EOF or `\q`; Readline not available). `-f` provides line-numbered error messages unlike shell redirection. | | `-F separator` / `--field-separator=separator` | Field separator for unaligned output (default: `|`) | | `-H` / `--html` | HTML output mode | | `-l` / `--list` | List available databases, then exit. Connects to `postgres` database unless a different database is specified via `-d` or a non-option argument. | | `-L filename` / `--log-file=filename` | Log all session output to file | | `-n` / `--no-readline` | Disable enhanced command-line editing and tab completion | | `-o filename` / `--output=filename` | Redirect all query output to file | | `-P assignment` / `--pset=assignment` | Set printing option (format: `option=value`) | | `-q` / `--quiet` | Quiet mode — no startup message, no informational messages | | `-R separator` / `--record-separator=separator` | Record separator for unaligned output (default: newline) | | `-s` / `--single-step` | Single-step mode. Confirm before each command is sent to the server. | | `-S` / `--single-line` | Single-line mode. Newline terminates a query (as if semicolon). Not recommended — execution order can be unclear when mixing SQL and meta-commands on the same line. | | `-t` / `--tuples-only` | Print rows only — no headers, footers | | `-T table_options` / `--table-attr=table_options` | HTML table attributes | | `-v assignment` / `--set=assignment` / `--variable=assignment` | Set psql variable (format: `name=value` sets, `name` unsets, `name=` sets to empty). Assignment happens at command-line processing time, so connection-state variables are overwritten later. | | `-V` / `--version` | Print psql version and exit | | `-w` / `--no-password` | Never issue a password prompt. Fails if password is required. Setting persists for the entire session, including `\connect` attempts. | | `-W` / `--password` | Force password prompt. Setting persists for the entire session, including `\connect` attempts. | | `-x` / `--expanded` | Turn on expanded table output | | `-X` / `--no-psqlrc` | Do not read the startup file (~/.psqlrc) | | `-z` / `--field-separator-zero` | Set field separator to NUL byte | | `-0` / `--record-separator-zero` | Set record separator to NUL byte | | `-1` / `--single-transaction` | Wrap `-f` or `-c` commands in a single transaction. If any command fails, all roll back. Warning: if the script itself contains `BEGIN`/`COMMIT`/`ROLLBACK`, this option will not have the expected effect. | | `-?` / `--help[=topic]` | Show help. `topic` can be `commands` (backslash commands), `options` (CLI options, default), or `variables` (config variables). | | `--csv` | Switch to CSV output mode. Equivalent to `\pset format csv`. | --- ## Connection Parameters These options control how psql connects to PostgreSQL. | Flag | Env Variable | Description | |------|-------------|-------------| | `-h host` | `PGHOST` | Host name or socket directory (default: local socket) | | `-p port` | `PGPORT` | Port number (default: 5432) | | `-U user` | `PGUSER` | Database user name | | `-d dbname` | `PGDATABASE` | Database name | | `-w` | — | Don't prompt for password | | `-W` | — | Force password prompt | **Connection URI:** ``` psql postgresql://user:password@host:5432/dbname?sslmode=require psql postgresql:///dbname?host=/var/run/postgresql ``` **Service lookup:** If `PGSERVICE` or `service=name` in connection string is set, psql reads connection parameters from `pg_service.conf`. --- ## Input/Output Options | Flag | Description | |------|-------------| | `-c command` | Execute command(s) then exit. Multiple commands separated by `;`. | | `-f filename` | Read commands from file then exit. Use `-` for stdin. | | `-1` | Run in a single transaction (only effective with `-c` or `-f`) | | `-a` | Echo all input lines to stdout | | `-b` | Echo failed SQL to stderr | | `-e` | Echo queries to stdout | | `-E` | Echo hidden queries (\d internals) to stderr | | `-L file` | Log all output to file | | `-o file` | Redirect output to file | | `-n` | Disable readline | **Common patterns:** ```bash # Run a migration in a transaction psql -1 -f migration.sql mydb # Execute a single query psql -c "SELECT count(*) FROM users" mydb # Pass a variable from the command line psql -v table=users -c 'SELECT count(*) FROM :"table"' mydb # Batch process with for-loop for f in /tmp/*.sql; do psql -1 -f "$f" mydb; done # Echo internal queries to learn psql psql -E mydb -c "\d+ users" ``` --- ## Output Format Options | Flag | Description | |------|-------------| | `-A` / `--no-align` | Unaligned (delimiter-separated) output | | `-F sep` | Field separator (default: `|`) | | `-H` / `--html` | HTML table output | | `-P opt=val` | Set pset option (e.g., `-P pager=off`) | | `-R sep` | Record separator (default: newline) | | `-t` | Tuples only (no headers/footers) | | `-T attrs` | HTML table attributes | | `-x` | Expanded display | | `-z` / `-0` | NUL separators | **Script-friendly output pattern:** ```bash # CSV output psql --csv -c "SELECT id, name FROM users" mydb # Custom delimiter output psql -A -F ',' -t -c "SELECT id, name FROM users" mydb # NUL-separated for xargs -0 psql -A -z -t -c "SELECT filename FROM files_to_process" mydb | xargs -0 process # JSON-friendly (one value per line) psql -A -t -c "SELECT json_agg(row_to_json(t)) FROM (SELECT id, name FROM users) t" mydb ``` --- ## psql Variables psql maintains internal variables that control behavior. Set with `\set`, unset with `\unset`, view all with `\set` (no arguments). ### Automatic Variables | Variable | Description | |----------|-------------| | `AUTOCOMMIT` | `on` (default) or `off`. When off, psql auto-issues implicit `BEGIN` before any command not in a transaction block (except `BEGIN`/`VACUUM` etc.). You must explicitly `COMMIT` or `ROLLBACK`. | | `COMP_KEYWORD_CASE` | `lower`, `upper`, `preserve-lower` (default), `preserve-upper`. Controls tab-completion keyword casing. `preserve-lower`/`preserve-upper` preserves case of already-typed input; empty input completes as lower/upper case. | | `DBNAME` | Current database name. Set automatically on connect. | | `ECHO` | `none` (default), `all`, `queries`, `errors`. Controls what gets echoed. `all` echoes all commands (including scripts). `queries` echoes only SQL queries, not meta-commands. `errors` echoes failed SQL commands to stderr (set by `-b`). | | `ECHO_HIDDEN` | `off`, `on`, `noexec`. When `on`, shows hidden queries (SQL behind \d commands). `noexec` shows them without executing. | | `ENCODING` | Current client encoding. Set automatically. | | `ERROR` | `true` if the last query failed, `false` otherwise. | | `FETCH_COUNT` | Integer (default: 0). When set, psql fetches rows in batches of this size instead of all at once. Useful for large result sets. | | `HIDE_TABLEAM` | If set, hide table access methods in `\d+` output. | | `HIDE_TOAST_COMPRESSION` | If set, hide compression method in `\d+` output. | | `HISTCONTROL` | `none` (default), `ignorespace`, `ignoredups`, `ignoreboth`. Controls history saving. | | `HISTFILE` | Path to history file (default: `~/.psql_history`). Can include psql variable references, e.g. `\set HISTFILE ~/.psql_history-:DBNAME`. | | `HISTSIZE` | Maximum number of history entries (default: 500). A negative value disables the limit. | | `HOST` | Current server host. Set automatically on connect. | | `IGNOREEOF` | If set, prevents Ctrl-D from exiting. Value is the number of EOFs to ignore before quitting. | | `LAST_ERROR_MESSAGE` | Error message from the last failed query. | | `LAST_ERROR_SQLSTATE` | SQLSTATE error code from the last failed query (`00000` if no error). | | `LASTOID` | OID of the last affected row by `INSERT` or `\lo_import`. Always 0 for PG 12+ tables (OID column removed). | | `ON_ERROR_ROLLBACK` | `off` (default), `on`, `interactive`. When `on`, errors inside a transaction create savepoints automatically, allowing continued execution. `interactive` only activates in interactive sessions, not when reading scripts. | | `ON_ERROR_STOP` | `off` (default) or `on`. When `on`, a query error or meta-command error stops script execution and exits. Critical for safe scripting. | | `PIPELINE_COMMAND_COUNT` | Number of queued commands in current pipeline. | | `PIPELINE_RESULT_COUNT` | Number of commands with pending results in current pipeline. | | `PIPELINE_SYNC_COUNT` | Number of queued sync messages in current pipeline. | | `PORT` | Current server port. Set automatically on connect. | | `PROMPT1`, `PROMPT2`, `PROMPT3` | Prompt format strings (see below). | | `QUIET` | `on` or `off`. Quiet mode. | | `ROW_COUNT` | Number of rows affected by the last query. | | `SERVER_VERSION_NAME` | Server version string. | | `SERVER_VERSION_NUM` | Server version as integer (e.g., 160000 for 16.0). | | `SERVICE` | Service name from the connection, if applicable. | | `SHELL_ERROR` | `true` if the last shell command (`\!`, `\g`, `\o`, `\w`, `\copy`, backquote) failed, `false` otherwise. | | `SHELL_EXIT_CODE` | Exit code of the last shell command (0-127 normal exit, 128-255 signal termination, -1 launch failure). | | `SHOW_ALL_RESULTS` | `on` (default) or `off`. When on, show all results from combined queries. | | `SHOW_CONTEXT` | `never`, `errors`, `always`. Controls display of `CONTEXT:` in messages. Default: `errors`. | | `SINGLELINE` | `on` or `off`. Newline acts as query terminator. | | `SINGLESTEP` | `on` or `off`. Confirm before each command. | | `SQLSTATE` | SQLSTATE error code from the last query. | | `USER` | Current database user. Set automatically on connect. | | `VERSION` | psql client full version string. | | `VERSION_NAME` | psql client short version (e.g., `18beta1`). | | `VERSION_NUM` | psql client version as integer (e.g., `180000`). | | `WATCH_INTERVAL` | Default interval (seconds) for `\watch` command (default: 2). | | `VERBOSITY` | `default`, `verbose`, `terse`, `sqlstate`. Controls error message detail level. | ### SQL Interpolation psql variables can be interpolated into SQL statements using colon-prefixed syntax. This is **plain text substitution**, not parameterized queries — understand the differences to use it safely. | Syntax | Behavior | Example | |--------|----------|---------| | `:varname` | Unquoted substitution. The variable's value replaces `:varname` literally, which can break SQL syntax or enable injection if the value contains special characters. | `\set table users` → `SELECT * FROM :table;` → `SELECT * FROM users;` | | `:'varname'` | Single-quoted string substitution. The value is placed inside single quotes, with any embedded single quotes and backslashes escaped. This is the safest form for values. | `\set name O'Brien` → `SELECT * FROM users WHERE name = :'name';` → `SELECT * FROM users WHERE name = 'O''Brien';` | | `:"varname"` | Double-quoted identifier substitution. The value is placed inside double quotes, with embedded double quotes doubled. Use this for table/column names. | `\set col first name` → `SELECT :"col" FROM users;` → `SELECT "first name" FROM users;` | | `:{?varname}` | Variable existence test. Always expands — `TRUE` if defined, `FALSE` otherwise. Designed for use in `\if` conditions. | `\if :{?myvar}` → true if `myvar` was set | | `\:varname` | Escaped colon. The colon is not treated as a variable reference — `:varname` is passed through literally. | `SELECT \:not_a_var FROM t;` → `SELECT :not_a_var FROM t;` | Note: Variable interpolation does NOT occur inside quoted SQL literals or identifiers. Therefore `':foo'` does not produce a quoted string from the variable (and wouldn't be safe even if it did — it can't handle embedded quotes properly). Use `:'foo'` instead. **Safety guidance**: Always prefer `:'varname'` (quoted string) over `:varname` (unquoted) when substituting user-provided values. Unquoted substitution can break SQL syntax or enable injection. For the safest programmatic parameter passing, use `\bind` with the extended query protocol (which provides true parameterized queries). ### Key Variables for Scripting **ON_ERROR_STOP** — The most important variable for scripts. Set it in scripts to ensure they abort on the first error instead of continuing: ``` -- At the top of any script: \set ON_ERROR_STOP on -- Now any error stops execution INSERT INTO users (id) VALUES (1); INSERT INTO users (id) VALUES ('bad'); -- aborts here INSERT INTO users (id) VALUES (2); -- never reached ``` **AUTOCOMMIT** — Turn off to manually manage transactions: ``` \set AUTOCOMMIT off UPDATE accounts SET balance = balance - 100 WHERE id = 1; UPDATE accounts SET balance = balance + 100 WHERE id = 2; COMMIT; \set AUTOCOMMIT on ``` **FETCH_COUNT** — For very large result sets that would consume too much memory: ``` \set FETCH_COUNT 1000 SELECT * FROM huge_table; ``` **ERROR / SQLSTATE / LAST_ERROR_MESSAGE** — For conditional logic: ``` INSERT INTO unique_table (id) VALUES (1); \if :ERROR \echo 'Insert failed: ' :LAST_ERROR_MESSAGE \else \echo 'Insert succeeded, rows affected: ' :ROW_COUNT \endif ``` ### Prompt Customization `PROMPT1` is the normal prompt (default: `'%/%R%x%# '`). `PROMPT2` appears when a command is incomplete (continuation) (default: `'%/%R%x%# '`). `PROMPT3` appears during `COPY FROM STDIN` when row values are needed (default: `'>> '`). **Format specifiers:** | Spec | Output | |------|--------| | `%/` | Current database name | | `%~` | Like `%/` but `~` if the database is your default database | | `%m` | Host name (truncated at first dot), or `[local]` for Unix sockets | | `%M` | Full host name, `[local:/dir/name]` for non-default Unix sockets | | `%>` | Port number | | `%n` | User name | | `%s` | Service name (from connection) | | `%#` | `#` if superuser, `>` otherwise | | `%p` | Process ID of the server backend | | `%R` | PROMPT1: `=` normally, `^` in single-line mode, `@` if conditional stack inactive (e.g., inside skipped `\if`), `!` if not connected. PROMPT2: `-` (continuation), `*` (comment), `'` (single-quoted), `"` (double-quoted), `$` (dollar-quoted), `(` (parenthesized). PROMPT3: empty. | | `%w` | Whitespace matching the visible width of the last PROMPT1 output (for aligning PROMPT2) | | `%x` | Transaction status: empty (idle), `*` (in transaction block), `!` (failed transaction), `?` (unknown or no connection) | | `%l` | Line number inside the current statement, starting from 1 | | `%P` | Pipeline status: `on` (pipeline mode active), `off` (not in pipeline mode), `abort` (pipeline aborted) | | `%%` | Literal `%` | | `%` digits | Character with the given octal code (e.g., `%033` = ESC character) | | `%:varname:` | Value of psql variable | | `` %`[command]` `` | Output of shell command (trailing newline stripped) | | `%[ ... %]` | Tell Readline that the contained text is invisible (for ANSI escape codes) | **Common prompt configurations:** ``` -- Show database and user \set PROMPT1 '%n@%m %/%R%# ' -- Show transaction status \set PROMPT1 '%/%x%# ' -- Production-safe prompt (color-coded) -- Note: %033 is octal for ESC character; %[...%] tells Readline these chars are invisible \set PROMPT1 '%[%033[1;31m%]%/%[%033[0m%]%R%# ' ``` --- ## Environment Variables | Variable | Description | |----------|-------------| | `PGDATABASE` | Default database name | | `PGHOST` | Default host (or socket directory) | | `PGPORT` | Default port (5432) | | `PGUSER` | Default user | | `PGPASSWORD` | Password (not recommended — use `~/.pgpass` instead) | | `PGPASSFILE` | Path to password file (default: `~/.pgpass`) | | `PGSERVICE` | Service name from `pg_service.conf` | | `PGSERVICEFILE` | Path to service file | | `PGOPTIONS` | Default options to pass to the server | | `PGSSLMODE` | SSL mode (`disable`, `allow`, `prefer`, `require`, `verify-ca`, `verify-full`) | | `PGREQUIRESSL` | Legacy SSL flag (use `PGSSLMODE` instead) | | `PGSSLCERT` | Client certificate path | | `PGSSLKEY` | Client key path | | `PGSSLROOTCERT` | Root certificate path | | `PGSSLCRL` | Certificate revocation list path | | `PGREQUIREPEER` | Require peer username for Unix socket connections | | `PGKRBSRVNAME` | Kerberos service name | | `PGGSSLIB` | GSS library to use | | `PGCONNECT_TIMEOUT` | Connection timeout in seconds | | `PGCLIENTENCODING` | Client encoding (overrides auto-detected locale setting) | | `PGDATESTYLE` | Date display format | | `PGTZ` | Time zone | | `PGSYSCONFDIR` | System config directory | | `PG_COLOR` | Color output (`auto`, `always`, `never`) | | `COLUMNS` | When `\pset columns` is 0, controls `wrapped` format width and the threshold for activating pager or switching to expanded auto mode | | `PSQL_EDITOR` | Editor for `\e`, `\ef`, `\ev`. Takes precedence over `EDITOR` and `VISUAL`. | | `PSQL_EDITOR_LINENUMBER_ARG` | Command-line argument for passing line numbers to the editor (default: `+`). E.g., set to `--line ` for editors that use `--line N` syntax. | | `PSQL_HISTORY` | Alternative history file path (overrides `HISTFILE`) | | `PSQLRC` | Alternative `.psqlrc` location | | `PSQL_PAGER` | Pager command (overrides `PAGER`) | | `PSQL_WATCH_PAGER` | Pager command specifically for `\watch` output (overrides `PSQL_PAGER` and `PAGER` when set). Unix only. | | `EDITOR` / `VISUAL` | Editor for `\e`, `\ef`, `\ev` (checked after `PSQL_EDITOR`) | | `SHELL` | Shell for `\!` | | `TMPDIR` | Temp directory for temp files | | `LANG` | Locale (affects sorting, number formatting) | ### The ~/.pgpass File Store passwords securely instead of using `PGPASSWORD`: ``` # Format: hostname:port:database:username:password # Use * as wildcard localhost:5432:mydb:myuser:YOUR_PASSWORD *:5432:*:admin:YOUR_PASSWORD ``` Permissions must be 0600: `chmod 600 ~/.pgpass` --- ## Configuration Files ### ~/.psqlrc Executed on every interactive psql startup (unless `-X` is used). Perfect for personal customizations: ```sql -- ~/.psqlrc example \set ON_ERROR_STOP on \timing on \pset null '(null)' -- Custom prompt showing database and transaction status \set PROMPT1 '%n@%m %/%x%# ' -- Shortcuts \set HISTSIZE 10000 \set HISTCONTROL ignoredups -- Show how long queries took \echo 'Welcome to' :DBNAME ``` ### Version-specific psqlrc Append `-` and the version number for version-specific configuration. psql reads the most specific match: - `~/.psqlrc-18` — applies for psql 18.x - `~/.psqlrc-18.3` — applies specifically for psql 18.3 - System-level: `psqlrc-18` in the `pg_config --sysconfdir` directory ### System-wide psqlrc System-level psql configuration at `pg_config --sysconfdir`/psqlrc (use `PGSYSCONFDIR` to override). Applied before user `~/.psqlrc`. ### Windows paths On Windows, user config is at `%APPDATA%\postgresql\psqlrc.conf` and history at `%APPDATA%\postgresql\psql_history`. --- ## Tab Completion psql provides intelligent tab completion for: - SQL keywords - Table, view, and column names - Function names and arguments - Schema-qualified names - `\d` command patterns Tab completion sends queries to the server to fetch metadata. This can interfere with operations: e.g., after `BEGIN`, a tab completion query means `SET TRANSACTION ISOLATION LEVEL` is too late. To disable tab completion permanently, add to `~/.inputrc`: ``` $if psql set disable-completion on $endif ``` Or use `-n` to disable for a single session. --- ## Editor Integration `\e`, `\ef`, and `\ev` use the editor specified by: 1. `PSQL_EDITOR` environment variable (highest priority) 2. `EDITOR` environment variable 3. `VISUAL` environment variable 4. Default: `vi` (Unix), `notepad.exe` (Windows) Use `PSQL_EDITOR_LINENUMBER_ARG` to control how line numbers are passed (default: `+`). **Useful editor settings:** ```bash export EDITOR='vim' # or for VS Code: export EDITOR='code --wait' # or for nano: export EDITOR='nano' ```