How to Fix SSH “Permission Denied (publickey)” Errors

Are you struggling with SSH connection issues? The dreaded “Permission Denied (publickey)” error is one of the most common roadblocks when using SSH to connect to remote Linux servers.

This comprehensive guide walks you through proven troubleshooting steps to resolve SSH key authentication problems, based on real-world experience managing Linux systems.

Understanding How SSH Public Key Authentication Works

Before diving into solutions, it’s essential to understand the underlying mechanisms of SSH public key authentication:

  1. Key Pair Generation: You create a cryptographic key pair consisting of:
    • A private key (kept secret on your local machine)
    • A public key (placed on remote servers you want to access)
  2. Authentication Process:
    • When connecting, your SSH client presents your identity using the public key
    • The server creates a challenge that only your private key can solve
    • Your client uses your private key to respond to the challenge
    • If successful, the server grants access without requiring a password

Read: How to use scp command in Linux to transfer files securely using ssh

Step-by-Step SSH Key Authentication Troubleshooting

1. Verifying Basic SSH Key Setup

Generate a Proper SSH Key Pair

If you haven’t created keys yet, or suspect your keys might be problematic:

ssh-keygen -t rsa -b 4096 -C "your_email@example.com"
  • -t rsa: Specifies RSA encryption (widely supported)
  • -b 4096: Creates a 4096-bit key for enhanced security
  • -C "your_email@example.com": Adds an identifying comment

You’ll be prompted to choose a file location (default: ~/.ssh/id_rsa) and an optional passphrase (recommended for security).

Deploy Your Public Key to the Remote Server

The most straightforward method is using the ssh-copy-id utility:

ssh-copy-id username@remote_server_ip

This command automatically appends your public key to the ~/.ssh/authorized_keys file on the remote server.

If ssh-copy-id isn’t available on your system, manually transfer your public key:

scp ~/.ssh/id_rsa.pub username@remote_server_ip:~/.ssh/uploaded_key.pub
ssh username@remote_server_ip "mkdir -p ~/.ssh && cat ~/uploaded_key.pub >> ~/.ssh/authorized_keys && rm ~/uploaded_key.pub"

Test Your Connection

Try connecting with verbose output to see what’s happening:

ssh -v username@remote_server_ip

2. Fixing SSH File Permissions (Most Common Solution)

SSH is extremely sensitive about file permissions for security reasons. Incorrect permissions are the #1 cause of “Permission Denied (publickey)” errors.

On the Remote Server

Connect using password authentication temporarily and run:

chmod 700 ~/.ssh
chmod 600 ~/.ssh/authorized_keys

These commands ensure:

  • Only you can access your .ssh directory (permission 700)
  • Only you can read/write the authorized_keys file (permission 600)

On Your Local Machine

Similarly, check permissions on your local machine:

chmod 700 ~/.ssh
chmod 600 ~/.ssh/id_rsa

3. Checking SSH Server Configuration Settings

The SSH server’s configuration can prevent key authentication if not properly set.

Verify Server SSH Configuration

On the remote server, examine the SSH daemon configuration:

sudo nano /etc/ssh/sshd_config

Ensure these critical settings are properly configured:

PubkeyAuthentication yes
AuthorizedKeysFile .ssh/authorized_keys
PasswordAuthentication yes  # Keep this enabled until your key auth works!

If you made changes, restart the SSH service:

sudo systemctl restart sshd  # For systemd-based systems
# OR
sudo service ssh restart     # For older init-based systems

4. Resolving SELinux or AppArmor Security Contexts

Security frameworks like SELinux and AppArmor can block SSH key authentication by restricting file access.

Checking SELinux Status

Determine if SELinux is enforcing restrictions:

getenforce

If it returns “Enforcing,” temporarily set it to permissive mode to test:

sudo setenforce 0  # Temporarily disable enforcement
# After testing, re-enable with:
sudo setenforce 1

If key authentication suddenly works, you need to adjust SELinux policies rather than disabling it.

Checking AppArmor Status

Similarly, check if AppArmor might be interfering:

sudo apparmor_status

Look for profiles related to SSH in the output.

5. Advanced Debugging with Verbose SSH Output

For difficult cases, use increased verbosity to pinpoint exactly where authentication fails:

ssh -vvv username@remote_server_ip

This provides detailed logs of the entire connection process. Look specifically for:

  • Lines containing “Offering public key”
  • Messages about “Server refused our key”
  • Authentication methods being attempted

6. Verifying authorized_keys File Format and Content

Ensure your public key is properly formatted in the authorized_keys file:

cat ~/.ssh/authorized_keys

Each key should:

  • Appear on a single line
  • Start with key type (e.g., ssh-rsa)
  • Contain the key data without line breaks
  • Optionally end with a comment

7. Checking User Home Directory Configuration

SSH requires the user’s home directory to be properly set and accessible:

echo $HOME
ls -la ~

Ensure:

  • The home directory exists
  • You have proper permissions to access it
  • The .ssh directory is located within it

8. Ensuring Firewall Access for SSH Connections

Make sure firewalls aren’t blocking SSH traffic (typically port 22):

# On Ubuntu/Debian:
sudo ufw status
sudo ufw allow ssh

# On CentOS/RHEL:
sudo firewall-cmd --list-all
sudo firewall-cmd --permanent --add-service=ssh
sudo firewall-cmd --reload

Common SSH Authentication Pitfalls to Avoid

  1. Using the Wrong Key Pair: Verify you’re using the private key that corresponds to the public key on the server
  2. Incorrect Username or Hostname: Double-check both are spelled correctly
  3. Line Break Issues: Ensure public keys are copied without extra line breaks
  4. Permission Changes After Setup: System updates can sometimes reset permissions
  5. Using sudo When Running SSH: Avoid using sudo ssh as it uses root’s SSH configuration
  6. Mixing Key Types: If you specified -t ed25519 but the server only supports RSA, authentication will fail

Advanced SSH Security Best Practices

Once key authentication is working, consider these security enhancements:

  1. Disable Password Authentication only after confirming key authentication works:
    PasswordAuthentication no
    
  2. Restrict Root Login for improved security:
    PermitRootLogin prohibit-password  # Allow root login with key only
    # OR
    PermitRootLogin no  # Completely disable root login (recommended)
    
  3. Use SSH Config Files to simplify connections: Create ~/.ssh/config with entries like:
    Host myserver
        HostName server.example.com
        User myusername
        IdentityFile ~/.ssh/special_id_rsa
        Port 2222
    

    Then simply connect with ssh myserver

  4. Consider Key Authentication Agents like ssh-agent to avoid typing your passphrase repeatedly

The “Permission Denied (publickey)” error can be frustrating, but with this systematic troubleshooting approach, you can identify and resolve the issue quickly. Public key authentication provides significantly better security than passwords and is worth the initial setup effort for any system administrator or developer working with remote Linux servers.


If you like the content, we would appreciate your support by buying us a coffee. Thank you so much for your visit and support.

 

Leave a Reply