caduh

A Simple Guide to SSH Keys — generate & use keys for secure server access

3 min read

Step-by-step: create an SSH key, add it to a server, use ssh-agent, set up ~/.ssh/config, and harden your SSH settings. Works on macOS, Linux, and Windows.

TL;DR

  • Generate a keypair (public + private). Share the public key; never share the private key.
  • Put the public key in the server’s ~/.ssh/authorized_keys, then connect with ssh user@host.
  • Use ed25519 keys by default; use rsa‑4096 only for legacy systems.
  • Protect the private key with a passphrase and load it into ssh‑agent.
  • Harden servers: disable password auth and root SSH, use firewall + fail2ban.

1) Generate a keypair

Recommended (Ed25519):

ssh-keygen -t ed25519 -C "[email protected]"
# Saves to: ~/.ssh/id_ed25519 (private) and ~/.ssh/id_ed25519.pub (public)
# Choose a strong passphrase when prompted

Legacy compatibility (RSA 4096, with modern key derivation):

ssh-keygen -t rsa -b 4096 -o -a 100 -C "[email protected]"
# Files: ~/.ssh/id_rsa and ~/.ssh/id_rsa.pub

Private key (id_ed25519 / id_rsa) stays on your machine. Public key (.pub) can be shared/pasted on servers and dev platforms.


2) Install your public key on the server

Quick way (macOS/Linux):

ssh-copy-id [email protected]

Manual way (works everywhere):

# On your laptop
cat ~/.ssh/id_ed25519.pub

# On the server (as target user)
mkdir -p ~/.ssh
chmod 700 ~/.ssh
echo "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAI.... [email protected]" >> ~/.ssh/authorized_keys
chmod 600 ~/.ssh/authorized_keys

Windows paths: keys live in C:\Users\<you>\.ssh\.
Permissions (PowerShell):

icacls $HOME\.ssh\id_ed25519 /inheritance:r
icacls $HOME\.ssh\id_ed25519 /grant:r "$($env:USERNAME):(R)"

3) Connect

ssh [email protected]
# custom port
ssh -p 2222 [email protected]
# specify identity explicitly
ssh -i ~/.ssh/id_ed25519 [email protected]

Increase verbosity when debugging:

ssh -vvv [email protected]

4) Use ssh‑agent (no passphrase prompts every time)

macOS/Linux (bash/zsh):

eval "$(ssh-agent -s)"
ssh-add ~/.ssh/id_ed25519
# list loaded keys
ssh-add -l

Windows 10+ (PowerShell, built‑in OpenSSH):

Start-Service ssh-agent
Get-Service ssh-agent
ssh-add $env:USERPROFILE\.ssh\id_ed25519

On macOS, keys can be stored in the Keychain (ssh-add --apple-use-keychain ~/.ssh/id_ed25519).


5) Make aliases with ~/.ssh/config

Create ~/.ssh/config (permissions 600) and add hosts:

Host prod
  HostName server.example.com
  User ubuntu
  Port 22
  IdentityFile ~/.ssh/id_ed25519
  IdentitiesOnly yes
  AddKeysToAgent yes
  ForwardAgent no

Host db
  HostName 10.0.2.15
  User postgres
  ProxyJump prod

Now connect with:

ssh prod
ssh db   # jumps through 'prod'

6) Use SSH keys with Git (GitHub/GitLab)

Test:

ssh -T [email protected]
# or
ssh -T [email protected]

Set remote:

git remote set-url origin [email protected]:yourname/yourrepo.git

Add your public key (.pub) in the platform’s SSH Keys settings.


7) Server hardening (must‑do basics)

Edit /etc/ssh/sshd_config (as root) and set:

PubkeyAuthentication yes
PasswordAuthentication no
PermitRootLogin no
ChallengeResponseAuthentication no
UsePAM yes

Then reload:

sudo systemctl reload sshd   # some distros: ssh

Important: keep an existing SSH session open while testing, so you don’t lock yourself out.

Firewall & abuse protection:

# Ubuntu example
sudo ufw allow 22/tcp
sudo ufw enable

# Optional: fail2ban
sudo apt install fail2ban

8) Rotate & revoke keys

  • Generate a new keypair and add it to all servers/services.
  • Remove the old public keys from authorized_keys.
  • If a private key leaks, revoke immediately and rotate credentials (and audit logs).

Common errors & quick fixes

| Symptom | Likely cause | Fix | |---|---|---| | Permission denied (publickey) | Public key not on server or wrong user/path | Ensure key is in ~/.ssh/authorized_keys for the right user; correct perms 700 ~/.ssh, 600 authorized_keys | | “Permissions are too open” | Private key mode too permissive | chmod 600 ~/.ssh/id_ed25519 (and 700 ~/.ssh) | | “Too many authentication failures” | Agent has many keys; server gives up | ssh -o IdentitiesOnly=yes -i ~/.ssh/id_ed25519 host or set in config | | “Host key verification failed” | Server’s fingerprint changed | Verify change is legitimate; update ~/.ssh/known_hosts | | Can’t use ed25519 on old boxes | Old OpenSSH/OpenSSL | Generate RSA‑4096 and use that key for legacy hosts |


Quick checklist

  • [ ] Use ed25519 with a passphrase; store via ssh‑agent.
  • [ ] Add public key to ~/.ssh/authorized_keys with correct permissions.
  • [ ] Create ~/.ssh/config aliases; prefer IdentitiesOnly yes.
  • [ ] Disable password auth and root SSH on servers.
  • [ ] Keep a firewall on; consider fail2ban.
  • [ ] Rotate keys periodically and after any suspicion of compromise.

One‑minute setup plan

  1. ssh-keygen -t ed25519 -C "[email protected]" → set passphrase.
  2. ssh-copy-id user@server (or paste .pub to authorized_keys).
  3. eval "$(ssh-agent -s)" && ssh-add ~/.ssh/id_ed25519.
  4. Create ~/.ssh/config with an alias and IdentitiesOnly yes.
  5. Harden server (PasswordAuthentication no, PermitRootLogin no) and test.