SecuredKit

Опубліковано: · Оновлено: · автор:

Як безпечно згенерувати SSH-ключ: інструкція 2026

Як створити SSH-ключ через ssh-keygen: ed25519 чи RSA, що дають парольна фраза й раунди KDF, якщо файл ключа вкрадуть, ssh-agent і відкликання доступу.

як згенерувати SSH-ключ — термінал із командою ssh-keygen ed25519 і відбитком ключа

Щоб безпечно згенерувати SSH-ключ у 2026 році, достатньо однієї команди і справжньої парольної фрази, коли програма її попросить:

ssh-keygen -t ed25519 -a 64 -C "you@laptop-2026"

-t ed25519 задає тип ключа, -a 64 — скільки раундів bcrypt захищатимуть файл приватного ключа на диску, а -C — це мітка, яка потрапить в authorized_keys на сервері, щоб згодом ключі можна було розрізнити. Сама команда — найпростіша частина. Чи перетвориться загублений ноутбук або злита резервна копія на доступ до ваших серверів, вирішують парольна фраза, те, як ви завантажуєте ключ в агент, і те, наскільки швидко ви можете прибрати ключ із серверів, коли він стає непотрібним.

Що робить кожен прапорець ssh-keygen

ПрапорецьПризначенняПримітки
-t ed25519Тип ключаЗа замовчуванням з OpenSSH 9.5 (жовтень 2023). Я все одно пишу його явно в документації та скриптах, щоб старіша машина мовчки не створила щось інше
-a 64Раунди KDFСкільки раундів bcrypt_pbkdf перетворюють парольну фразу на ключ, яким шифрується файл. Старіші версії мали за замовчуванням 16; OpenSSH 10.6 (жовтень 2026) підняв значення до 32
-C "you@laptop-2026"КоментарДовільний текст у кінці рядка відкритого ключа. Вказуйте людину й пристрій, а не лише email
-f ~/.ssh/id_ed25519_workІм'я файлуПотрібне, лише якщо ви тримаєте окремі ключі для різних задач

Реальний запуск, скорочено (блок randomart прибрано):

$ ssh-keygen -t ed25519 -a 64 -C "you@laptop-2026"
Generating public/private ed25519 key pair.
Enter file in which to save the key (/home/you/.ssh/id_ed25519):
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in /home/you/.ssh/id_ed25519
Your public key has been saved in /home/you/.ssh/id_ed25519.pub
The key fingerprint is:
SHA256:IikmcGblWuCYS6a6eqQ24RzSyqc9o36qkoPLnzdOxLE you@laptop-2026

На виході два файли. id_ed25519 — приватний ключ, він ніколи не залишає машину. id_ed25519.pub — один рядок, який ви вставляєте в GitHub або копіюєте на сервери.

Ed25519 чи RSA у 2026 році

Для нового ключа — ed25519. Відкритий ключ займає 68 символів base64, підпис швидкий, а nonce для підпису виводиться з ключа й повідомлення (RFC 8032), а не береться з генератора випадкових чисел. Останнє важить більше за розмір: ECDSA потребує свіжого секретного випадкового числа для кожного підпису, і якщо воно повториться, приватний ключ витікає. Саме так у 2010 році відновили ключ, яким Sony підписувала ПЗ для PS3.

Тип ключаВідкритий ключ (символів base64)Рівень стійкостіСтатус в OpenSSH
ed2551968~128 бітЗа замовчуванням з 9.5
RSA 3072544128 біт (NIST SP 800-57)Розмір за замовчуванням, якщо обрати RSA
RSA 2048372112 бітДосі приймається, для нових ключів замалий
ECDSA P-256140128 бітПрацює; залежить від якісного nonce для кожного підпису
DSAПовністю видалений в OpenSSH 10.0 (квітень 2025)

Мої власні ключі — RSA, і вони досі працюють усюди, де мені потрібно. Фразу «OpenSSH 8.8 вимкнув ssh-rsa» (вересень 2021) іноді читають як «RSA-ключі мертві», але 8.8 вимкнув саме підписи RSA з SHA-1. Той самий RSA-ключ автоматично підписує через SHA-256 або SHA-512. Якщо у вас теж RSA-ключі, дві перевірки дадуть більше, ніж заміна ключів із принципу:

ssh-keygen -lf ~/.ssh/id_rsa.pub   # перше число — розмір ключа: має бути 3072+
head -2 ~/.ssh/id_rsa              # у якому форматі збережено приватний ключ

Якщо друга команда виводить -----BEGIN RSA PRIVATE KEY-----, а за ним Proc-Type: 4,ENCRYPTED, ключ збережено у старому форматі PEM від OpenSSL, який ssh-keygen використовував за замовчуванням до OpenSSH 7.8 (серпень 2018). Цей формат отримує ключ шифрування з парольної фрази одним проходом MD5, без жодного фактора складності. ssh-keygen -p -a 64 -f ~/.ssh/id_rsa перезапише файл як -----BEGIN OPENSSH PRIVATE KEY----- з bcrypt_pbkdf, а відкритий ключ не зміниться.

Є ще два варіанти. З апаратним FIDO2-ключем ssh-keygen -t ed25519-sk (OpenSSH 8.2+) тримає приватний ключ на пристрої, а файл у ~/.ssh — лише дескриптор, марний без токена й дотику до нього. У release notes самого OpenSSH сказано, що Ed25519 токени підтримують рідше, ніж ECDSA, тож запасний варіант — -t ecdsa-sk. Гібридний постквантовий тип mldsa44-ed25519 увімкнули в OpenSSH 10.6, але сервери на старіших версіях його не приймуть, тому я поки не робив би його чиїмось єдиним ключем.

Що дає парольна фраза, коли файл ключа витік

Парольна фраза має значення лише в одному сценарії, і він найпоширеніший: у когось опинилася копія id_ed25519. Вкрадений ноутбук, домашня тека в резервній копії, репозиторій із dotfiles, який захопив ~/.ssh, шкідлива програма, що читає файли. Відтак перебір іде офлайн, без обмеження швидкості й без жодного запису в логах на вашому боці.

OpenSSH шифрує приватний ключ алгоритмом AES-256-CTR, а ключ AES отримує з парольної фрази через bcrypt_pbkdf. Кожен раунд KDF виконує bcrypt-подібну підготовку ключа з 64 проходами розширення, що приблизно дорівнює одному хешу bcrypt з cost 6, а 48 байтам ключа AES і IV потрібні два вихідні блоки. За 32 раундів це близько 64 хешів bcrypt з cost 6 на одну спробу. Якщо масштабувати виміряну hashcat швидкість bcrypt на RTX 4090 (184 000 на секунду при cost 5), виходить приблизно 1 440 спроб на секунду, стільки ж, скільки в bcrypt з cost 12. Це моя оцінка з алгоритму, а не опублікований бенчмарк саме цього формату файлу, тож сприймайте таблицю як порядок величин.

H = W × log₂(7776) ≈ W × 12.9 bits     W = random words from the EFF list
average time = 7776^W / 2 / guesses per second

Тут H — ентропія в бітах, W — кількість випадкових слів зі списку EFF, а середній час — це половина простору варіантів, поділена на швидкість перебору.

Парольна фразаЕнтропіяСередній час, одна RTX 4090, 32 раунди
Немає0 бітПеребирати нічого: файлом можна користуватися як є
Слово плюс рік, які ви обрали саміНизькаПадає під перебором за словником із правилами; вважайте, що фрази немає
2 випадкові слова EFF25,8 біта~6 годин
3 випадкові слова EFF38,8 біта~5 років
4 випадкові слова EFF51,7 біта~40 000 років
5 випадкових слів EFF64,6 біта~310 млн років
8 випадкових друкованих символів ASCII52,6 біта~73 000 років

Підлаштуйте під свою ситуацію: ключ, збережений зі старим значенням у 16 раундів, ламається вдвічі швидше, ферма з 8 GPU ділить кожен рядок на 8 (чотири слова — приблизно 5 000 років), а -a 64 подвоює кожен рядок. Ці цифри справедливі лише для слів, обраних випадково. Фраза, яку ви вигадали самі, належить до другого рядка.

Я вважав би чотири випадкові слова мінімумом, а для ключів, що мають доступ до продакшену, брав би п'ять. Збільшення -a у стільки ж разів сповільнює й розшифрування для вас, але з агентом ви платите цю ціну раз за сесію, тож перехід із 32 на 64 раунди майже нічого не коштує.

Не вигадуйте слова самі. Режим парольної фрази в моєму Генераторі паролів обирає їх через crypto.getRandomValues() і показує ентропію в бітах, поки ви змінюєте кількість слів; він працює у вашому браузері й нікуди нічого не надсилає. Для таблиці вище це принципово: у генератора на основі Math.random() внутрішній стан можна відновити з кількох значень, і тоді «випадкові» слова такими не є. Щоб порівняти фразу, якою ви вже користуєтеся, введіть у Перевірку стійкості пароля фразу такої самої форми (стільки ж слів того ж типу, але не справжню). Чим відрізняються секрети зі слів і з символів, я розбирав у статті парольна фраза чи пароль.

ssh-agent: вводити парольну фразу раз за сесію

Якщо парольну фразу треба вводити при кожному підключенні, рано чи пізно хтось її з ключа зніме. Агент тримає розшифрований ключ у пам'яті й підписує замість вас:

eval "$(ssh-agent -s)"
ssh-add -t 8h ~/.ssh/id_ed25519   # забути ключ через 8 годин
ssh-add -l                        # що зараз тримає агент

На macOS ssh-add --apple-use-keychain ~/.ssh/id_ed25519 зберігає парольну фразу в Keychain, а AddKeysToAgent yes разом із UseKeychain yes у секції Host * файлу ~/.ssh/config завантажують ключ при першому використанні.

Обережно з пересиланням агента (ForwardAgent yes або ssh -A). Поки ви підключені, будь-хто з root-доступом на віддаленій машині може скористатися вашим пересланим агентом і підписуватися вашим ключем на інших серверах. Щоб дістатися машин за bastion-хостом, ssh -J bastion target (ProxyJump) доведе вас туди, не відкриваючи агента.

Покладіть відкритий ключ на сервер, потім вимкніть паролі

ssh-copy-id -i ~/.ssh/id_ed25519.pub user@server

Команда додає рядок із вашого .pub до ~/.ssh/authorized_keys на сервері. Під час входу мережею не передається нічого секретного: після обміну ключами клієнт підписує приватним ключем блок даних з ідентифікатором сесії, а сервер перевіряє цей підпис відкритим ключем, який у нього записаний (RFC 4252, розділ 7). Підпис прив'язаний до однієї сесії, тож записаний вхід не вийде відтворити повторно.

client                                       server
  |  key exchange  ->  session identifier H     |
  |  "publickey" request + signature over H     |
  |  (made with the private key)  ------------> |
  |                                             |  verify with the key in
  |                                             |  ~/.ssh/authorized_keys
  |  <-------------------------  success / fail |

Коли вхід за ключем працює, вимкніть паролі в /etc/ssh/sshd_config:

PasswordAuthentication no
KbdInteractiveAuthentication no

Перш ніж перезавантажувати sshd, перевірте, які налаштування він реально застосує, бо файли в /etc/ssh/sshd_config.d/ можуть перекривати основний файл (хмарні образи Ubuntu постачаються з 50-cloud-init.conf, де може стояти PasswordAuthentication yes):

sudo sshd -t && sudo sshd -T | grep -iE 'passwordauth|kbdinteractive'

Не закривайте поточну сесію і перевірте новий вхід із другого термінала, перш ніж щось закривати. Так у вас лишиться шлях назад, якщо конфігурація виявиться хибною.

Права доступу та відбитки ключів

OpenSSH відмовляється працювати з приватним ключем, який можуть читати інші користувачі, тож налаштуйте права один раз:

chmod 700 ~/.ssh
chmod 600 ~/.ssh/id_ed25519 ~/.ssh/authorized_keys
chmod 644 ~/.ssh/id_ed25519.pub

ssh-keygen -lf ~/.ssh/id_ed25519.pub виводить відбиток: 256 SHA256:IikmcG… you@laptop-2026 (ED25519). Захищає вас інший відбиток — відбиток ключа хоста, який ви бачите при першому підключенні до нового сервера. Порівняйте його зі значенням у консолі провайдера або з виводом ssh-keygen -lf /etc/ssh/ssh_host_ed25519_key.pub на самому сервері, а не вводьте «yes» за звичкою.

Відбиток — це SHA-256 від декодованого блоку ключа, закодований у base64 без кінцевого =. Якщо хочете переконатися самі, декодуйте середнє поле рядка .pub у файл через Base64 декодувальник, захешуйте цей файл у Генераторі хешів з виводом у base64, і результат збіжиться з тим, що показує ssh-keygen.

Ротація й відкликання доступу відбуваються на сервері

Приватний ключ не можна відкликати з боку клієнта. Він перестає працювати лише тоді, коли зникає кожен рядок authorized_keys, що йому довіряє. Коли мені доводилося мати справу з людьми, які йшли з команди, робота була саме такою: пройтися серверами й оновити, хто має доступ. Кілька звичок роблять цю роботу короткою:

  1. Один ключ на людину на пристрій. Тоді загублений ноутбук означає видалити один рядок, і більше нікому нічого не треба ротувати.
  2. Коментарі, з яких видно людину й машину (-C "anna@work-laptop-2026"), щоб grep anna ~/.ssh/authorized_keys на всіх хостах знаходив кожен рядок.
  3. Ключі для CI і скриптів деплою обмежені на боці сервера, наприклад from="203.0.113.10",restrict,command="/usr/local/bin/deploy" перед ключем, замість парольної фрази, яку о третій ночі ніхто не введе.
  4. Коли серверів більше кількох, сертифікати SSH: підписуйте ключі користувачів ключем CA (ssh-keygen -s ca_key -I anna -n deploy -V +30d id_ed25519.pub) і дозвольте їм спливати, замість вишукувати рядки вручну.

Ніколи не комітьте приватний ключ і не пускайте ~/.ssh у репозиторії з dotfiles та теки, що синхронізуються з хмарою. Якщо ключ таки витік, поводьтеся з ним як з будь-якими викраденими обліковими даними: спершу приберіть його із серверів, потім генеруйте заміну.

Якщо після цієї статті зробити лише одне, виконайте head -1 для кожного приватного ключа в ~/.ssh. Усе без парольної фрази або досі у старому форматі PEM сьогодні ж отримує ssh-keygen -p -a 64 -f <file>.

FAQ

Яка команда найкраща для генерації SSH-ключа у 2026 році?

ssh-keygen -t ed25519 -a 64 -C "you@laptop-2026", а потім парольна фраза з чотирьох-п'яти випадкових слів. В OpenSSH 9.5 і новіших -t ed25519 і так стоїть за замовчуванням, але явно вказаний прапорець нічого не коштує і захищає вас на старіших системах.

Що обрати для SSH: ed25519 чи RSA?

Ed25519 для всього нового. RSA-ключі від 3072 біт досі нормальні й працюють після OpenSSH 8.8, який вимкнув лише підписи з SHA-1. Нові ключі RSA-2048 не генеруйте: 112 біт стійкості — найнижчий рівень, який NIST ще приймає.

Чи потрібна SSH-ключу парольна фраза?

Для будь-якого ключа, яким користується людина, так. Без неї скопійований файл — це готовий вхід. Чотири випадкові слова EFF за поточних стандартних 32 раундів, за моєю оцінкою, дають у середньому близько 40 000 років перебору на одній RTX 4090, а фраза, яку ви вигадали самі, падає під перебором за словником. Для ключів CI натомість обмежте на сервері, що ключ може робити.

Як додати парольну фразу до наявного SSH-ключа?

ssh-keygen -p -f ~/.ssh/id_ed25519. Команда спитає стару парольну фразу (просто натисніть Enter, якщо її не було) і перешифрує той самий ключ, тож на серверах нічого не зміниться. Додайте -a 64, щоб заодно збільшити кількість раундів KDF. Для старого ключа у форматі PEM команда також переведе файл у формат OpenSSH.

Де зберігаються SSH-ключі?

У ~/.ssh/: id_ed25519 (приватний, права 600) і id_ed25519.pub (відкритий). Резервну копію приватного ключа тримайте лише в зашифрованому місці, наприклад як вкладення в менеджері паролів або в зашифрованому образі диска. Відкритий ключ захисту не потребує.

Спробуйте безкоштовний генератор паролів

Генеруйте надійні, безпечні паролі миттєво. 100% приватно, на стороні клієнта.

Відкрити генератор паролів