GitHub no longer accepts account passwords for Git operations over HTTPS. You either use a personal access token, or — more convenient for daily work — SSH keys. On servers, deploy keys give one machine access to one repository without using anybody’s personal account.

1. Generate a key

On your computer:

ssh-keygen -t ed25519 -C "[email protected]"

Accept the default path (~/.ssh/id_ed25519) or name it (~/.ssh/id_ed25519_github), and set a passphrase. Load it into your agent so you type the passphrase once per session:

eval "$(ssh-agent -s)"
ssh-add ~/.ssh/id_ed25519

More about keys: ssh-keygen guide.

2. Add the public key to GitHub

cat ~/.ssh/id_ed25519.pub

GitHub → Settings → SSH and GPG keys → New SSH key, paste it, choose “Authentication key”. (You can add the same key again as a “Signing key” to sign commits.)

3. Test

ssh -T [email protected]
Hi alice! You've successfully authenticated, but GitHub does not provide shell access.

The first time, verify that the host key fingerprint matches the one GitHub publishes in its documentation before typing yes.

4. Use SSH URLs

git clone [email protected]:org/repo.git

Switch an existing clone from HTTPS:

git remote set-url origin [email protected]:org/repo.git
git remote -v

Port 22 blocked?

Some networks block outbound SSH. GitHub accepts SSH on port 443 at ssh.github.com:

# ~/.ssh/config
Host github.com
    HostName ssh.github.com
    Port 443
    User git

Several GitHub accounts

Use host aliases with separate keys:

Host github-personal
    HostName github.com
    User git
    IdentityFile ~/.ssh/id_ed25519_personal
    IdentitiesOnly yes

Host github-work
    HostName github.com
    User git
    IdentityFile ~/.ssh/id_ed25519_work
    IdentitiesOnly yes
git clone git@github-work:company/app.git

Set the matching commit email per repository: git config user.email [email protected]. See the SSH config file guide.

Deploy keys for servers

A server that pulls code (for git pull deployments) shouldn’t use your personal key — if the server is compromised, so is access to everything you can reach. Use a deploy key instead: an SSH key tied to a single repository, read-only by default.

On the server, as the deploy user:

ssh-keygen -t ed25519 -f ~/.ssh/deploy_myapp -N "" -C "deploy@web1 myapp"
cat ~/.ssh/deploy_myapp.pub

GitHub → repository → Settings → Deploy keys → Add deploy key, paste it, leave Allow write access unchecked.

Configure SSH to use it for this repository:

# ~/.ssh/config on the server
Host github-myapp
    HostName github.com
    User git
    IdentityFile ~/.ssh/deploy_myapp
    IdentitiesOnly yes
git clone git@github-myapp:org/myapp.git /var/www/myapp

Each deploy key works for exactly one repository; with several repositories, create one key each (and one host alias each). For organisations with many repositories and servers, a GitHub App or a machine user with fine-grained access may be easier to manage.

Troubleshooting

ssh -vT [email protected]
  • Permission denied (publickey) — the key isn’t loaded (ssh-add -l), isn’t on GitHub, or SSH is offering a different key; use IdentitiesOnly yes. See SSH Permission denied (publickey).
  • Key is already in use when adding a deploy key — a key can only be attached once on GitHub; generate a separate key.
  • ERROR: Repository not found — the key works but has no access to that repository (wrong account, or the deploy key belongs to another repo).

Other platforms

GitLab, Gitea and Bitbucket work the same way: add your public key to your profile, use deploy keys for servers. Self-hosting? See Gitea.

Next: deploying to a VPS with GitHub Actions.

  • Git
  • GitHub
  • SSH