>_ SSHDock
FeaturesHow it worksBlogGuidesPricing
Launch Terminal
Back to Journal

Git over SSH: how to use SSH with GitHub, GitLab, and Bitbucket

Ayan Hussain
Sep 12, 2026 · 8 min read

Quick Answer: Git over SSH uses key-based authentication instead of passwords. Generate an SSH key pair, add the public key to your GitHub/GitLab/Bitbucket account, and clone repositories using the git@github.com:username/repo.git format. After setup, every git push and git pull runs without prompting for credentials.


When you clone a repository using HTTPS, Git asks for your credentials on every push. Since GitHub removed password authentication in 2021, HTTPS now requires a Personal Access Token — which is just another credential to manage, store securely, and rotate when it expires.

SSH authentication solves this permanently. You generate a key pair once, add the public key to your account, and from that point on git push just works.

SSH vs HTTPS for Git: quick comparison

| | SSH | HTTPS | |---|---|---| | Authentication | Private key (stored locally) | Password or Personal Access Token | | Credential prompts | None after setup | Every push (unless cached) | | Setup effort | One-time, ~5 minutes | Immediate, but token management ongoing | | Firewall issues | Port 22 may be blocked on some networks | Port 443, almost never blocked | | Multiple accounts | Easy with ~/.ssh/config | Awkward with credential managers | | Recommended for | Daily development work | CI/CD pipelines, read-only cloning |

The short version: use SSH for day-to-day development. Use HTTPS tokens for automated pipelines where you cannot use key files.

Step 1: Generate an SSH key pair

If you already have an Ed25519 key at ~/.ssh/id_ed25519, you can reuse it. To create a dedicated key for Git services (recommended if you want separate keys per service):

macOS / Linux:

ssh-keygen -t ed25519 -C "your_email@example.com" -f ~/.ssh/github-key

Windows (PowerShell or Git Bash):

ssh-keygen -t ed25519 -C "your_email@example.com" -f "$env:USERPROFILE\.ssh\github-key"

This creates two files:

  • github-key — your private key. Never share this. Never copy it to a remote server.
  • github-key.pub — your public key. This goes on the hosting service.

Use Ed25519 rather than RSA. It produces smaller keys, signs faster, and avoids the SHA-1 deprecation issue that breaks old RSA keys on modern OpenSSH servers. See our RSA vs Ed25519 comparison for the full breakdown.

Step 2: Add the public key to your account

GitHub

Copy your public key to the clipboard:

macOS:

cat ~/.ssh/github-key.pub | pbcopy

Linux:

cat ~/.ssh/github-key.pub | xclip -selection clipboard
# or
cat ~/.ssh/github-key.pub | xsel --clipboard --input

Windows (PowerShell):

Get-Content "$env:USERPROFILE\.ssh\github-key.pub" | Set-Clipboard

Then:

  1. Go to github.com → profile picture → Settings
  2. Click SSH and GPG keys in the left sidebar
  3. Click New SSH key
  4. Give it a descriptive title (e.g. "MacBook Pro 2026" or "Work Windows Laptop")
  5. Paste the public key → click Add SSH key

GitLab

  1. Go to gitlab.com → profile picture → Preferences
  2. Click SSH Keys in the left sidebar
  3. Paste the public key, optionally set an expiry date → click Add key

Bitbucket

  1. Go to bitbucket.org → profile picture → Personal settings
  2. Click SSH keys under Security
  3. Click Add key → paste the public key → click Add key

Step 3: Test the connection

Before cloning anything, verify the key works:

# GitHub
ssh -T git@github.com

# GitLab
ssh -T git@gitlab.com

# Bitbucket
ssh -T git@bitbucket.org

GitHub responds with:

Hi username! You've successfully authenticated, but GitHub does not provide shell access.

The "does not provide shell access" message is expected. You are authenticated as the git system user — the hosting service maps your key to your account.

If you get "Permission denied (publickey)", see the troubleshooting section below.

Step 4: Configure SSH to use your key

If you named your key file something other than the default (id_ed25519), add this to ~/.ssh/config so SSH knows which file to use:

macOS / Linux — edit ~/.ssh/config:

Host github.com
  HostName github.com
  User git
  IdentityFile ~/.ssh/github-key
  AddKeysToAgent yes

Windows — edit C:\Users\YourName\.ssh\config (create it if it doesn't exist):

Host github.com
  HostName github.com
  User git
  IdentityFile C:/Users/YourName/.ssh/github-key

On Windows, use forward slashes in the IdentityFile path even though Windows normally uses backslashes. The OpenSSH client on Windows handles this correctly.

Step 5: Clone using SSH

On GitHub, click the Code button on any repository, switch from HTTPS to SSH, and copy the URL. The format is:

git clone git@github.com:username/repository.git

For an existing repository cloned via HTTPS, update the remote URL:

git remote set-url origin git@github.com:username/repository.git
git remote -v  # verify the change

Using the SSH agent

If your private key has a passphrase (it should), your system will ask for it the first time you use the key in each session. The SSH agent caches the decrypted key in memory so you only enter the passphrase once.

macOS / Linux:

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

On macOS, add this to ~/.ssh/config to persist across reboots:

Host github.com
  HostName github.com
  User git
  IdentityFile ~/.ssh/github-key
  AddKeysToAgent yes
  UseKeychain yes

UseKeychain yes stores the passphrase in the macOS Keychain. On Linux, add ssh-add ~/.ssh/github-key to your ~/.bashrc or ~/.zshrc so the key loads on every terminal session.

Windows: The OpenSSH Authentication Agent service handles this. Start it once in PowerShell as admin, then add your key:

# Enable and start the agent service
Set-Service -Name ssh-agent -StartupType Automatic
Start-Service ssh-agent

# Add your key
ssh-add "$env:USERPROFILE\.ssh\github-key"

After this, Windows automatically uses the agent across sessions without re-prompting for the passphrase.

Managing multiple GitHub accounts

A common scenario: a personal GitHub account and a work GitHub account, each needing its own SSH key. SSH always sends one default key, so without configuration it will authenticate to whichever account that key belongs to.

Step 1: Generate two separate keys:

ssh-keygen -t ed25519 -C "personal@email.com" -f ~/.ssh/github-personal
ssh-keygen -t ed25519 -C "work@company.com"   -f ~/.ssh/github-work

Step 2: Add each public key to the corresponding GitHub account.

Step 3: Create aliases in ~/.ssh/config:

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

Host github-work
  HostName github.com
  User git
  IdentityFile ~/.ssh/github-work

Step 4: Use the alias when cloning:

# Personal repository
git clone git@github-personal:your-personal-username/repo.git

# Work repository
git clone git@github-work:your-work-org/repo.git

Step 5: For existing repositories, update the remote:

git remote set-url origin git@github-personal:your-username/repo.git

SSH sees github-personal in the URL, looks it up in ~/.ssh/config, and uses ~/.ssh/github-personal as the key. Both accounts work from the same machine without interfering with each other.

Complete working config for GitHub + GitLab + multiple accounts

# Personal GitHub
Host github-personal
  HostName github.com
  User git
  IdentityFile ~/.ssh/github-personal
  AddKeysToAgent yes

# Work GitHub
Host github-work
  HostName github.com
  User git
  IdentityFile ~/.ssh/github-work
  AddKeysToAgent yes

# GitLab
Host gitlab.com
  HostName gitlab.com
  User git
  IdentityFile ~/.ssh/gitlab-key
  AddKeysToAgent yes

# Self-hosted GitLab at your company
Host git.company.com
  HostName git.company.com
  User git
  IdentityFile ~/.ssh/company-gitlab-key
  Port 22

# Global defaults
Host *
  ServerAliveInterval 60
  AddKeysToAgent yes

Switching all existing repos from HTTPS to SSH

To update all local repositories in a directory from HTTPS to SSH at once:

find . -name ".git" -type d | while read gitdir; do
  repo="$(dirname "$gitdir")"
  cd "$repo"
  current=$(git remote get-url origin 2>/dev/null)
  if [[ "$current" == https://github.com/* ]]; then
    new="${current/https:\/\/github.com\//git@github.com:}"
    git remote set-url origin "$new"
    echo "Updated: $repo → $new"
  fi
  cd - > /dev/null
done

Run this from a parent directory containing multiple cloned repositories. It only modifies GitHub HTTPS remotes — adjust the pattern for GitLab or Bitbucket if needed.

Troubleshooting

"Permission denied (publickey)"

This is the most common error. Work through this checklist:

1. Check the key is added to your account. On GitHub: Settings → SSH keys. Make sure the key fingerprint matches your local key:

ssh-keygen -lf ~/.ssh/github-key.pub

2. Check SSH is trying the right key.

ssh -vv git@github.com 2>&1 | grep -i "identity\|offer\|auth"

If SSH is not trying the key you expect, your ~/.ssh/config may be missing or using the wrong IdentityFile path.

3. Check the SSH agent has the key loaded.

ssh-add -l

If the output says "The agent has no identities", add your key: ssh-add ~/.ssh/github-key.

4. Check file permissions (macOS/Linux).

chmod 700 ~/.ssh
chmod 600 ~/.ssh/github-key
chmod 644 ~/.ssh/github-key.pub

If permissions are too open, SSH silently ignores the key.

"Warning: Permanently added 'github.com' to the list of known hosts"

Normal — SSH stores the server's fingerprint in ~/.ssh/known_hosts the first time you connect to detect future changes.

"Host key verification failed"

GitHub occasionally rotates its SSH host keys. If your ~/.ssh/known_hosts has an old fingerprint, you will see this error. Remove the old entry and reconnect:

ssh-keygen -R github.com
ssh -T git@github.com  # accept the new fingerprint

Always verify the new fingerprint against the official list published by the service before accepting.

SSH on port 443 (when port 22 is blocked)

Some corporate firewalls block port 22. GitHub supports SSH over port 443 as a fallback:

Host github.com
  HostName ssh.github.com
  User git
  Port 443
  IdentityFile ~/.ssh/github-key

This connects to ssh.github.com:443 which behaves identically to github.com:22 from Git's perspective.

AH
Written by
Ayan Hussain

Full-Stack Developer and creator of SSHDock. Ayan builds browser-based developer tools and writes about SSH security, Linux server management, and modern web engineering.

More about the author →GitHub
SSHDOCK

Full terminal in your browser. Local credential storage, jump host tunneling, live CPU/memory/disk metrics, and a mobile soft-key bar. Free to use. Built by developers, for developers.

© 2026 SSHDock

GitHub (@ayanhackss)
App
Launch TerminalFeaturesHow it worksBlog & TutorialsChangelogGuides
Cloud Guides
AWS EC2DigitalOcean DropletGoogle Cloud Compute EngineMicrosoft Azure Virtual MachineLinode Compute InstanceVultr Cloud Compute
Legal & Contact
Privacy PolicyTerms of ServiceDisclaimerContact UsAbout Creator
Modern, minimal browser SSH client
TerminalSitemap