世界を動かす技術を、日本語で。

SSH証明書: より良いSSH体験

2026年4月3日原文(jpmens.net)

概要

  • SSHの初回接続時 にはサーバの真正性確認が必要
  • 公開鍵認証 によりパスワード入力を省略可能
  • ホスト鍵の変更 時には警告や手動対応が必要
  • SSH CA(認証局)と証明書 を使えば運用が大幅に簡素化
  • 証明書運用のメリット と基本的な導入手順を解説

SSH証明書:より良いSSH体験

  • サーバへ初めて SSH接続 する際、「このサーバが本物か?」という確認ダイアログの表示
    • 例:ssh -l jane 192.0.2.65 実行時の警告表示
  • Trust on First Use(TOFU) による初回接続時の信頼確立
    • サーバ管理者から フィンガープリント を事前に取得・照合する運用推奨
    • 例:ssh-keygen -l -f /etc/ssh/ssh_host_ed25519_key でフィンガープリント確認
  • ssh-keyscan などで公開鍵取得可能だが、 別経路での検証 が必要

SSH鍵ペアによる認証

  • 自分の 公開鍵 をサーバの$HOME/.ssh/authorized_keysに設置
    • サーバ接続時に 秘密鍵 とパスフレーズで認証
  • 鍵作成例ssh-keygen -t ecdsa -C "JP's demo key" -f demokey
    • 公開鍵のサーバ登録:ssh-copy-id -i demokey.pub jane@192.0.2.65
  • SSHエージェント 利用でパスフレーズ入力の省略
    • eval $(ssh-agent)ssh-add demokeyで管理

公開鍵認証の課題

  • 各ユーザーごとに公開鍵設置 が必要
  • TOFU による known_hostsファイル へのホスト鍵保存
  • ホスト鍵のロール(再生成) 時に警告発生
    • サーバのホスト鍵変更時、ssh-keygen -Rknown_hosts から削除し再登録が必要
  • 大規模環境 ではこれらの運用が煩雑

SSH CA(認証局)とSSH証明書

  • SSH CA はシンプルな SSH鍵ペア で運用可能
    • OpenSSH 5.4以降 で証明書運用対応
  • SSH証明書 の特徴
    • 公開鍵ファイルに見えるが、 証明書情報 を含む
    • 例:ecdsa-sha2-nistp256-cert-v01@openssh.com ... Jane's key
  • CA鍵ペア を使い、ユーザー鍵やホスト鍵を署名
  • CA導入のメリット
    • サーバへの公開鍵配布(authorized_keys編集)が不要
    • 不要な鍵の登録リスク低減
    • ホスト鍵ロール 時もクライアント側警告なし
    • TOFU不要、ユーザー・サーバ間の相互信頼が自動化
    • 証明書の有効期間や利用ユーザー(プリンシパル)を柔軟に制御
    • IP制限 やリモートコマンド制限なども証明書側で設定可能
    • known_hosts にCA公開鍵を1行追加するだけで全ユーザー適用

SSH CA運用の基本手順

  • CA用ディレクトリ作成 と鍵生成
    • 例:umask 077; mkdir CA; ssh-keygen -t ecdsa -C "JP's SSH CA" -f CA/ssh-ca
  • ユーザー鍵ペア生成 (既存鍵でも可)
    • 例:ssh-keygen -t ecdsa -C "Jane's key" -f jane
  • ユーザー公開鍵をCAで署名し証明書発行
    • 証明書発行コマンド例や詳細は割愛(続きで解説可能)

SSH証明書運用のまとめ

  • 大規模サーバ運用セキュリティ要件の高い現場 でのSSH運用最適化
  • 鍵管理・配布・信頼性向上 のための現代的アプローチ
  • OpenSSH標準機能 で導入可能、追加ソフト不要

ご要望があれば、 証明書署名コマンド例やサーバ・クライアントの設定手順 も詳述可能です。

Hackerたちの意見

数ヶ月ごとに誰かがSSH証明書を再発見して、ブログに書くんだよね。俺もその一人だ。15年前の俺のブログ記事はOPの投稿には全然及ばないけど、15年前の自分が今の基準に達してたら、かなりがっかりするだろうな。: https://blog.habets.se/2011/07/OpenSSH-certificates.html

SSH証明書のことは前から知ってたけど、キーから移行する努力はしてなかったんだ。でも、いろんなサーバーやデバイスでSSHキーを手動で管理するのはすごくイライラする。15年の間にたくさんの考えをまとめたと思うけど、切り替えるべきかな?

SSH証明書のもう一つの便利な機能は、ユーザーの公開鍵に署名して、特定のリモートユーザーとしてリモートマシンへのアクセスを限られた時間だけ許可できることだよ。

怖い現実は、多くの人が「鍵」と「証明書」を混同していることだと思う。セキュリティエンジニアと一緒に働いていると、SSH証明書は使わないってことを思い出させないといけないことがあるんだよね。彼らはそれを理解するのにちょっと考えないといけないみたい。

ああ、やばい、10年くらい前に$jobのためにSSH証明書認証局を書いたとき、あなたのブログ記事を参考にしたよ… 書いてくれてありがとう!

開発/ステージング環境では、毎朝半分のマシンを再インストールしてるんだ(主にマシンセットアップの自動化をテストするため)。SSHホスト証明書があると、ホストキーを保持したり、known_hostsから削除・置き換えたりする必要がなくて、すごく楽になるよ。めっちゃおすすめ!

著者はCA証明書の利点をすべて挙げてるけど、欠点は挙げてないね。一方で、設定に必要な多くのステップがあるから、欠点はかなり明らかだよ。TOFUのせいでセキュリティ問題が起きたことはないけど、君はどう?

TOFUは便利だけど、必須ではないよ。TOFUを使う選択は、SSHで生成されたキーを使う選択とは別のものなんだ。もしTOFUを使いたくないなら、追加のセキュリティのために、対応する公開鍵を安全なチャネル(例えばUSBメモリを使って)でコピーして、コンピュータ同士をペアリングすればいい。証明書を使っても、簡略化や追加のセキュリティは得られないよ。本当のセキュリティを得るには、通信するコンピュータ同士を、やっぱり安全なチャネルで証明書をコピーしてペアリングする必要がある。HTTPSでブラウザに付属している証明書を使うときは、そのインストーラーパッケージが証明書を作成した権威から安全なチャネルでそのコンピュータに届いたと信じることになる。これは、君が管理しているコンピュータ間でTOFUを信頼できるという仮定よりも、はるかに非現実的な仮定だよ。証明書は大きな組織では役立つかもしれないけど、単に安全な通信チャネルを確立する以上の機能が必要な場合、例えば証明書の失効を使いたいときにね。親記事で挙げられている「利点」のリストの半分以上は間違ってる。なぜなら、証明書が正しく実装されていれば、TOFUなしのSSHキーを使うときと証明書を使うときで、完全に同じアクションを実行しなければならないから。著者は「利点」のいくつかを書くことで、証明書を使うときに必要なくなるアクションはユーザーではなく管理者が行うものだと言いたかったのかもしれない。でも、それはSSHにも当てはまる。管理者が証明書をインストールすれば、ユーザーからのアクションは不要になるけど、管理者がSSH公開鍵をインストールすれば、ユーザーからのTOFUも不要になる。証明書を使うには、SSHで生成されたキーを使うのとまったく同じステップが必要なんだ(つまり、証明書を生成して、安全なチャネルでコンピュータ間でコピーして、サーバーと認可されたユーザーをペアリングすること)。でも、証明書は追加の機能を提供するから、追加のステップが必要になることもある。

それに、TOFUのせいでセキュリティ問題が起きたことはないけど、君はどう? これは、車の事故に遭ったことがないからシートベルトは考慮する価値がないと言ってるようなものだね。設定に関する明らかで文書化された作業を超えて、SSH証明書を使うことに欠点があると思う?

ボックスに接続する前にCA設定を行うためのアクセス手段があるなら、その同じアクセスチャネルを使ってTOFUに頼らずに鍵アクセスを設定できるよ。インストールスクリプトの一部からカスタマイズされたデプロイメントイメージ、仮想化シナリオでのホストへの物理アクセスまで、何でもあり。TOFUは、ボックスがすでに設定されていて、SSHで接続して物をボックスにロードする以外に方法がないときに本当に関係してくる。でも、証明書アプローチを取るつもりなら、同じ話になるよ。

それに、TOFUのせいでセキュリティの問題が起きたことはないけど、君はどう? TOFUのせいでセキュリティの問題が起きたことがないのは君だけじゃないよ - それ、直したよ。

最近のnpmハックでプライベートキーが盗まれる事件があったから、キーの有効期限を制限したいと思ってる。管理しているホストにSSH CAとしていくつかのYubiKeyを設定したよ。これを使って、1日の始まりに短期間の証明書(例えば24時間)を作成してる。この方法だと、YubiKeyのPINを1日に1回だけ入力すればいいから楽なんだ。OpenSSHで最大証明書の有効期限を簡単に制限する方法が見つからなかったけど、AuthorizedPrincipalCommandを使うのが唯一の方法で、ちょっと脆弱に感じる。似たようなセットアップをしている人はいる?証明書の最大有効期限をどうやって制限してる?

Hacker Newsで議論の続きを見る