46
42

More than 5 years have passed since last update.

Kubernetesを使ったスケーラブルなWordPress環境を構築してみた

Last updated at Posted at 2017-09-06

はじめに

IBMのマネージドなKubernetes環境であるIBM Cloud Containers Serviceについて、スケーラブルなWordPress(ブログ・ソフトウェア)環境の構築手順とともにご紹介します。
image.png

※ライト版(無料)で月額$70-80相当の仮想サーバー(2コア/4GB RAM/Ubuntu 16.04 LTS)がユーザー専用のWorker Nodeとして無料提供されますのでぜひこの機会にお試しください(2017年9月現在) Kubernetesって何?という方はこちらからお読みください。

なぜIBMはKubernetesにコミットしているのか?

2013年にオープン・クラウド戦略を発表する以前からLinuxをはじめIBMは長年にわたってOSSを支援しています。特にクラウドの領域では、これまで以上に相互運用性や相互接続性が重要となるため積極的にOSSをIBM Cloudのコア・テクノロジーとして採用しています。Kubernetesへの取り組みもその一環と言えます。

image.png

Kubernetesといえば、Google Container Engine (GKE)で使われているコンテナ管理フレームワークとして有名ですが、現在は、オープンソース・プロジェクトとしてCNCF (Cloud Native Computing Foundation)により運営・管理されています。最近では、PivotalとVMwareがGoogleと協業してKubernetesを採用したプラットフォーム・ソフトウェア製品を発表するなどKubernetesは業界でも大変注目されています。

image.png

IBMは、オープンソース・プロジェクトとしてKubernetes自体の開発に参加するだけでなく、CNCFのプラチナメンバーとして、理事会の議長を務め、コンテナ運用環境の標準化に取り組んでいます。IBMがKubernetesにコミットしている最大の理由として、Kubernetesのオープン性とデプロイメント・オプションの幅広さがあげられます。KubernetesはオープンソースであるDockerベースのコンテナを管理対象としていますので、ユーザーは、ベアメタル・サーバー、仮想化サーバー、プライベート、パブリック、ハイブリッド・クラウドのいずれのオプションでも選択できます。さらに、従来のハイパーバイザー型の仮想化技術と違いコンテナは軽量・高速であるためインフラをコードベースで制御・管理しやすく、それゆえポータビリティ(移植性)が高いという特徴があります。そのため、IBMが提唱するハイブリッド・クラウドを実現する重要なテクノロジーとして位置付けられています。

もう1つの理由として、Kubernetesには、Linux Foundationによって管理される明確なガバナンス・モデルがあります。さらに、Googleは積極的に製品の機能とロードマップを推進しているので、ベンダーがエコシステムに参加しやすいプロジェクトと言えます。Kubernetesのエコシステムが活性化することで長期的な実行可能性の観点でユーザー企業は安心して採用することができます。IBM以外にもHuawei、Intel、およびRed HatなどがKubernetesの開発において大きく貢献しています。今年に入ってCNCFのPlatinum MembersとしてAWS、Microsoftも加わってきましたので、次世代クラウド・プラットフォームのデファクト・スタンダードになると考えています。

image.png
参考:CNCF Platinum Members

以上のような理由から、現在Kubernetesは、IBMのパブリック・クラウド・サービスであるIBM Cloud Containers Service (Bluemix Containers Service)や、プライベート・クラウド製品IBM Cloud privateにおいて採用され企業向けに提供しています。IBM Cloud private (ICP)についてはここでは詳しくは触れませんが、9月より、IBM Cloud private-ce v2.1 BETA 1としてDockerHub上に公開されていますのでこちらもぜひお試しください。

参考:IBM Cloud private画面イメージ
image.png

IBM Cloud Containers Service(=IBMのマネージドKubernetes環境)

IBM Cloud Containers Serviceでは、KubernetesのMaster Node部分は、IBMによるマネージド・サービスとして提供され、Worker Nodeがユーザーのコンテナ化アプリの可動領域として提供されます。実体として、Kubernetes環境はIBM CloudのIaaS (旧SoftLayer)の仮想サーバー上に展開されます。IBMが運用管理するMaster Nodeとユーザーに提供されるWorker Nodeの各コンポーネントは下図のように配置・展開されます。

image.png

IBM Cloud Containers Serviceをオーダーしてみる

Bluemixのカタログからコンテナーのカテゴリーを選択すると下図のようにKubernetes ClsuterとContainer Registryが表示されます。

image.png

Kubernetes Clsuterを選択するとクラスター・タイプの選択画面が表示されます。クラスター名は、ここでは、「mycluster」としてライト版(無料)をオーダーします。ライト版(無料)では1つのクラスターに1つのワーカーノードを利用しています。

image.png

ちなみに、標準版では、最低3台以上の複数のワーカー・ノードを作成することができます。ワーカー・ノードをホストするサーバーは4CPU/16GB、16CPU/64GB、32CPU/128GB、56CPU/242GBから選択できるだけでなく、専用ハードウェア(ベアメタル)と共用ハードウェア(仮想サーバー)を選択することができます。

image.png

また、ライト版と標準版のクラスターでは、インターネットからアプリケーションにアクセスさせる方法が異なります。

  • ライト版:NodePortのみ
  • 標準版:NodePort、ロード・バランサー、Ingressから選択可能

詳細はこちらをご確認ください。

また、可用性に応じて以下のような構成を組むことも可能です。

  • 複数のワーカー・ノードを配置した 1 つのクラスター
  • 同じ地域内の別々のロケーションで実行される 2 つのクラスター (ロケーションごとに複数のワーカー・ノードを配置)
  • 別々の地域で実行される 2 つのクラスター (地域ごとに複数のワーカー・ノードを配置)

image.png

クラスターをオーダーすると5分程度でWorker Nodeがデプロイされ利用可能な状態になります。

image.png

ダッシュボードから、Worker NodeのIDが割り振られていることが分かります。

image.png

Kubernetesクラスターへのアクセス

Kubernetesクラスターにアクセスするには、 Bluemix CLIツールとKubernetes CLIのプラグインをPC端末にダウンロードしてインストールしてください。

$ bx plugin install container-service -r Bluemix

次に、bxコマンドを使いユーザー自身のBluemixアカウントにログインします。

$ bx login -a https://api.ng.bluemix.net

※統合 ID を所有している場合には、bx login --sso を使用して Bluemix CLI にログインしてください。

次に、IBM Bluemix Container Service のプラグインを初期化します。

$ bx cs init

次に、ターミナル・コンテキストをクラスターに設定します。

$ bx cs cluster-config mycluster
export KUBECONFIG=/Users/ibm/.bluemix/plugins/container-service/clusters/mycluster/kube-config-prod-hou02-mycluster.yml

出力として構成ファイルへのパスが環境変数を設定するコマンドとして表示されます。ターミナルでコマンドをコピーして貼り付け、環境変数として設定してください。kubeconfigファイルを直接ダウンロードして、コンテキストを手動で構成することもできます。

設定が完了するとKubernetesコマンドを実行してワーカー・ノードを利用することができます。

$ kubectl get nodes
NAME           STATUS    AGE       VERSION
50.23.39.106   Ready     41d       v1.5.6-4+abe34653415733

KubernetesダッシュボードはターミナルからProxy経由でアクセスします。

$ kubectl proxy &

ブラウザから http://127.0.0.1:8001/ui を使用してKubernetesダッシュボードを表示することができます。

image.png

スケーラブルなWordpress環境を構築してみる

Kubernetesクラスターの機能を確認するためにサンプルとしてWordpress環境を構築してみます。WordPressはLAMP (Linux/Apache/MySQL/PHP)で動くオープンソースのブログソフトウェアです。この例では、フロントエンド層としてWordPressコンテナ、バックエンド層としてMySQLコンテナをKubernetesに展開し、フロントエンド層を不可に応じて柔軟にスケーラブルさせる方法を紹介します。

image.png

環境構築に必要なコンポーネントは以下のとおりです。

大まかな作業の流れは以下のとおりです。

  • 永続ディスクを定義するローカルの永続ボリュームを作成します。
  • 機密データを保護する秘密を作成します。
  • 1つまたは複数のポッドでWordPressフロントエンドを作成して展開します。
  • MySQLデータベースを作成し、展開します(今回はコンテナ内のMySQLを使用)。

ステップ1. MySQLシークレットの設定

PC端末のターミナル上の適当なディレクトリにpassword.txtという名前の新しいファイルを作成し、password.txt(ASCII文字を含む任意の文字列)に任意のMySQLパスワードを入れます。

$ vi password.txt

password.txt内の不要な改行を削除するために次のコマンドを使用します。

$ tr -d '\n' <password.txt >.strippedpassword.txt && mv .strippedpassword.txt password.txt

ステップ2. WordPressとMySQLのサービスと展開を作成する

※注意:Bluemix Compose-MySqlをバックエンドのデータベースとして使用する場合は、Bluemix MySQLをバックエンドとして使用するを参照してください。

まずは、以下のコマンドでKubernetesクラスターのローカル・ストレージとして永続ボリュームを作成します。

$ kubectl create -f local-volumes.yaml
persistentvolume "local-volume-1" created
persistentvolume "local-volume-2" created

local-volumes.yamlのファイルの中身は例えば以下のように記述してください。

local-volumes.yaml
apiVersion: v1
kind: PersistentVolume
metadata:
  name: local-volume-1
  labels:
    type: local
spec:
  capacity:
    storage: 20Gi
  accessModes:
    - ReadWriteOnce
  hostPath:
    path: /tmp/data/lv-1
  persistentVolumeReclaimPolicy: Recycle
---
apiVersion: v1
kind: PersistentVolume
metadata:
  name: local-volume-2
  labels:
    type: local
spec:
  capacity:
    storage: 20Gi
  accessModes:
    - ReadWriteOnce
  hostPath:
    path: /tmp/data/lv-2
  persistentVolumeReclaimPolicy: Recycle

次に、以下のコマンドでMySQLのシークレットとWordPressのサービスを作成します。

$ kubectl create secret generic mysql-pass --from-file=password.txt
secret "mysql-pass" created

次に、以下のコマンドでMySQLのPodを作成します。

$ kubectl create -f mysql-deployment.yaml
service "wordpress-mysql" created
persistentvolumeclaim "mysql-lv-claim" created
deployment "wordpress-mysql" created

ここでは、mysql-deployment.yamlの中身は以下のように記述しています。

mysql-deployment.yaml
apiVersion: v1
kind: Service
metadata:
  name: wordpress-mysql
  labels:
    app: wordpress
spec:
  ports:
    - port: 3306
  selector:
    app: wordpress
    tier: mysql
  clusterIP: None
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: mysql-lv-claim
  labels:
    app: wordpress
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 20Gi
---
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: wordpress-mysql
  labels:
    app: wordpress
spec:
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: wordpress
        tier: mysql
    spec:
      containers:
      - image: mysql:5.6
        name: mysql
        env:
        - name: MYSQL_ROOT_PASSWORD
          valueFrom:
            secretKeyRef:
              name: mysql-pass
              key: password.txt
        ports:
        - containerPort: 3306
          name: mysql
        volumeMounts:
        - name: mysql-local-storage
          mountPath: /var/lib/mysql
      volumes:
      - name: mysql-local-storage
        persistentVolumeClaim:
          claimName: mysql-lv-claim

次に、以下のコマンドでWordpressのPodをデプロイします。

$ kubectl create -f wordpress-deployment.yaml
service "wordpress" created
persistentvolumeclaim "wp-lv-claim" created
deployment "wordpress" created

今回、wordpress-deployment.yamlの中身は以下のように記述しました。ここで定義するnodePortは、外部からクラスター内のサービスにアクセスするための公開用のポート番号です。

wordpress-deployment.yaml
apiVersion: v1
kind: Service
metadata:
  name: wordpress
  labels:
    app: wordpress
spec:
  ports:
    - port: 80
      targetPort: 80
      nodePort: 30180
  selector:
    app: wordpress
    tier: frontend
  type: NodePort
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: wp-lv-claim
  labels:
    app: wordpress
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 20Gi
---
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: wordpress
  labels:
    app: wordpress
spec:
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: wordpress
        tier: frontend
    spec:
      containers:
      - image: wordpress:latest
        name: wordpress
        env:
        - name: WORDPRESS_DB_HOST
          value: wordpress-mysql
        # - name: WORDPRESS_DB_USER
        #   value: admin
        - name: WORDPRESS_DB_PASSWORD
          valueFrom:
            secretKeyRef:
              name: mysql-pass
              key: password.txt
        ports:
        - containerPort: 80
          name: wordpress
        volumeMounts:
        - name: wordpress-local-storage
          mountPath: /var/www/html
      volumes:
      - name: wordpress-local-storage
        persistentVolumeClaim:
          claimName: wp-lv-claim

すべてのPodが実行されたら、次のコマンドを実行してPod名を確認します。kubernetesクラスタからPodのリストが返されます。

$ kubectl get pods
NAME                               READY     STATUS    RESTARTS   AGE
wordpress-2140944197-r0rnv         1/1       Running   0          6m
wordpress-mysql-3502574762-fcl7s   1/1       Running   0          6m

以上が完了したら今度は、外部リンクにアクセスしてください。

ステップ3. 外部WordPressリンクへのアクセス

クラスタのIPアドレスを取得するには、次のコマンドを使用します。

$ bx cs workers mycluster
OK
ID                                                 Public IP      Private IP     Machine Type   State    Status
kube-hou02-pabb828381ec564eeca73ac80169753db5-w1   50.23.39.106   10.47.122.24   free           normal   Ready

また、NodePort番号を取得するために、次のコマンドを実行してください。

$ kubectl get svc wordpress
NAME        CLUSTER-IP     EXTERNAL-IP   PORT(S)        AGE
wordpress   10.10.10.152   <nodes>       80:30180/TCP   10m

上記よりパブリックIPアドレスと外部公開用のポート番号(NodePort)を取得して、 http://[IP]:[ポート番号] を使用してWordPressサイトにアクセスできます。

Kubernetesダッシュボードからもデプロイのステータスを確認できます。 $kubectl proxyを実行し、URL 'http://127.0.0.1:8001/ui' にアクセスして、WordPressコンテナがいつ準備完了になったかを確認します。Podが完全に機能するには最大5分かかることがあります。

ステップ4. WordPressの使用

外部公開用URL(今回は http://50.23.39.106:30180 ) にアクセスしてください。

image.png

WordPressが稼動しているので、新しいユーザーを登録すればWordPressをインストールすることができます。

image.png

WordPressをインストールした後、アップデートや必要な設定をしてください。

image.png

ブログ・サイトとして、新しい投稿をすることができます。

image.png

ステップ5. スケールアウトしてみる

クラスタにリソースがあり、WordPress Webサイトの規模を拡大する場合は、次のコマンドを実行して現在の展開を確認できます。

$ kubectl get deployments
NAME              DESIRED   CURRENT   UP-TO-DATE   AVAILABLE   AGE
wordpress         1         1         1            1           1h
wordpress-mysql   1         1         1            1           1h

これで、WordPressのフロントエンドのために以下のコマンドを実行することができます。例えば、Wordpressを10個のPodにスケールさせてみます。

$ kubectl scale deployments/wordpress --replicas=10
deployment "wordpress" scaled

以下のとおりWordPressのフロントエンドを実行している10個のポッドにスケールしました。

$ kubectl get deployments
NAME              DESIRED   CURRENT   UP-TO-DATE   AVAILABLE   AGE
wordpress         10         10         10            10           1h
wordpress-mysql   1         1         1            1           1h

kubectlコマンドでPodの一覧詳細を確認します。10個のポッドにスケールしていることが分かります。

$ kubectl get pods -o wide

NAME                               READY     STATUS    RESTARTS   AGE       IP             NODE
wordpress-2140944197-63jwn         1/1       Running   0          1h        172.30.53.88   50.23.39.106
wordpress-2140944197-ckk2m         1/1       Running   0          1h        172.30.53.90   50.23.39.106
wordpress-2140944197-g2f8d         1/1       Running   0          1h        172.30.53.83   50.23.39.106
wordpress-2140944197-khqxv         1/1       Running   0          1h        172.30.53.85   50.23.39.106
wordpress-2140944197-kpv84         1/1       Running   0          1h        172.30.53.82   50.23.39.106
wordpress-2140944197-l621r         1/1       Running   0          1h        172.30.53.84   50.23.39.106
wordpress-2140944197-p8xh2         1/1       Running   0          1h        172.30.53.87   50.23.39.106
wordpress-2140944197-qmgdp         1/1       Running   0          1h        172.30.53.89   50.23.39.106
wordpress-2140944197-r0rnv         1/1       Running   0          2h        172.30.53.81   50.23.39.106
wordpress-2140944197-r1xx0         1/1       Running   0          1h        172.30.53.86   50.23.39.106
wordpress-mysql-3502574762-fcl7s   1/1       Running   0          2h        172.30.53.80   50.23.39.106

Kubernetesダッシュボードからも10個のポッドに拡張されたことが確認できます。

image.png

※ライト版(無料)の場合、リソースが限られているため、10ポッド程度までの拡張をお勧めします。

トラブルシューティング

誤って改行でパスワードを作成したのにMySQLサービスを認可できない場合は、以下のコマンドで現在のシークレットを削除することができます。

$ kubectl delete secret mysql-pass

サービス、デプロイメント、および永続ボリュームのリクエストは、以下のコマンドで削除できます。

$ kubectl delete deployment,service,pvc -l app=wordpress

作成済みの永続ボリュームを削除するには、次のコマンドを実行します

$ kubectl delete -f local-volumes.yaml

【補足】Kubernetesとは

  • Google社内のアプリケーション基盤として利用されていた「Borg」にインスパイアされ開発されたコンテナ管理フレームワーク
    image.png
    出典:Large-scale cluster management at Google with Borg

  • 2014年にGoogleがオープン化しCNCF(Cloud Native Computing Foundation)に寄贈。現在はLinux Foundationによってオープンソース・プロジェクトとして管理

  • アプリケーションを仮想マシン単位ではなくコンテナ単位に分割

  • Webアプリケーション、バッチ・ジョブ、データベースといったコンテナ化アプリをデプロイするための統合的なAPIを提供

  • 「宣言的なデプロイ・モデル」という概念を導入。アプリケーションをどのように実行すべきかが記述されたテンプレートにしたがい、Kubernetesがアプリケーションのステータスを制御

  • サービス・ディスカバリー(サービスへのルーティングを自動で提供する)によるアプリケーション構成の自動化

  • コンテナのスケジューリング、スケーリング、健全性、ライフサイクル、ロード バランシング、データ永続性、ロギング、モニタリングを管理

  • Blue-Greenデプロイメント、ローリング・デプロイメント、カナリア・デプロイメントといった継続的デリバリー実現

Kubernetesの基本
ここではKubernetesを利用する上で最低限抑えておくべき用語、機能について解説します。アーキテクチャ全体像を下図に示します。

image.png

Kubernetesの基本用語

  • コンテナ(Container):同一ホスト上で動作しているプロセスのリソースを隔離することにより、異なる環境のように見せた仮想環境。
  • ポッド(Pod):1つ以上のコンテナを協調動作する単位でまとめたもの。同一ノード(後述)上での動作が前提となる。
  • ノード(Node):Dockerコンテナのホストとなる物理的もしくは仮想的なマシン。
  • ミニオン(Minion):マスター(後述)からの指示でポッドを動作させるノード。
  • マスター(Master):1つ以上のミニオンで動作するポッドを集中管理するためのノード。
  • サービス(Service):ポッドの集合によって実現されるシステムの機能を表す抽象的なもの。ロードバランサ的な役割も果たす。
  • レプリケーションコントローラ(Replication Controller):定義ファイルに指定されている数を保つようポッドを複製し、サービスの実装を行うもの。
  • キューブレット(Kubelet):定義ファイルにしたがってポッドを起動したり、ポッドが起動していない場合は再起動を行ったりするエージェント。
  • cAdvisor:Container Advisorの略で、コンテナのリソース監視を行う。Googleが開発しており、ソースコードはhttps://github.com/google/cadvisorにある。
  • プロキシ(Proxy):簡易なL3プロキシ
  • APIサーバ(APIs):kubectlコマンドからの命令を受けて、ポッド、サービス、レプリケーションコントローラを操作する機能を提供する。
  • スケジューラ(Schedular):コンテナをどのミニオン上で動かすかを決定する。

Kubernetesの基本機能

  • コンテナ操作機能:複数コンテナをPod単位でグルーピングし、配備/削除/起動/停止を行います。
  • フェイルオーバー機能:コンテナが異常終了したことを検知し再起動させます。
  • スケーリング機能:起動しているコンテナ数を増減させます。
  • スケジューリング機能:コンテナを任意のホストに割り振ります。
  • ロードバランス機能:複数コンテナにリクエストを振り分けて負荷分散を行います。
  • サービスディスカバリ機能:サービスへのルーティングを自動で提供します。
  • セキュリティ:「Kubernetes API」の実行に、ユーザ認証/TSL認証を持たせることが可能です。

Kubernetesで使われている関連製品

  • etcd:分散型設定共有サービス
  • Flannel:仮想ネットワーク機構
  • OpenVSwitch:仮想ネットワーク機構
  • cAdvisor:コンテナリソース監視

参考文献

46
42
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
46
42