【Docker】Docker 上で HTTP Server と Tomcat を連携する

どうも、エピックです。

この記事ではMacのDocker 上で HTTP Server と Tomcat を連携する方法について紹介します。

  • MacBook pro (13-inch, 2018)
  • 2.7 GHz クアッドコアIntel Core i7
  • macOS Monterey (v12.3.1)
目次

ワークスペースを作成

Dockerのバージョンは次のようになっています。

$ docker --version
Docker version 20.10.14, build a224086

デスクトップに次のフォルダ、ファイル構成でワークスペースを作成します。

Docker Compose を使用しないので、apache http server , tomcat それぞれでDockerファイルを作成し連携を行っていきます。

dockerイメージの作成には、”Dockerfile”という名前のファイルが必要となるのでそれぞれのフォルダに作成してください。

httpd.conf, server.xml はそれぞれのサーバーから事前にオリジナルを取得しているものとします。

httpd-proxy.conf は新規作成です。

Apache Http Server の設計

次のようにDockerファイルを作成します。

# https://hub.docker.com/_/httpd
FROM httpd:2.4
RUN apt-get update -y
RUN apt-get install -y vim
COPY httpd.conf /usr/local/apache2/conf/
COPY httpd-proxy.conf /usr/local/apache2/conf/extra/
EXPOSE 80
CMD ["httpd-foreground"]

それぞれのコマンドの役割は次の通りです。

  • FROM:コンテナのベースイメージを指定
  • RUN:ベースイメージ上で実行するコマンドを指定
  • COPY:ファイルをイメージ上へコピー
  • EXPOSE:公開ポートを設定
  • CMD:コンテナの実行時に実行されるコマンドを指定

ベースイメージは、オフィシャルからでている httpdのイメージを使います。

補足として実行ユーザーを定義していないので実行はルートで行われます。

セキュリティ上よろしくはないので必要に応じ実行用のユーザーを追加してください。

下記のサイトを参考にさせていただきました。

Dockerの実行ユーザー

続いて、あらかじめ用意していた httpd.confの次の箇所のコメントを解除します。

# 下記2つのコメントを解除する
LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_ajp_module modules/mod_proxy_ajp.so

また、httpd.conf の最後に次の1行を追記します。

# 最後に追加
Include /usr/local/apache2/conf/extra/httpd-proxy.conf

最後に、httpd-proxy.conf を作成し、次の1行を追加します。

# 新規作成し、次を追加
ProxyPass /sample/ ajp://localhost:8009/sample/

Tomcat の設計

次のようにDockerファイルを作成します。

curl を実行しサンプルのページを webapps へ配置しています。

# https://hub.docker.com/_/tomcat
FROM tomcat:9.0.46
RUN apt-get update -y
RUN apt-get install -y vim
RUN apt-get install -y curl
COPY server.xml $CATALINA_HOME/conf/
WORKDIR /usr/local/tomcat/webapps/
RUN curl -OL http://tomcat.apache.org/tomcat-8.5-doc/appdev/sample/sample.war

続いて、あらかじめダウンロードしておいた server.xml の AJP 1.3 Connector の箇所を有効化、下記のように修正します。

address に “0.0.0.0” を指定・secretRequired を “false” に設定しているため、あくまで開発用です。

<!-- Define an AJP 1.3 Connector on port 8009 -->
<Connector protocol="AJP/1.3"
           address="0.0.0.0"
           port="8009"
           redirectPort="8443"
           connectionTimeout="20000"
           useBodyEncodingForURI="true"
           secretRequired="false" />

以上で準備は完了です。

コマンドを実行していく

Tomcat のディレクトリへ移動します。

cd workspace/tomcat

DockerfileをもとにDockerイメージを作成します。

docker image build -t tomcat:sample .

tomcat_sample という名前のコンテナを作成実行します。

docker run --name tomcat_sample -dit tomcat:sample

これでTomcatのコンテナが動いているはずです。

続いて、apache のフォルダへ移動します。

cd workspace/apache

同じくDockerイメージを作成します。

docker image build -t httpd:sample .

httpd_sample という名前でコンテナを作成します。

docker run --name httpd_sample -p 80:80 -dit httpd:sample

docker ps -a で作成動作していることが確認できます。

$ docker ps -a
CONTAINER ID   IMAGE           COMMAND              CREATED          STATUS          PORTS                NAMES
9cbcabfbead0   httpd:sample    "httpd-foreground"   28 minutes ago   Up 7 minutes    0.0.0.0:80->80/tcp   httpd_sample
598b3b8debd5   tomcat:sample   "catalina.sh run"    28 minutes ago   Up 10 minutes   8080/tcp             tomcat_sample

ただこの状態では httpd_sample から tomcat_sample コンテナへのアクセスができていないはずです。

Docker には大きく3つのネットワーク(今はもっとある)”bridge” “host” “none” があるのですが、デフォルトの設定が bridge ネットワークになります。

今回のように、特段ネットワークを指定せずに作成したコンテナは別のネットワーク上の扱いとなるため名前解決ができません。

Docker Compose入門 (3) ~ネットワークの理解を深める~

今回はローカルのIPアドレスをもとに接続設定をしてあげます。

docker inspect bridge コマンドでネットワークを確認してあげます。

このとき tomcat_sample 側のIPアドレスを控えてください。

docker inspect bridge

httpd_sample コンテナへbashで接続します。

docker exec -it httpd_sample /bin/bash

httpd-proxy.conf の localhost となっている箇所をIPアドレスに書き換えます。

vi /usr/local/apache2/conf/extra/httpd-proxy.conf

Vimの書き込み保存はコマンドモードで :wq です。

補足としてコンテナ名指定でもトップのTomcatページへはアクセスできますがそれ以降でDNSエラーがでます。

コンテナから exit し、httpd_sample をリスタートします。

exit
docker restart httpd_sample

http://localhost/sample/ へアクセスし、表示されれば連携完了です!

最後に

今回はMacのDocker 上で HTTP Server と Tomcat を連携する方法ついて書いてみました。
もしわからないこと等あればコメントにていただけれればと思います。

今回も最後までお読みいただきありがとうございました。

では。

目次