SSH tunnels
When the database is only reachable from inside a private network, connect through an SSH server that is: a bastion host. Alcuin opens the tunnel itself; you do not need to run ssh -L first.
Set up a tunnel
Section titled “Set up a tunnel”-
Open the connection’s form and fill in Host, Port, Database and User as the bastion sees the database. Host is resolved by the SSH server, so a private name such as
db.internalworks. -
Beside Connect through SSH, click Set up.
-
Fill in the SSH fields:
Field What it takes SSH host The bastion’s name or address SSH port Its SSH port, 22 by default SSH user Your user on the bastion SSH authentication SSH agent, Private key file or Password -
Click Test connection. The steps start with SSH tunnel.
-
The first time, Alcuin stops at the bastion’s host key. Check it and click Trust this key, as below.
-
Click Save.
On success, Test connection says through the SSH tunnel. Turn the tunnel off again with Turn off.
Sign in to the bastion
Section titled “Sign in to the bastion”SSH agent
Section titled “SSH agent”The default. Alcuin uses the agent that SSH_AUTH_SOCK names in the environment Alcuin started with. If none is set, the test fails with no SSH agent is running (SSH_AUTH_SOCK is not set).
A variable set only in your shell’s startup files, such as ~/.zshrc, does not reach an app started from the Dock, Finder or a desktop launcher. That matters for agents such as 1Password’s: Alcuin uses one only when SSH_AUTH_SOCK in its own environment points at that agent’s socket.
Private key file
Section titled “Private key file”Set Key path, or click Choose…. Alcuin reads OpenSSH, PEM and PuTTY private keys. If the key has a passphrase, enter it in Key passphrase. Alcuin keeps it encrypted with your system keychain.
~/ at the start of the path is your home folder. Alcuin refuses a file that is not a private key, with that file is not an SSH private key, and never shows its contents.
Password
Section titled “Password”Enter SSH password. Alcuin keeps it in your keychain.
Host keys
Section titled “Host keys”Before it sends the bastion any password, passphrase or agent signature, Alcuin checks that the bastion is the server you trusted.
It trusts a key when:
- the connection’s settings hold it as Trusted server key, or
~/.ssh/known_hostslists it for the same host and port. Hashed entries count.
The first time, neither holds, and Test connection stops with the key’s fingerprint and a Trust this key button. Compare the fingerprint with the one the bastion’s owner gives you before you trust it. ALC-1003: Unknown SSH host key has the steps.

The first time: compare the fingerprint, then Trust this key.
If the bastion presents a different key from the one trusted, Alcuin refuses to connect and offers Trust the new key. Find out why the key changed first. ALC-1004: SSH host key changed lists the harmless causes and the one that matters.

A changed key: find out why before you choose Trust the new key.
To stop trusting a key, click Forget beside Trusted server key and save. To read keys from another file than ~/.ssh/known_hosts, start Alcuin with ALCUIN_SSH_KNOWN_HOSTS set to its path.
A saved password is kept with the key it was saved under. If the trusted key changes, Alcuin asks before it sends a saved password over the tunnel.
What Alcuin does not read
Section titled “What Alcuin does not read”Alcuin doesn’t read ~/.ssh/config, so Host aliases, User, Port, IdentityFile and ProxyJump lines are not used: enter the real host name, user, port and key in the form. A tunnel goes through one SSH server. Not supported yet lists what else Alcuin doesn’t do.
Through a jump host
Section titled “Through a jump host”For a chain of SSH servers, run the forward in a terminal and point Alcuin at it:
ssh -N -J jump.example.com -L 15432:db.internal:5432 bastion.example.comThen set Host to localhost, Port to 15432, and leave Connect through SSH off. The certificate names the database host, not localhost, so use Required, verify certificate if the server has TLS.
Encryption through the tunnel
Section titled “Encryption through the tunnel”The tunnel encrypts the hop to the bastion. The hop from the bastion to the database is only encrypted by Postgres’s own TLS, so keep Encryption on where the server offers it. Required, verify server works through Alcuin’s tunnel, because the host name is checked against Host as you typed it. See TLS and sslmode.
Keepalives and dropped tunnels
Section titled “Keepalives and dropped tunnels”Alcuin sends the bastion a keepalive every 15 seconds and closes the tunnel after three go unanswered. It waits 15 seconds for the SSH handshake, and 15 seconds for the bastion to open a channel to the database.
When the tunnel drops, the connection drops with it: you see Connection lost. Reconnecting…, and Alcuin opens a new tunnel when it reconnects. Your tabs stay. See ALC-1002: Connection lost.
If the tunnel does not open
Section titled “If the tunnel does not open”Test connection names the step Couldn't open the SSH tunnel. Try ssh -p <port> <user>@<host> from a terminal: if that fails too, fix SSH access first. Connection errors by message has each message and its fix:
- The bastion refused your key, agent or password:
All configured authentication methods failed. - The bastion didn’t answer:
Timed out while waiting for handshake. - The bastion can’t reach Host and Port:
the SSH server could not reach db.internal:5432. - An unknown or changed host key: SSH host key not known or changed.