ラズベリーパイ単体でDockerを使う分にはいいのですが、ラズベリーパイをミニサーバー代わりにして、そこでDockerを使うのは使い勝手が良くないなぁという話です。
きっかけ
定期的にクロールを実行するサーバーを、デスクトップPCで動かしていました。
追々専用サーバーを用意するつもりだったので、サーバー移行しやすいようDockerを使用しました。
コンテナ構成は下記のとおりで、docker-composeで構成し、docker-machineでWindowsにHyper-VのDockerマシンを作成して、そのマシンにdocker-composeをアップしていました。
+-------+ +---------+ +-------------+ +---------------------+ | Nginx | --> | Jenkins | --> | Linux + SSH | --> | Node.js + puppeteer | +-------+ +---------+ +-------------+ +---------------------+
なので、サーバー移行は、新しいサーバーをDockerマシンとして追加して、
% docker-machine 新しいマシン名 % docker-compose up
で済みます。
ラズベリーパイに興味があってさわってみたかったので、ラズベリーパイをミニサーバー代わりにして、そこにdocker-composeをアップしてみることにしました。
手順
ラズベリーパイでDockerを動くようにして、Dockerマシンにするのはこちらの記事を参考にしました。
Dokcerマシンには、既存のPCをDockerマシンにする「generic」ドライバーというものがあり、それを利用してラズベリーパイをDockerマシンにしています。
問題発生
後はDockerマシンをラズベリーパイに切り替えて、docker-compose upすれば終わりかと思ったのですが、全然ダメでした。
Dockerイメージに互換性がない
PCのCPUは「x86」。一方ラズベリーパイのCPUは「ARM」なので、Dockerイメージに互換性がありません。
Docker Hubから取ってくるイメージも「ARM」専用のものでないと動かず、結果として「ARM」用に別途Dockerfileを作成する必要があります。
「PCで動作検証したものを、そのままラズベリーパイにアップして終わり」とはならず、動作検証後、ラズベリーパイ用に修正してラズベリーパイにアップして、更にラズベリーパイで動作検証する必要があります。
Dockerfileが違うので構成が微妙に異なっていたりして、PCではうまく動いているのにラズベリーパイに持っていくとエラーなることが多々あり、かつ、環境が異なるので原因究明が手間でした。
イメージ作成に時間がかかりすぎる
それでも何とか動作するようにはなったのですが、Dockerイメージの作成はラズベリーパイ上で行うので、そのイメージ作成時間が長かったです。
クローラーに「puppeteer」を使っていたため、「xlib付きLinux+Node.js+Chronium+日本語フォント」のイメージ作成に30分程かかります。
上記は極端な例ですが、元々「x86」から「ARM」に変更時点でもエラーが発生しやすく、その上イメージ作成に時間がかかるので、ちょっとした修正も億劫になってしまいました。
結論
Dockerのメリットは、開発環境で作成したものを、そのままサーバーに載せられるポータビリティーだと思うのですが、ラズベリーパイをミニサーバーとした場合、そこが完全に切れてしまいます。
つまり、PCで開発していても、別途ラズベリーパイ専用に開発し直す必要があり、2回開発している気分になります。
それがかなり手間だったのと、そもそもDockerにした意図って何だっけと振り返ると、ラズベリーパイをミニサーバー代わりにして、そこでDockerを使うのは何か違うなぁとやめました。…というお話でした。
巷にはラズベリーパイを使ったKubernetesクラスター作成の記事があり、当初は、最終的にはdocker-composeからKubernetesにすることも妄想していたのですが、よくよく考えると、Kubernetesにしてもラズベリーパイ用のDockerイメージを作成するラズベリーパイが必要なことは変わらず、やはり何だかなぁという結論になります。
それらの記事はネタでやっているのだとは思うのですが、実際にそれを使っているの?と思ってしまいます。
ただ、今回は、PCの代用としてラズベリーパイを使用しようとした所に問題があったのですが、ラズベリーパイに特化したものを作るのであれば、Dockerを使うのは問題ないと思います。
おまけ
内容古くなっているかも知れませんが、使用していたラズベリーパイ用Dockerfielを記載します。
ラズベリーパイでDockerを使おうとして、Dockerfileを探している人がいましたら、参考にして頂けると幸いです。
Nginx Dockerfile
FROM tobi312/rpi-nginx COPY copy/etc/nginx/conf.d/default.conf /etc/nginx/conf.d/ COPY copy/etc/nginx/server.key /etc/nginx/ COPY copy/etc/nginx/server.crt /etc/nginx/
Jenkins Dockerfile
FROM djdefi/rpi-jenkins RUN apt-get install -y tzdata RUN cp /usr/share/zoneinfo/Asia/Tokyo /etc/localtime RUN echo "Asia/Tokyo" > /etc/timezone
Linux+SSH Dockerfile
FROM resin/rpi-raspbian:latest USER root RUN mkdir /var/run/sshd RUN apt-get update RUN apt-get install -y openssh-server RUN echo 'root:xxxx' | chpasswd RUN sed -i 's/PermitRootLogin.*/PermitRootLogin yes/' /etc/ssh/sshd_config RUN cat /etc/ssh/sshd_config RUN sed -i 's/root:\/bin\/ash/root:\/bin\/bash/' /etc/passwd RUN ssh-keygen -A EXPOSE 22 RUN apt-get install -y tzdata RUN cp /usr/share/zoneinfo/Asia/Tokyo /etc/localtime CMD ["/usr/sbin/sshd", "-D"]
Node.js + puppeteer Dockerfile
FROM hypriot/rpi-node
RUN apt-get update \
&& apt-get install -y \
zip \
unzip \
gconf-service \
libasound2 \
libatk1.0-0 \
libc6 \
libcairo2 \
libcups2 \
libdbus-1-3 \
libexpat1 \
libfontconfig1 \
libgcc1 \
libgconf-2-4 \
libgdk-pixbuf2.0-0 \
libglib2.0-0 \
libgtk-3-0 \
libnspr4 \
libpango-1.0-0 \
libpangocairo-1.0-0 \
libstdc++6 \
libx11-6 \
libx11-xcb1 \
libxcb1 \
libxcomposite1 \
libxcursor1 \
libxdamage1 \
libxext6 \
libxfixes3 \
libxi6 \
libxrandr2 \
libxrender1 \
libxss1 \
libxtst6 \
ca-certificates \
fonts-liberation \
libappindicator1 \
libnss3 \
lsb-release \
xdg-utils \
wget
RUN ln -sf /usr/share/zoneinfo/Asia/Tokyo /etc/localtime
# Japanese font
RUN mkdir /noto
COPY ./app/font/NotoSansCJKjp-hinted.zip /noto
WORKDIR /noto
RUN unzip NotoSansCJKjp-hinted.zip && \
mkdir -p /usr/share/fonts/noto && \
cp *.otf /usr/share/fonts/noto && \
/usr/bin/fc-cache -fv
WORKDIR /
RUN rm -rf /noto
WORKDIR /usr/src/app
COPY ./app/package.json .
COPY ./app/build ./build
COPY ./app/views ./views
RUN npm install
COPY ./app/chromium/chromium-codecs-ffmpeg_65.0.3325.181-0ubuntu0.14.04.1_armhf.deb .
RUN sudo dpkg -i chromium-codecs-ffmpeg_65.0.3325.181-0ubuntu0.14.04.1_armhf.deb
COPY ./app/chromium/chromium-browser_65.0.3325.181-0ubuntu0.14.04.1_armhf.deb .
RUN sudo dpkg -i chromium-browser_65.0.3325.181-0ubuntu0.14.04.1_armhf.deb
EXPOSE XXXX
CMD [ "npm", "start" ]