Claude DesktopのSSHでConnectTimeoutを延ばす手順と45秒の壁
踏み台のスマホ承認が間に合わないときはConnectTimeoutを延ばせます。ただしリモート機自体の承認待ちは45秒で固定です。書く場所と確認コマンドを示します。
Claude DesktopのSSHセッションで、踏み台(ジャンプホスト)のスマホ承認が間に合わずに接続が切れるなら、~/.ssh/config に ConnectTimeout を足すと待ち時間を延ばせます。ただし延ばせるのは踏み台や ProxyCommand が待つ時間だけです。リモート機そのものがスマホ承認を待つ場合は、設定に関係なく45秒で切れます。
どちらの待ちで切れているかを先に見分けると、無駄な設定変更をしなくて済みます。
ConnectTimeoutを延ばせる待ちと延ばせない待ち
Desktopは、~/.ssh/config にそのホストの ConnectTimeout が無いと、ssh に30秒で接続を終えるよう求めます。踏み台や ProxyCommand を通る経路では、その経路が繋がるまでの時間も30秒に含まれます。
つまり踏み台のログインでスマホ承認を挟む構成は、承認の操作が遅れるだけで30秒の枠を使い切ります。
一方で、接続の最後にリモート機が承認を求める構成は別の仕組みです。こちらは次の節のとおり、Desktopが固定する値で決まります。
| 承認が起きる場所 | 延ばせるか | 効く設定 |
|---|---|---|
踏み台(ProxyJump) | 延ばせるか延ばせる | 効く設定接続先エントリの ConnectTimeout |
ProxyCommand が呼ぶ処理 | 延ばせるか延ばせる | 効く設定同上 |
| リモート機自体のログイン | 延ばせるか延ばせない | 効く設定なし(45秒固定) |
ConnectTimeoutを書く場所と順序
踏み台を使うエントリに、ConnectTimeout を1行足します。次の例は、bastion.example.com 経由で devbox に入る構成に120秒を与えます(Desktopのドキュメントにある形に沿った例です)。
Host devbox
HostName devbox.internal.example.com
User alice
ProxyJump bastion.example.com
ConnectTimeout 120ConnectTimeout は秒単位です。OpenSSHの説明では、接続の確立に加えて、最初のSSHプロトコルのやり取りと鍵交換にもこの時間が適用されます。
書く位置には決まりがあります。ssh は、ホストに対して最初に見つけた値を使います。そのため、Host * のエントリが ConnectTimeout を持っているなら、延ばしたいエントリをその上に置きます。下に置くと、Host * の値が先に採用されます。
次のような並びが安全な形です。
Host devbox
HostName devbox.internal.example.com
ProxyJump bastion.example.com
ConnectTimeout 120
Host *
ConnectTimeout 10エントリ名(ここでは devbox)は、DesktopのSSH host欄に入れる名前です。macOSとLinuxでは、Desktopは手元のOpenSSHクライアントを動かして ~/.ssh/config を読みます。OpenSSHクライアント経由の接続にはClaude Desktop v1.37937.0以降が必要で、クライアントはOpenSSH 7.6以降という条件も付きます。
Windowsの手元PCでは ~/.ssh/configが使われるとは限らない
~/.ssh/config を読む仕組みを説明している節の見出しは「Use your SSH configuration on macOS and Linux」で、対象はmacOSとLinuxです。Windowsの手元PCで同じように ConnectTimeout が効くとは、この節からは言えません。
別の箇所には、Desktopが内蔵のSSHクライアント(built-in SSH client)を使う条件が書かれています。Microsoft Store版をインストールしている場合、MicrosoftのOpenSSH 9.4以降が入っていないWindowsの場合、サードパーティのproviderを使うWindowsの場合です。内蔵クライアントが ~/.ssh/config をどう扱うかについて、ドキュメントに記載はありません。
Windowsで ConnectTimeout を書いても待ち時間が変わらないときは、次の点を見ます。
ssh -Gは手元のOpenSSHでの解決結果です。Desktopが内蔵クライアントで接続している場合、同じ値が使われるとは限りません- 手元のPCでエントリ単体(
ssh devbox)が通るかを確かめ、通るのにDesktopだけ時間切れになるなら、クライアントの違いを疑います
どちらのクライアントで接続しているかの判別方法は、ドキュメントに示されていません。時間切れが続くなら、macOSまたはLinuxの手元PCで同じエントリを試すと、切り分けが進みます。
効いているかをssh -Gで確かめる
書き換えたら、手元のターミナルで次を実行します。
ssh -G devbox | grep -i connecttimeoutconnecttimeout 120 と出れば、そのエントリの値が採用されています。10などの別の値が出るなら、Host * が先に効いています。エントリの順序を見直します。
設定を直したあとは、Desktopを一度終了して開き直します。開いたままだと古い値のまま接続を試みます。
MatchブロックだけがDesktopで効く場合
端末の ssh devbox とDesktopで挙動が違うときは、HostName の行より上にある Match host ブロックを疑います。Desktopは HostName の値をコマンドラインで ssh に渡すため、Match はその値と比べられます。端末ではエントリ名の devbox と比べられます。
Desktopと同じ条件で確かめるなら、こう実行します。
ssh -G -o HostName=devbox.internal.example.com -l alice devbox \
| grep -i connecttimeout2つの出力が食い違うなら、MatchブロックがDesktopだけで効いています。外したいブロックの Match 行に !originalhost devbox を足すと、Desktopでも対象から外れます。ConnectTimeout を Match の中に書いた場合も、この差で値が食い違い得ます。
スマホ承認が45秒で切れるのはなぜか
リモート機自身がログインのときにスマホ承認を待つ場合は、ConnectTimeout をいくら大きくしても、45秒以内に承認する必要があります。ドキュメントはこの上限を変えられないと書いています。Desktopが ServerAliveInterval と ServerAliveCountMax を自分で設定するためです。ssh は、リモート機から何も返ってこない状態がその時間続くと、ログインを閉じます。
OpenSSHの説明には、ServerAliveInterval を15、ServerAliveCountMax を既定のままにすると、応答しないサーバーから約45秒後に切断される、という例が載っています。45秒という数字はこの種の組み合わせから出ます。ただしDesktopが実際に使う個々の値はドキュメントに載っておらず、設定を上書きする手段も示されていません。
整理すると、ConnectTimeout は接続を始める側の待ちを延ばし、ServerAlive* は接続後の無反応を見張ります。性質が別なので、片方の設定でもう片方は動きません。
承認の置き場所を動かせるなら、そこが現実的な解決策です。
- 承認を踏み台側に寄せる: 踏み台で承認し、リモート機はキー認証だけで入れるようにすると、
ConnectTimeoutで待ちを延ばせます - リモート機の承認を省く: 手元で
ssh devboxを実行して、承認なしで入れるログインに切り替えます
どちらも組織のセキュリティ方針に関わるため、変更の可否は管理者に確認する話になります。
延ばしたあとに起きる再接続の挙動
踏み台が毎回スマホ承認を求める構成は、ConnectTimeout を延ばしても別の問題が残ります。ドキュメントは、長いタスクを任せる前の準備として、踏み台のログインを承認なしで通る形に切り替えるよう案内しています。そうしないと、Desktopが再接続を試みるたびに、また承認のプッシュ通知が飛ぶ可能性があるためです。
macOSとLinuxのDesktopは、誰も承認しない状態を見分けられます。承認が3回続けて応答なしになると、再試行か新しいメッセージ送信まで待機します。PCのロックを解除したり操作したりしたときに、Desktopがもう一度試して、プッシュが届くこともあります。
WindowsのDesktopは、承認が放置されていることを見分けられません。再接続の対象のプロセスが残っている間は試行を続けるため、通知が何度も届き得ます。止めるにはDesktopを終了しますが、実行中のタスクが失われる場合があります。
長い停止になると、試行の間隔は約5分に1回まで空きます。早く戻したいときは、セッション内で再試行するか、メッセージを送ります。
ConnectTimeoutを延ばしても直らないとき
延ばしても同じ症状が出るなら、次を順に当たります。
ssh -Vで、手元のクライアントがOpenSSH 7.6以降か。これより古いと、DesktopのOpenSSHクライアント経由の接続の条件を満たしませんssh -Gの出力でconnecttimeoutが意図した値か。違えばHost *の順序かMatchを見直す- 手元のターミナルで
ssh devboxを実行し、承認から接続まで通るか。ここで失敗するならDesktopの問題ではなく経路の問題で、ドキュメントも接続を足す前にこの確認を求めています - 承認を求めているのが踏み台か、リモート機か。後者なら45秒が上限
- 手元がWindowsなら、上の節のとおり内蔵クライアントで接続していて
~/.ssh/configが使われていない可能性もあります
WindowsのDesktopで ssh の起動自体に失敗する場合は、ConnectTimeout とは別の原因です。「Failed to spawn /usr/bin/ssh」の原因と対処で扱っています。
また、Claude Codeが ssh を実行したときにパスフレーズ待ちで固まる件は、接続の時間切れとは別の症状です。こちらはClaude Codeのsshでpassphraseを聞かれて固まる原因と回避策にまとめてあります。
チームで同じSSH接続を配る場合は、設定ファイルを各自に書かせるのではなく、sshConfigsでチーム共通の接続を配る方法があります。接続先を絞る運用はsshHostAllowlistの記事が参考になります。許可リストの判定は ssh -G で解決したあとのホスト名に対して行われるため、本記事の確認コマンドと同じ出力が使えます。
まとめ
承認が踏み台や ProxyCommand 側で起きるなら、接続先のエントリに ConnectTimeout 120 を書き、Host * より上に置きます。ssh -G で connecttimeout の値を見れば、効いているかが分かります。
リモート機自体の承認待ちは、ConnectTimeout ではなくDesktopが固定する見張りの時間で切れます。承認の場所を踏み台に寄せるか、承認なしのログインに切り替えるのが、設定側で動かせる範囲です。