Fix 'Permission denied (publickey)' with Git and SSH
git clone or push fails with Permission denied (publickey) — how do I fix my SSH key?
If you’re seeing this error
git@github.com: Permission denied (publickey).fatal: Could not read from remote repository.You’re in the right place — the fix is below.
Short answer
The server didn't accept any key your SSH client offered. Either you have no key, the key isn't loaded into the agent, or its public half was never added to your account. Run ssh -T git@github.com to see exactly which keys are being tried.
ssh -T git@github.com
Tests your SSH setup and names the exact problem
Does this match your situation?
- 'git@github.com: Permission denied (publickey).'
- 'fatal: Could not read from remote repository.'
- Cloning over HTTPS works but SSH doesn't.
- It worked on your old machine but not the new one.
Step-by-step fix
Test the connection directly
This bypasses Git entirely and tells you whether SSH authentication itself works. A successful result greets you by username; anything else is the real error.
step 1ssh -T git@github.com # success: "Hi username! You've successfully authenticated..." # see exactly which keys get offered: ssh -vT git@github.comCheck whether you actually have a key
A new machine has no keys at all. If the directory is empty or missing, generate one — ed25519 is the modern default.
step 2ls -al ~/.ssh # nothing there? create one: ssh-keygen -t ed25519 -C "you@example.com"Show the PowerShell (Windows) version
PowerShell (Windows)Get-ChildItem $env:USERPROFILE\.ssh ssh-keygen -t ed25519 -C "you@example.com"Load the key into the SSH agent
A key on disk that the agent doesn't know about is never offered. On Windows the agent service is disabled by default and has to be started first.
step 3eval "$(ssh-agent -s)" ssh-add ~/.ssh/id_ed25519 ssh-add -l # confirm it is loadedShow the PowerShell (Windows, as Admin) version
PowerShell (Windows, as Admin)Set-Service ssh-agent -StartupType Automatic Start-Service ssh-agent ssh-add $env:USERPROFILE\.ssh\id_ed25519 ssh-add -lAdd the PUBLIC key to your account
Copy the contents of the .pub file — never the private key, which has no extension — and paste it into your host's SSH keys settings.
step 4cat ~/.ssh/id_ed25519.pub # paste at: # GitHub -> github.com/settings/keys # GitLab -> gitlab.com/-/user_settings/ssh_keysOnly ever share the .pub file. The file without .pub is your private key and must never leave the machine.
Fix permissions if SSH still refuses
OpenSSH ignores keys whose files are readable by other users. On Unix-like systems this is a very common cause after copying keys between machines.
step 5chmod 700 ~/.ssh chmod 600 ~/.ssh/id_ed25519 chmod 644 ~/.ssh/id_ed25519.pub
Why this works
SSH public-key authentication works by the client proving it holds the private key matching a public key the server already trusts. Three separate things must line up: the key pair must exist, the client must actually offer that key (which usually means the agent has it loaded), and the server must have the public half on your account. 'Permission denied (publickey)' means the handshake finished without any offered key matching — which is why the verbose output, showing exactly which keys were tried, is the fastest diagnosis.
If that didn’t work
- Multiple accounts or hosts? Add a Host block in ~/.ssh/config with an explicit IdentityFile.
- Corporate network blocking port 22? Use ssh.github.com on port 443 via ~/.ssh/config.
- For an organisation repo, the key may need SSO authorisation in your account settings.
- Confirm the remote URL is the SSH form (git@host:user/repo.git), not HTTPS.
How to stop it happening again
- Back up ~/.ssh securely, or accept generating a fresh key per machine (which is arguably better practice).
- Add every machine's public key to your account as you set it up.
- Use ~/.ssh/config to pin the right key per host so nothing depends on agent ordering.
Commands used in this guide
Still stuck?
Search the full command reference and every other rescue guide — there are 76 of them, covering everything from detached HEAD to force-push disasters.
Browse all guides →Frequently asked questions
What does 'Permission denied (publickey)' mean?
The SSH server rejected every key your client offered. Either no key was offered at all, or the ones offered aren't registered on your account. It's an authentication failure, not a repository permission problem.
Which file do I paste into GitHub — id_ed25519 or id_ed25519.pub?
The .pub one, always. That's the public half and is safe to share. The file without .pub is your private key; if it ever leaves your machine, delete the key pair and generate a new one.
How do I use different SSH keys for work and personal accounts?
Create a ~/.ssh/config with a Host block per identity — for example Host github-work with its own HostName github.com and IdentityFile — then use git@github-work:org/repo.git as the remote URL so the right key is always chosen.
Related rescue guides
Git keeps saying authentication failed even though my password is correct — why?
GitHub stopped accepting account passwords over HTTPS in August 2021. You need a personal access token in place of the password, or better, switch the remote to SSH. If it worked yesterday, a cached old credential is usually the culprit — clear it and re-authenticate.
Read the fix →Always fixableGit says 'Repository not found' but the URL is definitely right — why?
On a private repository, GitHub returns 'not found' rather than 'access denied' — so this usually means you are authenticated as the wrong account, not that the repository is missing. Check who you are with ssh -T git@github.com, and clear any stale credential your helper is replaying.
Read the fix →Always fixablegit commit fails with 'error: gpg failed to sign the data' — how do I fix commit signing?
Test the signing outside Git first: echo test | gpg --clearsign. 'Inappropriate ioctl for device' means the passphrase prompt has nowhere to draw — add export GPG_TTY=$(tty) to your shell profile. 'No secret key' means user.signingkey does not match a key you hold. If you just want to commit right now, git commit --no-gpg-sign gets you through.
Read the fix →Always fixableHow do I make Git remember my credentials?
Configure a credential helper that stores the token in your OS keychain, or switch to SSH keys and skip credentials entirely. Avoid the `store` helper — it writes your token to a plaintext file.
Read the fix →