🔒 Local-only generation
All key generation, import, and encryption happens in your browser via Web Crypto and pure-JS primitives. Imported files are read locally, never uploaded. Close the tab and every key in memory is gone forever.
📥 Import existing key (optional)
Drop key file here! Drag in an OpenSSH or PuTTY .ppk key
or
Supported: OpenSSH PEM, PuTTY .ppk v2/v3 (incl.
MobaXterm), and legacy PEM
(-----BEGIN RSA/EC/PRIVATE KEY-----)
— encrypted or plain.
🔐 This key is encrypted. Enter its current passphrase to decrypt:
🔧 Algorithm
Recommended
RSA
ECDSA (NIST curves)
Currently selected: {{ algorithmLabel }}
📝 Key comment
Appended to the public key (and stored inside the private blob). Edits here re-render the output when a key is loaded.
💾 Output format
OpenSSH suits Linux/macOS clients and modern Windows OpenSSH. PuTTY .ppk v3 is what PuTTY, Pageant, WinSCP, and FileZilla expect on Windows.
🔐 Passphrase (optional)
⚠️ Passphrases do not match.
OpenSSH: aes256-ctr + bcrypt-pbkdf
(16 rounds). PuTTY: AES-256-CBC + Argon2id
(13 passes, 8 MiB).
🔐 Private key ({{ outputFormatLabel }})
{{ privateDisplay }}
Save as ~/.ssh/{{ privateFileName }} and
chmod 600. Never transmit a private key.
🌐 Public key (authorized_keys line)
{{ publicDisplay }}
Append to ~/.ssh/authorized_keys on the server
you want to authenticate to — see the install commands below.
🖥️ Install on the server (authorized_keys)
Option A — paste into a shell on the server
{{ authorizedKeysScript }}
Log in as the user the key is for, then paste. It creates
~/.ssh (700) and
~/.ssh/authorized_keys (600) if they
don't exist, fixes their permissions if they do, and appends
the key only once — safe to run twice.
Generate or import a key to fill in the real public key.
Option B — from your machine with ssh-copy-id
{{ sshCopyIdCommand }}
Save the public key as ~/.ssh/{{ publicFileName }}
first and replace user@server. ssh-copy-id
logs in with your existing password and sets the same
permissions for you.
🪪 Fingerprints
- SHA256
- {{ sha256Fp || '—' }}
- MD5
- {{ md5Fp || '—' }}
Both fingerprints match the output of
ssh-keygen -l -E {sha256,md5} for this public
key.
ℹ️ About SSH Key Generator
What this tool does
SSH Key Generator creates an SSH key pair — a public key you can
upload to a server's ~/.ssh/authorized_keys file
and a corresponding private key you keep locally — in your
browser. Key material is generated by
Web Crypto's crypto.subtle.generateKey,
then re-serialised into either the OpenSSH wire format described by
RFC 4253 §6.6
and OpenSSH's
PROTOCOL.key,
or the PuTTY .ppk v3 format used by PuTTY 0.75+
and WinSCP.
You can also drag an existing key file into the page (OpenSSH PEM or PuTTY v3) to inspect its fingerprints or re-export it in a different format with a different passphrase. The imported key never leaves the page either — parsing, decryption, re-encryption, and fingerprinting all run in your browser tab.
Algorithm strength ratings
SSH supports several signature algorithms with very different security profiles, performance characteristics, and ecosystem support. Pick a row that matches both the threat model and the servers you'll be authenticating to.
-
Ed25519 (
ssh-ed25519) — Excellent. Modern default. 256-bit security level via curve25519, deterministic signatures, side-channel resistant, fastest verification, smallest public/private keys (32 bytes each), smallest signatures (64 bytes). Supported by OpenSSH 6.5+ (2014), so by every modern server. Recommended choice for new deployments. -
RSA 4096 (
ssh-rsa) — Strong. ~140-bit security level. Slower keygen and bigger signatures than EC, but ubiquitous. Use when the target server is too old for Ed25519 or when policy requires RSA with maximum key size. -
RSA 3072 (
ssh-rsa) — Strong. ~128-bit security level. NIST SP 800-57 recommendation for new RSA keys. -
RSA 2048 (
ssh-rsa) — Adequate. ~112-bit security level. Acceptable today, but considered borderline beyond 2030 per NIST guidance. Prefer 3072+ for long-lived keys. -
ECDSA P-256 (
ecdsa-sha2-nistp256) — Strong. NIST curve P-256, ~128-bit security level. Concerns about NIST curve provenance and a known history of catastrophic per-signature nonce-reuse failures in poor implementations. Modern OpenSSH implementations are not vulnerable, but Ed25519 is the generally preferred alternative. -
ECDSA P-384 (
ecdsa-sha2-nistp384) — Strong. NIST curve P-384, ~192-bit security level. Used when policy requires NIST curves and a higher security level. -
ECDSA P-521 (
ecdsa-sha2-nistp521) — Strong. NIST curve P-521 (note: not P-512), ~256-bit security level. Largest signatures of any option here. Rarely necessary in practice.
NIST / OpenSSH recommendation: default to Ed25519; fall back to RSA 3072+ for legacy compatibility. Avoid DSA entirely (OpenSSH 7.0 removed it as a default in 2015) — this tool does not offer it.
Output formats
-
OpenSSH — PEM block starting with
-----BEGIN OPENSSH PRIVATE KEY-----, described in OpenSSH'sPROTOCOL.key. When a passphrase is set, the private section is encrypted withaes256-ctrkeyed viabcrypt-pbkdf, matching whatssh-keygen -pproduces. Save as~/.ssh/id_ed25519(orid_rsa/id_ecdsa) andchmod 600. -
PuTTY .ppk v3 — text format used by
PuTTY 0.75+ (2021), WinSCP, FileZilla, and Pageant on
Windows. When a passphrase is set the private section is
encrypted with
AES-256-CBCkeyed viaArgon2id; the file carries an HMAC-SHA-256 tag over the algorithm, encryption type, comment, public blob, and private blob. v1 and v2 .ppk files are not emitted (v2 used SHA-1 derivation; v3 is the modern replacement).
The public key is always emitted as the single-line
authorized_keys format defined by
RFC 4253 §6.6:
an algorithm string (e.g. ssh-ed25519), one
base64-encoded wire blob, and an optional trailing comment.
Fingerprints
Two fingerprints are computed for each public key:
-
SHA256 — the modern default
(
ssh-keygen -l -E sha256), printed asSHA256:<base64>with no padding. -
MD5 — the legacy format
(
ssh-keygen -l -E md5), printed as 16 colon-separated lowercase hex pairs (e.g.aa:bb:cc:dd:…). MD5 is broken for collision resistance but is still emitted by older tooling, so the tool computes it for compatibility. Prefer SHA256 when verifying a host fingerprint.
Both fingerprints are computed over the binary public-key blob
(the base64-decoded payload), matching ssh-keygen -l.
How to use the generated key
-
For OpenSSH: save the private key as
~/.ssh/id_ed25519(orid_rsa/id_ecdsa) andchmod 600it. SSH refuses to use a private key that is world-readable. -
For PuTTY: save as
mykey.ppkand load it via Pageant or the connection profile's "Auth" → "Private key file" field. PuTTY 0.75+ is required to read the v3 format emitted here. -
Append the public key (single line) to
~/.ssh/authorized_keyson the server you want to log in to. Replaceuser@hostnamewith something useful so the key is easy to identify later. -
Test the login with
ssh -i ~/.ssh/id_ed25519 user@serverbefore closing your existing session, so a mistake can't lock you out. - Verify the server's fingerprint on first connect against the SHA256 value the server admin advertises out-of-band.
Adding the key to ~/.ssh/authorized_keys
sshd reads one public key per line from
~/.ssh/authorized_keys in the home directory of the
account you log in as. If the directory or file is missing,
create them; if their permissions are too open, OpenSSH's
StrictModes check (on by default) silently ignores
the file and falls back to password auth.
mkdir -p ~/.ssh touch ~/.ssh/authorized_keys chmod 700 ~/.ssh chmod 600 ~/.ssh/authorized_keys cat id_ed25519.pub >> ~/.ssh/authorized_keys
The panel next to the generated key gives the same commands with
your key filled in, plus an ssh-copy-id one-liner.
From Windows PowerShell, where ssh-copy-id isn't
available:
type $env:USERPROFILE\.ssh\id_ed25519.pub | ssh user@server "mkdir -p ~/.ssh && chmod 700 ~/.ssh && cat >> ~/.ssh/authorized_keys && chmod 600 ~/.ssh/authorized_keys"
-
Permissions:
~/.sshmust be700(drwx------),authorized_keys600(-rw-------), and the home directory itself must not be group- or world-writable. -
Ownership: both must belong to the login
user. If you created them as root for someone else, run
chown -R user:user ~user/.ssh. -
One key per line: use
>>(append), never>, which overwrites every existing key. A key pasted without a trailing newline gets glued to the next one and both stop working. -
SELinux (RHEL, Fedora, Rocky): if the key is
still refused, restore the file labels with
restorecon -Rv ~/.ssh. -
Debugging:
ssh -v user@servershows which keys the client offered; the server'sjournalctl -u ssh(orsshd) or/var/log/auth.logsays why one was rejected, e.g. bad ownership or modes.
Source references
- RFC 4253 §6.6 — SSH public-key wire format.
- RFC 4251 §5 — SSH primitives (string, mpint, uint32).
- RFC 8709 — Ed25519 and Ed448 for SSH.
- RFC 5656 — ECDSA for SSH (P-256 / P-384 / P-521).
- OpenSSH PROTOCOL.key — OpenSSH private-key file format.
- RFC 4716 — SSH public-key file format (alternate text encoding).
- PuTTY —
sshpubk.csource for the .ppk v3 binary layout and Argon2id derivation. - RFC 9106 — Argon2 password hashing (used by PuTTY v3).
- sshd(8) AUTHORIZED_KEYS FILE FORMAT and sshd_config StrictModes — file format and permission checks.
- ssh-copy-id(1) — installs a public key on a remote host.
- NIST SP 800-57 — key-size recommendations for RSA / ECC.