コンテナの中からrebootできない問題
Debian Stretchで採用されているsystemd 232では、systemd-nspwanコンテナの中でreboot
コマンドを叩いても、コンテナが停止するだけで再起動してくれません。
このissueが関連しているようで、
このpull requestがパッチのようで、最近(2018-11-10)にmergeされたようです。
この修正はおそらくsystemd 240に含まれるものと考えられますが、Debian Stretchの現行バージョンにパッチが当てられるのかどうかはよくわからなかったので、ワークアラウンドを用意してみました。
ワークアラウンド
コンテナで/boot/reboot
という空のファイルがつくられたかどうかをホスト側から監視して、ファイルがつくられていて、かつコンテナがシャットダウン状態であればコンテナを起動する、という手順でrebootの代用にします。
ホスト側の手順
/usr/local/sbin/nspawn_reboot_watchd
#!/bin/sh
while :; do
ls /var/lib/machines |
while read machine; do
if # "reboot" が存在していてかつ, コンテナが停止していれば
test -f "/var/lib/machines/${machine}/boot/reboot" &&
! ( /bin/machinectl | grep "^${machine}" > /dev/null );
then
#echo "${machine} need reboot"
echo "reboot container: ${machine}"
rm "/var/lib/machines/${machine}/boot/reboot" # rebootファイルを削除
/bin/machinectl start ${machine} # コンテナを再起動
fi
done
sleep 5
done
/etc/systemd/system/nspawn_reboot_watchd.service
[Unit]
Description=nspawn reboot watch
After=systemd-machined.service
[Service]
ExecStart=/usr/local/sbin/nspawn_reboot_watchd
Restart=always
RestartSec=5
StartLimitBurst=0
[Install]
WantedBy=multi-user.target
$ chmod +x /usr/local/sbin/nspawn_reboot_watchd
$ systemctl enable nspawn_reboot_watchd.service
# systemctl start nspawn_reboot_watchd.service
コンテン側の手順
-
/boot/reboot
を作成して、シャットダウンするシェルスクリプトをつくり、rebootコマンドと置き換えます
コンテナ側の手順
$ cat <<EOF > /usr/local/sbin/nspawn-reboot
#!/bin/sh
touch /boot/reboot
shutdown -h now
EOF
$ chmod +x /usr/local/sbin/nspawn-reboot
$ unlink /sbin/reboot # rebootコマンドを置き換える
$ ln -s -T /usr/local/sbin/nspawn-reboot /sbin/reboot # rebootコマンドを置き換える
最後に
- systemdの方針として、古いバージョンでバグが見つかっても対応するのは各ディストリビューションの責任で、systemdとして旧バージョンに対するパッチを提供することは無いらしい
- Debianにおいて、メジャーバージョンが変わらない間にsystemdがバージョンアップされることがあるのかどうかとか、systemdでバグが見つかった場合のDebianチームの対応がどうなってるのかとか、そういえばなんも知らないので、調べとかないといけないと思った