Help us understand the problem. What is going on with this article?

GKEのコンテナ内のディレクトリにGCSバケットをマウントする

More than 1 year has passed since last update.

概要

Cloud Storage FUSEを使用して、Google Kubernetes Engine(以下、GKE)で動いてるコンテナ内のディレクトリにGoogle Cloud Storage(以下、GCS)のバケットをマウントすることを目指します。

WordPressのuploadsディレクトリなど、コンテナ間で共有したいリソースがある時に便利です。

GCP側の準備

プロジェクトを作成

コンソール画面などからプロジェクトを作成します。
今回は説明のためexampleというプロジェクト名であると仮定しています。

バケットの作成

Cloud SDKかGCPコンソール画面でバケットを作成します。

バケット名やプロジェクト名は他ユーザも含めて全プロジェクトでユニークなので、
名前が被った場合は違うバケット名を試してください。

クラスタ作成

コマンドで作成を行います。
重要なのは--scopesオプションで、必ずstorage-rwstorage-fullを指定してください。
他のオプションはお好みで大丈夫です。

$ gcloud container clusters create example-cluster \
--machine-type f1-micro \
--scopes storage-full

Cloud Storage FUSEのインストール

ベースイメージを元に、FUSEがインストールされたイメージを作っていきます。
基本的には公式ドキュメントの手順に従って準備をしていきます。

ベースイメージ

今回は例としてphp:5.6-apacheを使用します。
他のイメージを使用する場合は、コマンドが異なる場合がございますのでご注意ください。

ベースイメージOSのバージョン名を確認

公式ドキュメントの通り、lsb_releaseコマンドを使用してOSバージョン名を確認します。

# docker run -it php:5.6-apache /bin/bash
# apt-get install -y lsb-release
# lsb_release -c -s
jessie

Apacheのユーザ名を確認

Apacheのユーザ名(=FUSEを使用するユーザ名)を確認します。

/etc/apache2/apache2.conf
 .
 .
 .
# These need to be set in /etc/apache2/envvars
User ${APACHE_RUN_USER}
Group ${APACHE_RUN_GROUP}
 .
 .
 .

/etc/apache2/envvarsで定義されている環境変数が指定されているようですので、コメントに書いてあるファイルを確認します。

 .
 .
 .
: ${APACHE_RUN_USER:=www-data}
export APACHE_RUN_USER
: ${APACHE_RUN_GROUP:=www-data}
export APACHE_RUN_GROUP
 .
 .
 .

Apacheのユーザはwww-dataであることがわかりました。

Dockerfileを用意する

gcsfuseのパッケージURLを指定する際に、先程確認したOSバージョン名を使用します。
後ほどApacheユーザーでFUSEを使用するため、sudoもインストールしておきます。
私はvimをApacheの設定を確認するためにインストールしていますが、必須ではございません。

また、fuseグループを作成し、apacheのユーザをfuseグループに追加します。

末尾ではENTRYPOINTを指定しています。
ここで実行するスクリプトの詳細は後述します。

FROM php:5.6-apache
WORKDIR /path/to/DocumentRoot

# gcsfuse-[バージョン名]を指定する
RUN echo "deb http://packages.cloud.google.com/apt gcsfuse-jessie main" | tee /etc/apt/sources.list.d/gcsfuse.list
RUN curl https://packages.cloud.google.com/apt/doc/apt-key.gpg | apt-key add -
RUN groupadd fuse
RUN usermod -aG fuse www-data

RUN apt-get update -y && apt-get install -y \
    gcsfuse \
    sudo \
    vim

COPY entrypoint.sh /usr/local/bin/entrypoint.sh
RUN chmod a+x /usr/local/bin/entrypoint.sh

EXPOSE 80 443
ENTRYPOINT ["/usr/local/bin/entrypoint.sh"]

ENTRYPOINTを指定

この例では、ドキュメントルートをGCSにマウントしていますが、他のディレクトリでももちろん構いません。
Apacheユーザとして、gcsfuseコマンドを実行しないと、ページにアクセスした際に、403エラーが出てしまう可能性があります。

entrypoint.sh
#!/bin/bash
source /etc/apache2/envvars
chown -R www-data:www-data *
sudo -u www-data gcsfuse example-bucket ./
exec apache2 -D FOREGROUND

イメージファイルのビルド・プッシュ

イメージをビルドし、GCPのContainer Registryにプッシュします。

docker build -f ./Dockerfile -t example_image:0.0.0 .
docker tag example_image:0.0.0 gcr.io/example/example_image:0.0.0
gcloud docker -- push gcr.io/example/example_image:0.0.0

k8sの設定ファイルを用意

example.yaml
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: example
spec:
  replicas: 1
  template:
    metadata:
      labels:
        app: example
        tier: frontend
        environment : production
    spec:
      containers:
        - image: gcr.io/example/example_image:0.0.0
          imagePullPolicy: Always
          name: example
          ports:
            - containerPort: 80
              name: example
          securityContext:
            privileged: true
---
apiVersion: v1
kind: Service
metadata:
  name: example
  labels:
    app: example
spec:
  selector:
    app: example
    tier: frontend
    environment : production
  type: LoadBalancer
  ports:
    - port: 80
      protocol: TCP
      targetPort: 80

GKEにデプロイする

$ gcloud container clusters get-credentials example-cluster --project example
$ kubectl create -f example.yaml

GKEクラスタに接続して外部IPを確認

$ kubectl get svc example

上のコマンドを実行することで表示されるEXTERNAL IPを確認します。

確認

GCSにindex.htmlをアップし、ブラウザからhttp://[確認したEXTERNAL IP]/にアクセスします。
アップした内容が表示されたら成功です。
なお、GKEにデプロイするのに少し時間がかかる(イメージのプル時間とエントリポイントの実行時間)ため、表示されない場合は少し時間を置いてからアクセスしましょう。

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away