以前、FedoraのDockerで構築したWordPressサーバが御座います。
その後、FedoraがDockerのサポートを終了し、代わりにPodmanが導入されました。
過去に、このようなコンテナ・ポッドの運用環境を変えなければならない状況が、現実に発生しました。
一方、災害や機器の故障に備えて、ポッドの内容をすべて、バックアップしておきたいと考えておりました。
この2つの理由から、コンテナ・ポッドを、別の実行環境(別のPCや別のOS)にいつでもマイグレーション(移動)できる環境を整えておくのも悪いことではないと思います。
というわけで、割りと本気で、WordPressの運用環境をPodmanで構築して、ポッドのマイグレーションに備えたいと思います。
目次
Windows 10でPodman.exeを実行
ポッドの運用環境ですが、Windows 10 Proを使用しました。
DockerやLinuxディストリビューション(UbuntuとかCentOSとか)の知識は一切不要だと思います。
Podmanのインストール手順はこちらになります。
インストール後、マシンを初期化して準備完了になります。
管理用のphpMyAdminも実行
以前、同様の記事を作成致しましたが。
こちらの内容に加えまして、Mysqlのメンテナンスのため、今回は同じポッドの中でphpMyAdminを実行したいと思います。
ちなみに、WordPressの公式イメージと同時に起動すると、ポート番号80がぶつかります。
このため、phpMyAdmin側のApacheのポート番号を変更してから起動する必要がありました。phpMyAdminの公式イメージを使用させて頂こうと思います。
2022年11月19日現在、バージョンは5.1.1のようです。
永続化ボリューム構成
そのようなわけで、今回はMysql、WordPressのWebサーバ、phpMyAdminの3つのコンテナを起動します。
それらのコンテナ内で、データがどこに保存されるかを確認しておこうと思います。
調べ方の詳細はこちらの記事になります。
Mysqlコンテナの永続化ボリューム
Mysqlの永続化ボリュームは、既定では。
- /var/lib/mysql
こちらが匿名ボリュームにマウントされていました。
よって、Mysqlコンテナは、こちらをバックアップ・リストアの対象にしようと思います。
※22.11.20追記:データベースは、ボリュームをバックアップしても、マイグレーション先でうまく動きませんでした。リストアに使用するデータは別途SQLでダンプしようと思います。
この記事はmysqlイメージを使用しています。Mariadbイメージではありません。
Mariadbの場合、この記事の内容とバックアップ・リストア時の動作が異なる可能性が御座います。
WordPressコンテナの永続化ボリューム
WordPressの永続化ボリュームは下記になります。
- /var/www/html
WordPressで作成した記事の文章はMysqlに格納されますが、WordPress本体のほか、プラグインやアップロードされた画像等のコンテンツは、こちらのディレクトリに格納されるようです。
phpMyAdminの永続化ボリューム
先ほど確認しましたphpMyAdminの現在のバーションは、既定でボリュームのマウントはされていないようです。
設定ファイルを/run/secrets ディレクトリに置いて運用することも可能のようですが、今回の目的では必須ではありません。
よって、phpMyAdminのコンテナについて、何かバックアップが必要なデータは置かない、ここではバックアップ不要とします。
ポッド運用スクリプト構成
いよいよ、具体的にポッドを作ったりバックアップするための、スクリプトを作成しようと思います。
wp-podというフォルダを作成。
次の4つのファイルを作ろうと思います。
- ポッド作成: 1_create.bat
- ポッドのバックアップ: 2_backup.bat
- ポッド削除: 3_rm.bat
- ポッドのリストア: 4_restore.bat
内容は、ほぼpodmanのコマンドを実行するのみの内容のため、シンプルにバッチファイルにしました。
PowerShellのps1ファイルで作成しても全く問題無いと思います。
こちらのフォルダに、バックアップしたコンテナ内のデータや、コンテナを作成するためのイメージ、ポッドを再生するためのyamlファイルが作成したいと思います。
バッチファイルは必ずANSIで保存
Windows 10、Windows 11のメモ帳を利用する場合は注意が必要です。
バッチファイルを作成する場合、必ずANSIで保存する必要があります。
文字コード違いは、ポッドがうまく操作できない不具合の原因になってしまいます。
ファイルを保存する際に必ず文字コードをご確認下さい。
WordPress運用スクリプトの例
ポッド作成: 1_crate.bat
最初にWordPressのポッドを作成するバッチファイルです。
コマンドは4つ。
ポッドを作成後、コンテナを3つ作成する内容です。
例によって、ポート番号や、データベース名、ユーザ名、パスワードは適宜変更して下さい。
使用するイメージのバージョンであるタグ指定も必要に応じて変更して下さい。
データベースコンテナがローカルボリュームとして/backupをマウントしているのは、データベースのバックアップに使用するためです。
:main
rem WordPress用ポッド作成
podman pod create ^
--name wp-pod -p 8080:80/tcp,8090:8090/tcp
rem Mysqlコンテナ作成
podman.exe run --restart=always ^
--pod=wp-pod ^
--name=wp-db ^
-e MYSQL_ROOT_PASSWORD="wordpress" ^
-e MYSQL_DATABASE="wordpress" ^
-e MYSQL_USER="wordpress" ^
-e MYSQL_PASSWORD="wordpress" ^
-v .:/backup ^
-d docker.io/library/mysql:latest
rem 名前付きボリュームは要らないか
rem ダンプ用に/backupをマウント
rem -v wp-db-vol:/var/lib/mysql ^
rem WordPressコンテナ作成
podman.exe run --restart=always ^
--pod=wp-pod ^
--name=wp-web ^
-e WORDPRESS_DB_NAME="wordpress" ^
-e WORDPRESS_DB_USER="wordpress" ^
-e WORDPRESS_DB_PASSWORD="wordpress" ^
-e WORDPRESS_DB_HOST="127.0.0.1" ^
-d docker.io/library/wordpress:latest
rem phpMyAdminコンテナ作成
podman.exe run --restart=always ^
--pod=wp-pod ^
--name=wp-phpmyadmin ^
-e PMA_HOST="127.0.0.1" ^
-e APACHE_PORT=8090 ^
-d docker.io/library/phpmyadmin:latest
特にエラー無く、正常に起動しました。
WordPressとphpMyAdminの動作確認
ポッド起動後、ポート番号8080のWordPress、8090のphpMyAdminにアクセスしてみます。
http://localhost:8080
http://localhost:8090
WordPressの初期設定画面が表示され、正常に起動していることがわかります。
起動時のオプションでMysqlサーバは指定済みのため、ユーザ名とパスワードを入力してログイン可能です。ここでは次の内容になります
- ユーザ名: wordpress
- パスワード: w0rdpr3ss
WordPressサイトを構築後にアクセスすると、wpデータベースにテーブルが作成されていることを確認できました。
これでWordPressのメンテナンスを行ううえで、phpMyAdminを利用する事が可能になりました。便利ですね!
ポッドのバックアップ: 2_backup.bat
バックアップの前に。ポッドのデータが入るボリュームについて。
名前付きボリューム・匿名ボリュームどちらが利便性が高いか考えました。
コンテナ間のファイルのやり取りは必要無いこと、ポッドを作り直すタイミングで、名前付きボリュームを使用する必要性が無いことから、匿名ボリュームを前提にしようと思います。
つまり、ポッドのマイグレーション時、ボリュームは持ち越さずに全部消える前提。
必要なデータはすべてバックアップして、すべてリストアする設計にしたいと思います。
バックアップ・リストアの詳細はこちらの記事になります。こちらの内容に基づき、バックアップ・スクリプトを作成しました。
んー。もっと整頓できそうですね。
イメージのファイル名はimage_から、コンテナのファイル名はcontainer_から、ボリュームは(略
※22.11.20追記:データベースはダンプしてもマイグレートできない可能性が御座います。別途、データベースはファイルとしてダンプして保存する処理を追加しました。
:start
pushd %~dp0
set pod=wp-pod
set containers=wp-web wp-db wp-phpmyadmin
:main
rem wp-podのバックアップ phpMyAdmin付き
rem イメージをバックアップ
set imgtag=docker.io/library/wordpress:latest
set imgfile=image_wordpress.tar
if NOT EXIST %imgfile% podman image save -o %imgfile% %imgtag%
set imgtag=docker.io/library/mysql:latest
set imgfile=image_mysql.tar
if NOT EXIST %imgfile% podman image save -o %imgfile% %imgtag%
set imgtag=docker.io/library/phpmyadmin:latest
set imgfile=image_phpmyadmin.tar
if NOT EXIST %imgfile% podman image save -o %imgfile% %imgtag%
rem ポッドとコンテナ設定yamlの生成
podman generate kube wp-pod > wp-pod.yaml
rem データベースのダンプ
set ctn=wp-db
podman exec -it %ctn% sh -c "/bin/mysqldump --user=wordpress --password=wordpress wordpress > /backup/%ctn%-mysql.sql"
rem podman container pause %containers%
podman container stop %containers%
rem コンテナのイメージ化と保存
set container=wp-web
podman container commit %container% %container%-image
podman image save -o container_%container%.tar %container%-image
set container=wp-db
podman container commit %container% %container%-image
podman image save -o container_%container%.tar %container%-image
set container=wp-phpmyadmin
podman container commit %container% %container%-image
podman image save -o container_%container%.tar %container%-image
rem wp-podポッドのボリュームバックアップ
set container=wp-web
set fn=volume_%container%.tar.gz
set mp=/var/www/html
podman run --rm --volumes-from %container% -v .:/backup fedora tar zcvf /backup/%fn% %mp%
set container=wp-db
set fn=volume_%container%.tar.gz
set mp=/var/lib/mysql
podman run --rm --volumes-from %container% -v .:/backup fedora tar zcvf /backup/%fn% %mp%
rem 名前付きボリュームのバックアップ
rem podman run --rm -v %container%-vol:/var/lib/mysql -v .:/backup fedora tar zcvf /backup/%fn% %mp%
rem podman container unpause %containers%
podman container start %containers%
:end
popd
Windows版Podmanコマンドで、特に問題なくバックアップできた感じです。
運用フォルダにバックアップファイルが作成されました。
具体的に次の内容になります。
- image_tarファイルが3つ。コンテナ作成用。
- yamlファイルが1つ。ポッドの再生用。
- container_tarファイルが3つ。コンテナそのもの。(ボリュームを除く)
- volume_ファイルが2つ。コンテナのボリュームマウント部分。
- sqlファイルが1つ。データベースのダンプ。
こちらを保存しておけば、別の環境でもポッドが再生できる、ということになります。
ポッド削除: 3_rm.bat
次にポッドの削除スクリプトです。
他のポッドと干渉しないように、必ずコンテナ名・ポッド名を指定します。
:start
pushd %~dp0
set pod=wp-pod
set containers=wp-db wp-web wp-phpmyadmin
:ls-pod-before
podman container ls -a
podman pod ls
:rm-pod
podman container stop %containers%
podman container rm %containers%
podman pod stop %pod%
podman pod rm %pod%
:ls-pod-after
podman container ls -a
podman pod ls
:end
popd
確認のため、lsコマンドでポッドとコンテナの一覧を表示しています。
消去前と消去後。
完全にポッドが消えました。しかし実は匿名ボリュームが残っています。この構文では、ボリュームは残るのですね。
ボリュームが消える条件がよくわからないのですが・・・(調査不足
この後リストアが正しく行えるか検証するため、ボリュームとイメージも消しておきます。
podman volume ls
podman volume prune
podman image ls
podman image rm --all
ポッドのリストア: 4_restore.bat
バックアップしたファイルを使用して、ポッドをリストアしたいと思います。
少し手を抜いて、コンテナは再現せず、イメージとyamlファイルとボリュームからリストアしていますのでご注意下さい。
※22.11.20追記:データベースは、ボリュームをリストアしてもマイグレートできない可能性が御座います。
:start
pushd %~dp0
set pod=wp-pod
set containers=wp-web wp-db wp-phpmyadmin
:main
rem イメージリストア
set img=mysql
podman image load < image_%img%.tar
set img=phpmyadmin
podman image load < image_%img%.tar
set img=wordpress
podman image load < image_%img%.tar
rem yaml再生 ポッドとコンテナ作成
podman play kube %pod%.yaml
rem yamlファイルから起動したコンテナの名前を変更
set container=wp-web
podman container rename %pod%-%container% %container%
set container=wp-db
podman container rename %pod%-%container% %container%
set container=wp-phpmyadmin
podman container rename %pod%-%container% %container%
: restore_start
podman container pause %containers%
podman container stop %containers%
:restore_volume
rem 匿名ボリュームをリストア
set container=wp-web
set fn=volume_%container%.tar.gz
podman run --rm --volumes-from %container% -v .:/backup fedora bash -c "cd / && tar zxvf /backup/%fn%"
:restore_end
podman container unpause %containers%
podman container start %containers%
:restore_db
rem データベースをリストア
set ctn=wp-db
podman exec -it %ctn% sh -c "/bin/mysql --user=wordpress --password=wordpress wordpress < /backup/%ctn%-mysql.sql"
:end
popd
実行すると、ポッドが再生され、ボリュームがリストアされます。
データベースのリストアですが、タイミングが早すぎて、コンテナが起動する前に動作しているようです。
データベースが空の場合は、SQLリストアを後から、コンテナが起動してから行う必要がありました。
ポートフォワード
Windows版のPodman.exeでは、WSL2の仕様から、他のPCからPodmanのサービスへ直接アクセスすることができません。
ポートフォワードを有効にして、ファイアウォールの送受信を許可する必要があります。
そのためのスクリプトも作っておきます。
5_portforward.bat
こちらのバッチファイルは、管理者権限で実行する必要がありますのでご注意下さい。
それと、PC再起動後にポッドを動かせるように、こちらのスクリプトでマシンとポッドを起動しています。
※22.11.25修正:IPアドレスを取り出す構文に不具合がありましたので修正しました。不具合の内容:IPアドレスが0で終わる場合、正しく取り出せませんでした。構文に\.を追加しました。
※22.12.8追記:ファイアウォールのルールが無限に追加されてしまうため、ルールが存在するか判定するIF文を追加しました。
rem podmanマシン起動
podman machine start
rem podmanマシンのIPアドレス取得
FOR /F %%i in ('podman.exe machine ssh "cat /proc/net/fib_trie | sed -e 's/^[ \-\|\+]*[ \-]*//' | grep '[\d]*\.' |grep -v -e '0.0.0.0' -e '^127\.[\d]*' -e '\/' -e '\.0$' -e '\.255$'"') DO set IPADR=%%i
rem ポッド起動
set pod=wp-pod
podman pod start %pod%
rem ポートフォワード
set PTNB=8080
netsh interface portproxy add v4tov4 listenaddress=0.0.0.0 listenport=%PTNB% connectaddress=%IPADR% connectport=%PTNB%
rem 受信ルール
netsh advfirewall firewall show rule name= "TCP %PTNB%" dir=in
IF %ERRORLEVEL% GEQ 1 (
netsh advfirewall firewall add rule name= "TCP %PTNB%" dir=in action=allow protocol=TCP localport=%PTNB%
)
rem 送信ルール
netsh advfirewall firewall show rule name= "TCP %PTNB%" dir=out
IF %ERRORLEVEL% GEQ 1 (
netsh advfirewall firewall add rule name= "TCP %PTNB%" dir=out action=allow protocol=TCP localport=%PTNB%
)
rem ポートフォワード
set PTNB=8090
netsh interface portproxy add v4tov4 listenaddress=0.0.0.0 listenport=%PTNB% connectaddress=%IPADR% connectport=%PTNB%
rem 受信ルール
netsh advfirewall firewall show rule name= "TCP %PTNB%" dir=in
IF %ERRORLEVEL% GEQ 1 (
netsh advfirewall firewall add rule name= "TCP %PTNB%" dir=in action=allow protocol=TCP localport=%PTNB%
)
rem 送信ルール
netsh advfirewall firewall show rule name= "TCP %PTNB%" dir=out
IF %ERRORLEVEL% GEQ 1 (
netsh advfirewall firewall add rule name= "TCP %PTNB%" dir=out action=allow protocol=TCP localport=%PTNB%
)
バックアップ後、phpMyAdminが動かない問題
バックアップ時、コンテナを停止、バックアップ後再起動しましたが。
phpMyAdminに、アクセスできなくなってしまいました。おそらく、データベースのコンテナが停止した影響だと思います。
回避策として、phpMyAdminのコンテナを作り直すスクリプトを作成しました。
6_phpMyAdmin.bat
podman container stop wp-phpmyadmin
podman container rm wp-phpmyadmin
rem phpMyAdminコンテナ作成
podman.exe run --restart=always ^
--pod=wp-pod ^
--name=wp-phpmyadmin ^
-e PMA_HOST="127.0.0.1" ^
-e APACHE_PORT=8090 ^
-d docker.io/library/phpmyadmin:latest
WordPress本体につきましては、作成したスクリプトで、なんとか(状況によって)バックアップ・マイグレーションする事ができるようになりました。
スクリプトは他のコンテナに干渉しないように、ポッド名とコンテナ名を指定して動くようにしましたので、他のポッドとの併用が可能になりました。
データベースコンテナですが、ボリュームをリストアしても、以前の状態を復元できない場合があり、別途、ダンプしたSQLファイルをリストアしています。
以前、mysqlを使用していた影響かもしれません。新しいポッドのデータベースはmariadbに変更して、リストアしてみようと思います。
一方で。
PodmanコマンドがWindows環境で動くため、気軽に実行できるのは大きな進歩だと思います。
さてと。マイグレーション先の環境ができましたので、マイグレーション元のFedoraで無理やり動かしているDocker版のWordPressのデータをバックアップしようと思います。
それではまた!