Docker上のリバースプロキシで静的コンテンツを複数コンテナ間と共有

リバースプロキシをたてて複数サイトをマルチドメインで運用しているため 、静的コンテンツの配信をちょっと考える必要があった。

場当たり的に、リバースプロキシの配下にstaticフォルダを作成して、別コンテナのファイルをコピーして置いておいたけど、全く関係のないコンテナに資産をおいて管理上問題がある。

特によくないと感じたのは、1サービスで変更をおこなっても、全サービスに影響のあるリバースプロキシをdocker-compose up -d –buildし直す必要がある点です。

何かあってからでは遅いと考え、構成を見直しました。

共有ボリュームの作成

ターミナルを開いて以下のコマンドを実行します。

以下のコマンドで共有のボリュームを作成します。

docker volume create static_file_share
docker volume create static_file_share
docker volume create static_file_share

作成結果を確認します。

docker volume ls
docker volume ls
docker volume ls

Nginxとginx側の見直し

docker-comopose.ymlの修正

まずは、リバースプロキシのnginx側のdocker-compose.yml

作成したボリュームを追記します。

Compose の外ですでに作成済みの volume を指定するため、externalには ture を設定します。 これにより、 docker-compose up 時に Compose は volume を作成しません。

version: '3'
services:
proxy:
build: ./proxy
tty: true
image: dc_proxy
container_name: dc_proxy
ports:
- "80:80"
- "443:443"
volumes:
- '/etc/letsencrypt:/etc/letsencrypt'
- /var/run/docker.sock:/tmp/docker.sock:ro
restart: always
networks:
default:
external:
name: dc_proxy_nw
# volumes を定義
volumes:
static_file_share:
external: true
version: '3' services: proxy: build: ./proxy tty: true image: dc_proxy container_name: dc_proxy ports: - "80:80" - "443:443" volumes: - '/etc/letsencrypt:/etc/letsencrypt' - /var/run/docker.sock:/tmp/docker.sock:ro restart: always networks: default: external: name: dc_proxy_nw # volumes を定義 volumes: static_file_share: external: true
version: '3'
services:
  proxy:
    build: ./proxy
    tty: true
    image: dc_proxy
    container_name: dc_proxy
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - '/etc/letsencrypt:/etc/letsencrypt'
      - /var/run/docker.sock:/tmp/docker.sock:ro
    restart: always
networks:
  default:
    external:
      name: dc_proxy_nw

# volumes を定義
volumes:
  static_file_share:
    external: true

Nginxのconfigファイル

nginxのconfigファイルは変更しません。アプリケーション側で静的コンテンツをコピーする際に、現状と同じ構成になるようにします。

...
# staticfiles
location /static/ {
alias /static/mt/static/;
}
location / {
root /static/mt/html/;
index index.html;
}
location /api/ {
proxy_pass http://mt:8000;
}
}
... # staticfiles location /static/ { alias /static/mt/static/; } location / { root /static/mt/html/; index index.html; } location /api/ { proxy_pass http://mt:8000; } }
...
    # staticfiles
    location /static/ {
        alias /static/mt/static/;
    }

    location / {
        root /static/mt/html/;
        index index.html;
    }

    location /api/ {
        proxy_pass   http://mt:8000;
    }
}

アプリケーション側の修正

アプリケーションはDjangoのRest Api Frameworkです。

リバースプロキシ側の設定は変更しなかったので、アプリケーション側のファイル配置を見直します。

docker-compose.ymlの修正

先ほどと同様、 作成したボリュームを追記します。

...
volumes:
static_file_share:
external: true
... volumes: static_file_share: external: true
...

volumes:
  static_file_share:
    external: true

また、静的ファイルが格納されているフォルダを、共有フォルダにマウントします。

...
web:
# Dockerfile が存在するディレクトリの相対パスを指定する
build: .
# コンテナ実行時に実行するコマンド
command: uwsgi --ini ./app/app.ini
# コンテナの /code を、ホストのカレントディレクトリにマウントする
volumes:
- .:/code
- "static_file_share:/static"
... web: # Dockerfile が存在するディレクトリの相対パスを指定する build: . # コンテナ実行時に実行するコマンド command: uwsgi --ini ./app/app.ini # コンテナの /code を、ホストのカレントディレクトリにマウントする volumes: - .:/code - "static_file_share:/static"
...
web:
    # Dockerfile が存在するディレクトリの相対パスを指定する
    build: .
    # コンテナ実行時に実行するコマンド
    command: uwsgi --ini ./app/app.ini
    # コンテナの /code を、ホストのカレントディレクトリにマウントする
    volumes:
      - .:/code
      - "static_file_share:/static"
    

ちなみに、Djangoの場合、静的コンテンツは、以下のコマンドで収集します。

python manage.py collectstatic
python manage.py collectstatic
python manage.py collectstatic

Dockerfileの修正

静的コンテンツをコピーする処理を追加します。が、もともと、カレントディレクトリ配下をすべてコピーしていたので、今回は修正不要です。

# カレントディレクトリ配下を /code 配下にコピーする
ADD . /code/
# カレントディレクトリ配下を /code 配下にコピーする ADD . /code/
# カレントディレクトリ配下を /code 配下にコピーする
ADD . /code/

動作確認

それでは、それぞれ起動しなおし、動作確認をおこないます。

docker-compose up -d --build
docker-compose up -d --build
docker-compose up -d  --build

無事、index.htmlが参照され動きました。

タグ: ,

About: ken


コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

このサイトはスパムを低減するために Akismet を使っています。コメントデータの処理方法の詳細はこちらをご覧ください