Dockerコンテナを新しいサーバーへ移行する:確実な「手動」テクニック

Docker tutorial - IT technology blog
Docker tutorial - IT technology blog

5分で完了(クイックスタート)

Docker Hubを経由せずに、サーバーAからサーバーBへコンテナを急いで移動させたいですか?ここでは、最短で移行を完了させる手順を紹介します。コンテナ名を web_app、データが web_data ボリュームにあると仮定します。

  1. 旧サーバーにて: コピー時のデータ破損を防ぐため、コンテナを安全に停止させます。
    docker stop web_app
    docker commit web_app web_app_backup
    docker save -o web_app_image.tar web_app_backup
  2. 新サーバーにファイルを転送: 圧縮機能があり、接続が切れても再開できる rsync を使用します。
    rsync -avzP web_app_image.tar [email protected]:/root/
  3. 新サーバーにて: イメージをロードして実行します。
    docker load -i web_app_image.tar
    docker run -d --name web_app web_app_backup

これは理想的なシナリオです。実際には、アプリケーションにボリューム(データ)がある場合、イメージだけを移動させるのは、家具をすべて古い家に残して新しい家へ引っ越すようなものです。

Dockerレジストリがあるのに、なぜ手動で行うのか?

Docker Hubやプライベートレジストリを使えば簡単です。しかし、システム運用の現場では、以下のような「手動」で対応せざるを得ない状況に直面することがあります。

  • エアギャップ環境: サーバーが完全なオフラインの学内・社内ネットワーク内にあり、インターネット接続がない場合。
  • 厳しいセキュリティ要件: イメージに機密設定や独自のソースコードが含まれており、クラウドへのアップロードが禁止されている場合。
  • ホットフィックス: コンテナ内で直接コードを修正してしまい、Dockerfileからビルドし直すのが手間な場合。
  • 帯域の節約: 2GBのファイルを1GbpsのLAN経由で転送する方が、レジストリにアップロードしてダウンロードするよりも遥かに高速です。

安全な移行プロセス:急がば回れ

ステップ1:器(コンテナイメージ)のパッケージング

多くの人が Docker Hub から取得した元のイメージをそのまま docker save してしまいますが、これは間違いです!コンテナ内でツールをインストールしたり、設定を変更したりした場合、それらの変更は消えてしまいます。ここで重要になるのが commit コマンドです。

# コンテナの現在の状態を新しいイメージとして保存
docker commit web_app web_app_migrated:v1

# tarファイルに書き出し
docker save -o web_app_migrated.tar web_app_migrated:v1

注意:commit は書き込み可能レイヤー(writable layer)のみをパッケージ化するもので、ボリューム内のデータには一切触れません。

ステップ2:魂(ボリュームデータ)の移動

データこそが最も価値のあるものです。まず、ボリュームがディスク上のどこにあるかを確認しましょう。

docker inspect web_app | grep -A 10 "Mounts"

複雑なJSONが表示されたときは、JSON Formatter を使って整形すると、Source パスが見やすくなり、目が疲れません。

通常、データは /var/lib/docker/volumes/ にあります。ここでは scp ではなく rsync を使いましょう。なぜなら、rsync は所有権(owner)とパーミッションを保持できるからです。これは、MySQL 8.0 などのデータベースを新しいマシンで起動する際に「Permission denied」エラーを防ぐために非常に重要です。

# データフォルダを新サーバーに転送し、ファイルの権限を維持する
rsync -avzP /data/my_app/ [email protected]:/data/my_app/

データが数十GBある場合の対処法

ボリュームが50GBを超える場合、単純な rsync では数時間かかることがあります。私の経験から言えば、zstd を使って圧縮するのがベストです。gzip よりも3倍速く、圧縮率も非常に優れています。

tar -I zstd -cf web_data.tar.zst /var/lib/docker/volumes/my_volume/_data
rsync -avzP web_data.tar.zst [email protected]:/root/

新サーバーで解凍した後、UID/GIDを確認してください。旧マシンで mysql ユーザーのIDが 999 だった場合、コンテナがファイルを読み取れるように新サーバーでも一致させる必要があります。

「小さくても効果絶大」な注意点

  • ディスク容量の確認: 5GBのtarファイルでも、注意しないと /root パーティションがいっぱいになることがあります。実行前に df -h で確認しましょう。
  • Docker Composeを活用: 5行もある docker run コマンドを覚えようとしないでください。docker-compose.yml ファイルを新マシンにコピーし、イメージ名を修正するだけで完了です。
  • 容量の照合: コピー後、両方のサーバーで du -sh を実行します。数KBでも差がある場合は、すぐに rsync のログを確認してください。
  • ゴミ掃除: 作業が終わったら、すぐに .tar ファイルを削除してください。サーバーのリソースを無駄に消費させないようにしましょう。

手動でのDocker移行は決して時代遅れではありません。クラウドやサードパーティのレジストリに頼れない状況では、不可欠なサバイバルスキルです。rsyncsave/load を丁寧に行えば、システムを完全にコントロールできるようになります。

Share: