はじめに
本記事では、Dockerを使用してUbuntu 24.04のコンテナ内でGoogle Chromeをインストールし、ホスト側のXサーバーでブラウザを表示させ、音声出力もサポートする方法について解説する。最初に手動で行う手順を説明し、その後にこれをDockerfileとして自動化する方法を示す。
ホストのXサーバーでGoogle Chromeを表示させる
Dockerコンテナの起動(Xと音声サポート付き)
Ubuntu24.04のイメージをホストPC側のXサーバーでの描画とPulseAudioの音声出力をサポートするための複数のオプションをつけてコンテナを起動する。
docker run -it --rm \
--name ubuntu24 \
--env="DISPLAY=$DISPLAY" \
--env="PULSE_SERVER=unix:${XDG_RUNTIME_DIR}/pulse/native" \
--volume="$HOME/.Xauthority:/root/.Xauthority:rw" \
--volume="${XDG_RUNTIME_DIR}/pulse/native:${XDG_RUNTIME_DIR}/pulse/native" \
--volume="/etc/machine-id:/etc/machine-id:ro" \
--volume="/run/user/$(id -u)/pulse:/run/user/$(id -u)/pulse" \
--network=host \
ubuntu:24.04 bash
オプションの詳細
-
docker run
: Dockerコンテナを起動するためのコマンド -
-it
-
-i
: コンテナが標準入力(stdin
)を受け付ける -
-t
: 仮想端末を割り当てコマンドラインインターフェースでの対話を可能にする
-
-
--rm
- コンテナの実行が終了した際に、そのコンテナを自動的に削除する
-
--name ubuntu24
- コンテナに
ubuntu24
という名前を付ける
- コンテナに
-
--network=host
- コンテナがホストのネットワークスタックを使用するようにします。コンテナとホストが同じネットワークインターフェースとIPアドレスを共有しX11やPulseAudioなどローカルホスト経由での通信が必要な場合に必要
-
ubuntu:24.04
-
ubuntu:24.04
は、使用するDockerイメージを指定する
-
-
bash
-
bash
は、コンテナ内で起動するコマンド(この場合はBashシェル)を指定する
-
ホストPCのXサーバーで描画するためのオプション指定
-
--env="DISPLAY=$DISPLAY"
- ホストシステムの
DISPLAY
環境変数をコンテナに渡す
- ホストシステムの
-
--volume="$HOME/.Xauthority:/root/.Xauthority:rw"
- ホストの
.Xauthority
ファイルをコンテナにマウントします。このファイルにはXサーバーの認証情報を含む。コンテナ内のアプリケーションがホストのXサーバーに接続するための設定 -
rw
は読み書き権限
- ホストの
-
--env="PULSE_SERVER=unix:${XDG_RUNTIME_DIR}/pulse/native"
- ホストシステムのPulseAudioサーバーに接続する。
PULSE_SERVER
環境変数にPulseAudioサーバーのソケットパスを設定し、コンテナ内のアプリケーションがホストのオーディオ出力を利用する
- ホストシステムのPulseAudioサーバーに接続する。
ホストPCに音声を再生するためのオプション指定
-
--volume="${XDG_RUNTIME_DIR}/pulse/native:${XDG_RUNTIME_DIR}/pulse/native"
- ホストのPulseAudioサーバーのUNIXソケットをコンテナにマウントする。コンテナ内のアプリケーションがこのソケットを介してホストのPulseAudioサーバーに接続する
-
--volume="/etc/machine-id:/etc/machine-id:ro"
- ホストの
/etc/machine-id
ファイルをコンテナにマウントする。このファイルはシステム固有の識別子を含む。コンテナ内のアプリケーションがホストのサービスにアクセスする -
ro
は読み取り専用
- ホストの
-
--volume="/run/user/$(id -u)/pulse:/run/user/$(id -u)/pulse"
- ホストのユーザーランタイムディレクトリ内のPulseAudioソケットをコンテナにマウントする。コンテナ内のアプリケーションがこのソケットを利用してホストのオーディオサービスにアクセスする
コンテナ内でGoogle Chromeをインストール
必要なパッケージを含めてGoogle Chromeをインストールする。
export DEBIAN_FRONTEND=noninteractive
apt-get update
apt-get install -y wget
wget -q https://dl.google.com/linux/direct/google-chrome-stable_current_amd64.deb
apt-get install -y \
./google-chrome-stable_current_amd64.deb \
libcanberra-gtk-module \
libcanberra-gtk3-module \
fonts-ipafont-gothic \
fonts-ipafont-mincho \
fonts-noto-cjk \
language-pack-ja \
pulseaudio \
socat \
alsa-base \
--no-install-recommends && \
apt-get clean && \
rm -rf /var/lib/apt/lists/*
dbusエラーを回避する
# D-Busサービスを開始
/etc/init.d/dbus start
# XDG_RUNTIME_DIR環境変数を設定
export XDG_RUNTIME_DIR=/run/user/$(id -u)
# 適切な権限でランタイムディレクトリを作成
mkdir -p $XDG_RUNTIME_DIR
chmod 700 $XDG_RUNTIME_DIR
chown $(id -un):$(id -gn) $XDG_RUNTIME_DIR
# DBUS_SESSION_BUS_ADDRESS環境変数を設定
export DBUS_SESSION_BUS_ADDRESS=unix:path=$XDG_RUNTIME_DIR/bus
# D-Busセッションデーモンを開始
dbus-daemon --session --address=$DBUS_SESSION_BUS_ADDRESS --nofork --nopidfile --syslog-only &
X11フォワーディングの許可
ホストのXサーバーが外部接続を許可しているか確認する。必要に応じて以下のコマンドをホスト側のPCで実行する。
xhost +
DISPLAY環境変数を設定
# 環境変数の確認
echo $DISPLAY
# $DISPLAYに :0 などが適切に設定されていない場合は手動で設定する
export DISPLAY=:0
Google Chromeの起動
Google Chromeを起動してホスト側のXサーバーで表示する。
# Google Chromeブラウザを起動する
google-chrome --no-sandbox --disable-gpu --disable-dev-shm-usage
オプションの解説
-
--no-sandbox
- docker内で root で google-chrome を実行する場合に必要となる
-
--disable-gpu
- GPUアクセラレーションを無効にする。Dockerコンテナ内でChromeを実行する際、ホストのGPUを適切に利用できない場合がある。このオプションを使用することで、GPUに依存する処理(ハードウェアアクセラレーション)を無効にし、代わりにCPUでレンダリングを行う。GPU関連のエラーや問題を回避する。
-
--disable-dev-shm-usage
-
/dev/shm
(共有メモリ)を使用せず、代わりにディスク上の一時ファイルを使用する。Dockerコンテナ内の/dev/shm
(共有メモリ)はデフォルトでサイズが制限されており(通常は64MB)、これによりChromeが大量のメモリを必要とする処理(例えば、大きなウェブページのレンダリング)が失敗する。このオプションを使用することで、/dev/shm
の制限を回避し、Chromeが安定して動作する
-
トラブルシューティング
Xのフォワーディングの確認
Docker内で起動したxeyesがホスト側のXサーバーで表示されることを確認する
apt-get update
apt-get install -y x11-apps
xeyes
音声再生の確認
Docker内で音声再生が正常に動作しているか確認するために、以下のコマンドを使用する。
# サンプル音源をダウンロード
wget https://freewavesamples.com/files/1980s-Casio-Piano-C5.wav
# サンプル音声を再生
apt-get update
apt-get install -y alsa-utils
aplay 1980s-Casio-Piano-C5.wav
音声が正常に再生されれば成功
手順の自動化
これまで手動で行った手順をDockerfileにまとめ自動化する
Dockerfileの作成
# 適当なワークディレクトリに移動
mkdir -p /tmp/test
cd /tmp/test
# 上記のDockerfileの内容をコピペして作成
vi Dockerfile
FROM ubuntu:24.04
ENV DEBIAN_FRONTEND=noninteractive
ENV DISPLAY=:0
ENV PULSE_SERVER=unix:/run/user/1000/pulse/native
RUN apt-get update && \
apt-get install -y wget pulseaudio socat alsa-base \
libcanberra-gtk-module libcanberra-gtk3-module \
fonts-ipafont-gothic fonts-ipafont-mincho fonts-noto-cjk \
language-pack-ja dbus-x11 && \
wget -q https://dl.google.com/linux/direct/google-chrome-stable_current_amd64.deb && \
apt-get install -y ./google-chrome-stable_current_amd64.deb --no-install-recommends && \
apt-get clean && rm -rf /var/lib/apt/lists/*
# D-Busの設定と起動を行うスクリプトを作成
RUN echo "#!/bin/bash\n\
/etc/init.d/dbus start\n\
export XDG_RUNTIME_DIR=/run/user/\$(id -u)\n\
mkdir -p \$XDG_RUNTIME_DIR\n\
chmod 700 \$XDG_RUNTIME_DIR\n\
chown \$(id -un):\$(id -gn) \$XDG_RUNTIME_DIR\n\
export DBUS_SESSION_BUS_ADDRESS=unix:path=\$XDG_RUNTIME_DIR/bus\n\
dbus-daemon --session --address=\$DBUS_SESSION_BUS_ADDRESS --nofork --nopidfile --syslog-only &\n\
exec \"\$@\"" > /start.sh && chmod +x /start.sh
CMD ["/start.sh", "google-chrome", "--no-sandbox", "--disable-gpu", "--disable-dev-shm-usage"]
このDockerfileを使用することで、コンテナを簡単にビルドして音声サポート付きのGoogle Chromeを実行できる
Dockerイメージの作成
# chrome起動用のDockerイメージを作成
docker build -t ubuntu24_chrome .
# イメージの作成を確認
docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
ubuntu24_chrome latest 48318381cbff 50 seconds ago 1.23GB
ubuntu 24.04 35a88802559d 2 months ago 78.1MB
ubuntu latest 35a88802559d 2 months ago 78.1MB
Dockerイメージの実行
作成したDockerイメージ(ubuntu24_chrome)を実行する
docker run -it --rm \
--name ubuntu24_chrome \
--env="DISPLAY=$DISPLAY" \
--env="PULSE_SERVER=unix:${XDG_RUNTIME_DIR}/pulse/native" \
--volume="$HOME/.Xauthority:/root/.Xauthority:rw" \
--volume="${XDG_RUNTIME_DIR}/pulse/native:${XDG_RUNTIME_DIR}/pulse/native" \
--volume="/etc/machine-id:/etc/machine-id:ro" \
--volume="/run/user/$(id -u)/pulse:/run/user/$(id -u)/pulse" \
--network=host \
ubuntu24_chrome
必要に応じて以下のコマンドをホスト側のPCで実行しておく
xhost +
まとめ
Dockerを利用して、ホストのXサーバーでGoogle Chromeを表示し、音声出力もサポートする手順を説明した。最終的には、これらの手順をDockerfileにまとめて自動化した。
ハードウェアアクセラレーションのサポート
次回はDockerでGPUを有効にしてハードウェアアクセラレーションをサポートでWebGLの高速描画を実現する
xhost +
を使わずに実現する方法