SSH tunnel troubleshooting
Use the Test Connection button on the connection card to run a preflight check before provisioning. Most SSH problems are caught here before any build is started.
Common errors
Section titled “Common errors”ssh: handshake failed: ssh: unable to authenticate
Section titled “ssh: handshake failed: ssh: unable to authenticate”The bastion accepted the TCP connection but rejected the SSH key.
Causes and fixes:
| Cause | Fix |
|---|---|
| Wrong key uploaded | Verify you uploaded the private key, not the public key |
| Key has a passphrase | Strip the passphrase: ssh-keygen -p -f your_key and re-upload |
| Key not authorised on the bastion | Add the corresponding public key to ~/.ssh/authorized_keys on the bastion for the SSH user |
| Wrong SSH user | Check the username — it must match the account on the bastion host |
dial tcp: connection refused or i/o timeout
Section titled “dial tcp: connection refused or i/o timeout”The bastion host is unreachable.
Causes and fixes:
| Cause | Fix |
|---|---|
| Wrong bastion host or port | Double-check the hostname/IP and port (default: 22) |
| Firewall blocking inbound SSH | Add an inbound rule allowing TCP port 22 from the ReflexDB NAT IP (see below) |
| Bastion is stopped or terminated | Start the bastion host |
mysql: connection refused or unknown host
Section titled “mysql: connection refused or unknown host”The SSH tunnel is established but the MySQL server is unreachable from inside the bastion.
Causes and fixes:
| Cause | Fix |
|---|---|
| Wrong MySQL host/port | Use the internal hostname of the MySQL server as seen from the bastion, not the public hostname |
| MySQL not listening on the given port | Verify netstat -tlnp on the MySQL host shows port 3306 (or your custom port) |
| Security group blocks bastion → MySQL | Allow TCP 3306 from the bastion’s private IP in the MySQL security group |
mysql: Access denied for user
Section titled “mysql: Access denied for user”The tunnel is working but the MySQL credentials are wrong.
Fix: Verify the MySQL username and password, and confirm the user has SELECT (and REPLICATION CLIENT for binlog mode) on the target database from the bastion’s IP or subnet.
Firewall requirements
Section titled “Firewall requirements”ReflexDB connects from a fixed NAT IP per region. Add this IP to your bastion’s inbound SSH security group:
| Region | NAT IP |
|---|---|
| eu-west-1 (Ireland) | Contact support@reflexdb.cloud |
| us-east-1 (Virginia) | Contact support@reflexdb.cloud |
Key format requirements
Section titled “Key format requirements”ReflexDB accepts OpenSSH-format private keys only.
Supported key types: Ed25519 (recommended), RSA (2048+ bits), ECDSA (P-256, P-384)
Generate a new key:
# Ed25519 (recommended)ssh-keygen -t ed25519 -f reflexdb_key -N ""
# RSA (4096-bit)ssh-keygen -t rsa -b 4096 -f reflexdb_key -N ""The -N "" flag sets an empty passphrase. Upload the private key file (reflexdb_key, no extension); keep reflexdb_key.pub for the bastion’s authorized_keys.
Strip a passphrase from an existing key:
ssh-keygen -p -f reflexdb_key# When prompted for "New passphrase", press Enter to leave it emptyTesting the tunnel manually
Section titled “Testing the tunnel manually”To verify the tunnel works before configuring ReflexDB, test from a machine that can reach your bastion:
# Test SSH connectivity to the bastionssh -i reflexdb_key -p 22 <ssh-user>@<bastion-host> echo "SSH OK"
# Test MySQL connectivity through the tunnelssh -i reflexdb_key -N -L 3307:<mysql-host>:3306 <ssh-user>@<bastion-host> &mysql -h 127.0.0.1 -P 3307 -u <mysql-user> -p <database>If the SSH step fails, fix that first before troubleshooting MySQL.
Still stuck?
Section titled “Still stuck?”Contact support@reflexdb.cloud with:
- The error message from Test Connection
- Your bastion host (hostname only, no credentials)
- Your database ID (visible in the dashboard URL)