32blogby Studio Mitsu

ssh・rsync実践ガイド:リモートサーバー操作の必須スキル

ssh鍵認証・設定ファイル・ポートフォワーディングからrsyncの差分転送・バックアップまで。セキュリティ対策も含めて解説。

by omitsu23 min read
目次

「サーバーにログインするたびにパスワードを打つのが面倒」「本番にファイルをアップロードしたいけど scp は遅い」「手元の開発サーバーに外からアクセスしたい」

こういう場面の答えが sshrsync だ。ssh はリモートサーバーへの暗号化接続を提供し、rsync は差分転送で効率的なファイル同期を実現する。どちらもサーバー管理やデプロイのワークフローに欠かせない基盤ツールだ。

この記事では、鍵認証のセットアップから設定ファイルのチューニング、ポートフォワーディング、rsync のバックアップパターンまで、実行可能なコマンド例を交えて解説する。

ssh とは

ssh(Secure Shell)は、ネットワーク越しに別のマシンを安全に操作するためのプロトコルとコマンドだ。通信はすべて暗号化されるため、パスワードやコマンドが平文で流れることはない。

かつてリモート接続に使われていた telnet は通信が暗号化されない。ssh はその安全な後継として1995年に登場し、今ではサーバー管理の事実上の標準になっている。

ssh でできることは接続だけではない:

  • リモートコマンド実行ssh user@server "ls -la /var/log" のようにワンライナーで実行できる
  • ファイル転送:scp や sftp による暗号化ファイル転送
  • ポートフォワーディング:ローカルとリモートの間にトンネルを作り、特定のポートを転送する
  • トンネリング:VPN 的な用途にも使える SOCKS プロキシ

基本的な接続は簡単だ:

bash
ssh user@192.168.1.100

ポートを指定する場合は -p オプションを使う:

bash
ssh -p 2222 user@192.168.1.100

鍵認証の設定

ssh の認証方法は大きく2つある:パスワード認証と鍵認証だ。

パスワード認証 は接続のたびにパスワードを入力する方式で、手軽だが弱い。ブルートフォース攻撃の標的になるし、パスワードが漏れたら終わりだ。

鍵認証 は公開鍵と秘密鍵のペアを使う方式で、パスワードより圧倒的に安全だ。秘密鍵が手元にない限りログインできないため、ブルートフォース攻撃が通用しない。本番サーバーでは鍵認証が必須と考えていい。

鍵の生成

2026年の標準は Ed25519 だ。RSA より短い鍵長で同等以上のセキュリティを提供し、署名・検証も高速になる。

bash
ssh-keygen -t ed25519 -C "your_email@example.com"

実行すると保存先とパスフレーズを聞かれる。パスフレーズは設定することを強く推奨する。秘密鍵が流出した場合の最後の防壁になる。

RSA を使わなければならない環境(古いサーバーなど)では、最低 4096bit を指定する:

bash
ssh-keygen -t rsa -b 4096 -C "your_email@example.com"

公開鍵をサーバーに登録する

最も簡単な方法は ssh-copy-id を使うことだ:

bash
ssh-copy-id user@server

これでローカルの公開鍵(~/.ssh/id_ed25519.pub)がサーバーの ~/.ssh/authorized_keys に追加される。

ssh-copy-id が使えない環境では手動で登録する:

bash
cat ~/.ssh/id_ed25519.pub | ssh user@server "mkdir -p ~/.ssh && cat >> ~/.ssh/authorized_keys"

パーミッションの設定

ssh はパーミッションに厳格だ。以下の設定でないと鍵認証が拒否される場合がある(Linuxのパーミッションについて詳しくはchmod・chownガイドを参照):

bash
# サーバー側
chmod 700 ~/.ssh
chmod 600 ~/.ssh/authorized_keys

# クライアント側
chmod 700 ~/.ssh
chmod 600 ~/.ssh/id_ed25519
chmod 644 ~/.ssh/id_ed25519.pub

ssh-agent で鍵を管理する

パスフレーズ付きの鍵を使っている場合、接続のたびに入力するのは面倒だ。ssh-agent に鍵を登録すると、セッション中はパスフレーズなしで使えるようになる:

bash
eval "$(ssh-agent -s)"
ssh-add ~/.ssh/id_ed25519

ssh 設定ファイル

~/.ssh/config を設定すると、接続パラメータを記憶させて入力を大幅に省ける。

基本構文

text
Host myserver
    HostName 192.168.1.100
    User deploy
    Port 2222
    IdentityFile ~/.ssh/id_ed25519

これで ssh myserver だけで ssh -p 2222 -i ~/.ssh/id_ed25519 deploy@192.168.1.100 と同じ接続ができる。

ワイルドカード

複数のサーバーに共通設定を適用できる:

text
Host *.example.com
    User admin
    IdentityFile ~/.ssh/id_ed25519_work

接続維持(KeepAlive)

SSH 接続がアイドル状態で切断されるのを防ぐ:

text
Host *
    ServerAliveInterval 60
    ServerAliveCountMax 3

60秒ごとにサーバーへ生存確認を送り、3回応答がなければ切断する。

多段 SSH(ProxyJump)

踏み台サーバー(bastion)を経由して内部サーバーに接続する構成はよくある。ProxyJump を使えば1コマンドで多段接続できる:

text
Host bastion
    HostName bastion.example.com
    User admin

Host internal
    HostName 10.0.0.5
    User deploy
    ProxyJump bastion

ssh internal で bastion を自動的に経由して内部サーバーに接続される。

接続の多重化(ControlMaster)

同じサーバーへの2回目以降の接続を高速化する。最初の接続でソケットを作り、以降の接続はそれを再利用する:

text
Host *
    ControlMaster auto
    ControlPath ~/.ssh/sockets/%r@%h-%p
    ControlPersist 600

ソケット用のディレクトリは事前に作っておく:

bash
mkdir -p ~/.ssh/sockets

ControlPersist 600 は最後の接続が閉じてから600秒間ソケットを維持する設定だ。デプロイスクリプトなど短時間に同じサーバーへ何度も接続する場面で効果が大きい。

ポートフォワーディング

ssh のポートフォワーディングは、暗号化されたトンネルを通じてポートを転送する機能だ。ファイアウォールの内側にあるサービスへのアクセスや、ローカルサービスの外部公開に使える。

ローカルフォワード(-L)

リモートサーバーのポートをローカルに転送する。最もよく使うパターンだ:

bash
ssh -L 8080:localhost:3000 user@server

これでローカルの localhost:8080 にアクセスすると、リモートサーバーの localhost:3000 に転送される。リモートの開発サーバーやダッシュボードにローカルからアクセスしたい場面で使う。

実践例:リモートの PostgreSQL に接続する

bash
ssh -L 5433:localhost:5432 user@db-server

別のターミナルを開いて:

bash
psql -h localhost -p 5433 -U myuser mydb

リモートの PostgreSQL にあたかもローカルで動いているかのように接続できる。tmux を使えば複数ターミナルの管理も楽だ。

リモートフォワード(-R)

ローカルのポートをリモートサーバー経由で外部に公開する:

bash
ssh -R 8080:localhost:3000 user@server

リモートサーバーの localhost:8080 にアクセスすると、あなたのローカルの localhost:3000 に転送される。ローカルで動かしている開発中のアプリをチームに見せたい場面で使える。

ダイナミックフォワード(-D)

SOCKS プロキシとして機能させる:

bash
ssh -D 1080 user@server

ブラウザの SOCKS プロキシに localhost:1080 を設定すると、すべてのトラフィックが ssh トンネルを経由する。公共 Wi-Fi での暗号化や、地域制限のあるサービスへのアクセスに使える。

バックグラウンドでトンネルを維持する

フォワーディングだけが目的でシェルは不要な場合、-fN オプションを使う:

bash
ssh -fNL 8080:localhost:3000 user@server

-f はバックグラウンド実行、-N はリモートコマンドを実行しない指定だ。

rsync とは

rsync は差分転送に特化したファイル同期ツールだ。ファイルの変更部分だけを検出して転送するため、2回目以降の同期が高速になる。

scp との違い を明確にしておこう:

機能scprsync
転送方式毎回全体をコピー差分のみ転送
中断からの再開不可--partial で対応
圧縮なし-z で対応
除外パターンなし--exclude で柔軟に制御
ミラーリング不可--delete で対応

大量のファイルを扱う場面では rsync 一択だ。

基本構文:

bash
rsync [オプション] 転送元 転送先

よく使うオプション:

  • -a(archive):パーミッション・タイムスタンプ・所有者を保持する再帰コピー
  • -v(verbose):転送中のファイル名を表示
  • -z(compress):転送データを圧縮
  • -n(dry-run):実際には転送せず、何が起こるか確認
  • --progress:転送の進捗を表示

rsync 実践パターン

基本的なファイル同期

ローカルからリモートへ:

bash
rsync -avz ./dist/ user@server:/var/www/

リモートからローカルへ:

bash
rsync -avz user@server:/var/log/ ./logs/

実行前にドライランで確認するのは鉄則だ。-n オプションを追加するだけでいい:

bash
rsync -avzn ./dist/ user@server:/var/www/

除外パターン

特定のファイルやディレクトリを転送対象から除外する:

bash
rsync -avz --exclude='node_modules' --exclude='.git' --exclude='.env' ./project/ user@server:/app/

除外パターンが多い場合はファイルにまとめる。.rsyncignore を作成して:

text
node_modules
.git
.env
*.log
.DS_Store

このファイルを --exclude-from で指定する:

bash
rsync -avz --exclude-from='.rsyncignore' ./project/ user@server:/app/

バックアップ

ミラーバックアップ はソースと完全に一致させる。--delete でソースにないファイルはバックアップ先からも削除される:

bash
rsync -avz --delete /data/ /backup/data/

世代管理バックアップ は削除されたファイルを日付付きディレクトリに退避する:

bash
rsync -avz --backup --backup-dir="/backup/$(date +%Y%m%d)" --delete /data/ /backup/current/

/backup/current/ には常に最新の状態が入り、削除・更新されたファイルは /backup/20260308/ のようなディレクトリに保存される。

デプロイスクリプト

Web アプリのデプロイを rsync で自動化する実践例:

bash
#!/bin/bash
set -euo pipefail

REMOTE_USER="deploy"
REMOTE_HOST="server.example.com"
REMOTE_PATH="/var/www/myapp"
LOCAL_PATH="./dist/"

echo "Starting deployment to ${REMOTE_HOST}..."

rsync -avz --delete \
  --exclude='.git' \
  --exclude='node_modules' \
  --exclude='.env' \
  --exclude='*.log' \
  "${LOCAL_PATH}" "${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_PATH}/"

echo "Deployment complete."

set -euo pipefail はスクリプトのエラーハンドリングに必須だ。エラーが発生した時点でスクリプトが停止する。堅牢なシェルスクリプトの書き方はシェルスクリプト実践ガイドで詳しく解説している。

応用テクニック

SSH エージェント転送(ForwardAgent)

踏み台サーバーから、さらに内部サーバーに SSH 接続する場合がある。踏み台にも秘密鍵を置くのはセキュリティリスクだ。エージェント転送を使えば、ローカルの鍵をトンネル経由で使える。

text
# ~/.ssh/config
Host bastion
    HostName bastion.example.com
    User admin
    ForwardAgent yes

Host internal-*
    User deploy
    ProxyJump bastion
    ForwardAgent yes
bash
# bastion 経由で internal に接続し、そこから git pull できる
ssh internal-web
git pull  # ローカルの鍵が転送されるので認証が通る

セキュリティ上の注意: ForwardAgent yes は信頼できるサーバーにのみ設定すること。踏み台の root 権限を持つユーザーがエージェントソケットにアクセスして、あなたの鍵を使える状態になる。Host * での設定は避け、必要なホストにだけ明示的に指定しよう。

rsync の中断再開と進捗表示(-P)

大ファイルの転送で接続が切れた場合に、途中から再開できる。

bash
# -P は --partial --progress のショートカット
rsync -avzP user@server:/data/large-dump.sql.gz ./backups/

--partial は中断時に部分的に転送されたファイルを保持する(デフォルトでは削除される)。次回の rsync で残りの部分だけを転送する。--progress は転送中のファイルの進捗をリアルタイム表示する。

bash
# 複数の大ファイルを中断再開可能な状態で同期
rsync -avzP --partial-dir=.rsync-partial user@server:/data/ ./local-data/

--partial-dir を指定すると、部分ファイルを隠しディレクトリに退避する。転送完了後に自動削除されるので、中途半端なファイルが作業ディレクトリを汚さない。

rsync の帯域制限(--bwlimit)

本番サーバーへの大量転送でネットワークを圧迫したくない場合に使う。

bash
# 帯域を 5MB/s に制限
rsync -avz --bwlimit=5000 ./release/ user@production:/app/

# 業務時間帯は控えめに、夜間はフルスピードで
rsync -avz --bwlimit=1000 ./data/ user@server:/backup/

--bwlimit の単位は KBytes/s だ。5000 = 約 5MB/s。デプロイスクリプトに入れておくと、「デプロイしたらサイトが遅くなった」を防げる。

sshfs でリモートファイルシステムをマウント

リモートサーバーのディレクトリをローカルにマウントして、普通のファイルとして操作できる。sshfs は内部的に SFTP を使っている。

bash
# リモートをローカルにマウント
mkdir -p ~/mnt/server
sshfs user@server:/var/www ~/mnt/server

# ローカルのエディタで直接編集できる
code ~/mnt/server/index.html

# アンマウント
fusermount -u ~/mnt/server

~/.ssh/config の設定が自動的に使われるので、sshfs myserver:/var/www ~/mnt/server のように短縮名も使える。

ただし、ネットワーク遅延の影響を直接受けるため、大量のファイル操作には向かない。設定ファイルの確認や小規模な編集に適している。

セキュリティの注意点

ssh とリモートサーバーのセキュリティは表裏一体だ。最低限やるべき対策をまとめる。

OpenSSH 10.0 の主な変更

OpenSSH 10.0(2025年4月)で重要なセキュリティ変更が入った:

  • DSA 完全削除:DSA 鍵は生成も使用もできなくなった。Ed25519 に移行が必要
  • ML-KEM 対応:ポスト量子暗号の鍵交換アルゴリズム(mlkem768x25519-sha256)がデフォルト有効に。量子コンピュータへの事前対策

CVE-2025-26465(MITM 攻撃)

OpenSSH 6.8p1〜9.9p1 で VerifyHostKeyDNS が有効な場合、中間者攻撃(MITM)が成立する脆弱性が Qualys TRU により発見された9.9p2(2025年2月)で修正済み だ。なお VerifyHostKeyDNS はデフォルト無効のため、明示的に有効化しているユーザーのみ影響を受ける。

sshd_config の推奨設定

サーバー側の /etc/ssh/sshd_config で以下を設定する:

PasswordAuthentication no は鍵認証のセットアップが完了してから有効にすること。先に無効にするとサーバーに入れなくなる。

rsync のセキュリティ

rsync 3.4.0(2025年1月)でGoogle Cloud研究者が発見した6件の重大CVEが修正された(CVE-2024-12084: ヒープバッファオーバーフローによるRCE等)。3.3.x 以前を使っている場合は早急にアップデートすべきだ。 3.4.1 はリグレッション修正のマイナーリリースなので、3.4.1 を推奨する。

バージョン確認:

bash
rsync --version

ファイアウォールと fail2ban

SSH ポート(デフォルト 22)へのアクセスを IP で制限する:

bash
# ufw の場合
sudo ufw allow from 203.0.113.0/24 to any port 22
sudo ufw deny 22

fail2ban はログイン試行の失敗を検知して自動的に IP をブロックする。SSH のブルートフォース対策として定番だ:

bash
sudo apt install fail2ban
sudo systemctl enable fail2ban
sudo systemctl start fail2ban

よくある質問

SSH の鍵認証はパスワード認証より安全?

圧倒的に安全だ。パスワード認証はブルートフォース攻撃やフィッシングに弱い。鍵認証は暗号学的な鍵ペアを使うため、秘密鍵ファイルがなければログインは数学的に不可能だ。本番サーバーでは鍵認証を設定した後、パスワード認証を必ず無効化しよう。

同じ SSH 鍵を複数のサーバーで使える?

使える。同じ公開鍵(~/.ssh/id_ed25519.pub)を各サーバーの ~/.ssh/authorized_keys に登録すればいい。ただし、セキュリティ意識の高いチームでは環境ごとに鍵を分ける(本番用と開発用で別の鍵)ケースもある。万が一の漏洩時に影響範囲を限定するためだ。

"Permission denied (publickey)" エラーの直し方は?

順番に確認しよう:(1) サーバー側で ~/.ssh700~/.ssh/authorized_keys600 になっているか。(2) 正しい公開鍵が authorized_keys に登録されているか。(3) sshd_configPubkeyAuthentication yes が設定されているか。(4) ssh -vvv user@server で詳細なエラー理由を確認する。

scp と rsync の違いは?

scp は毎回ファイル全体をコピーするが、rsync は変更された部分だけを転送する(差分転送)。rsync は中断からの再開(--partial)、圧縮(-z)、除外パターン(--exclude)、ミラーリング(--delete)もサポートする。一度きりのコピー以外では rsync 一択だ。

rsync の末尾スラッシュって本当に挙動が変わる?

変わる。rsync で最もよくあるミスの一つだ。rsync -avz src/ dest/src中身dest に同期する。rsync -avz src dest/src ディレクトリ自体dest/src/ に同期する。意図しないネスト構造を避けるため、確信がなければ必ず -n でドライランしよう。

rsync で SSH の非標準ポートを使うには?

-e フラグで指定する:rsync -avz -e 'ssh -p 2222' ./files/ user@server:/data/~/.ssh/config でポートを設定済みなら、ホスト名エイリアスを使えば rsync が自動的にその設定を使う。

ForwardAgent は安全?

信頼できるサーバーにのみ設定すること。ForwardAgent yes を有効にすると、そのサーバーの root 権限を持つユーザーが転送されたSSH鍵を使って、あなたとして他のサーバーに認証できてしまう。Host * でのグローバル設定は避け、踏み台サーバーや自分が管理する CI サーバーにだけ明示的に指定しよう。

関連記事

まとめ

sshrsync はリモートサーバー操作の基盤だ。鍵認証で安全に接続し、設定ファイルで効率化し、rsync で高速にファイルを同期する。

押さえておくべきポイント:

  • 鍵は Ed25519 を使う。DSA は OpenSSH 10.0 で削除済み
  • ~/.ssh/config で接続パラメータをまとめる。ProxyJump で多段接続も1コマンド
  • ポートフォワーディングでリモートサービスにローカルからアクセスできる
  • rsync は -avz が基本。-n のドライランで必ず確認してから実行
  • 末尾スラッシュの有無で挙動が変わる。これは覚えるまで毎回確認
  • サーバー側では PasswordAuthentication noPermitRootLogin no を設定する

ssh と tmux を組み合わせると、リモートでのターミナル作業が格段に快適になる。