Kubernetesとは何ですか? コンテナ化とデプロイのガイド
公開: 2022-03-11少し前に、モノリスWebアプリケーションを使用しました。巨大なコードベースは、新しい機能や機能で成長し、巨大で動きが遅く、管理が難しい巨人になりました。 現在、開発者、アーキテクト、DevOpsの専門家の数が増えており、巨大なモノリスよりもマイクロサービスを使用する方がよいという意見が出ています。 通常、マイクロサービスベースのアーキテクチャを使用するということは、モノリスを少なくとも2つのアプリケーション(フロントエンドアプリとバックエンドアプリ(API))に分割することを意味します。 マイクロサービスを使用することを決定した後、疑問が生じます。どの環境でマイクロサービスを実行するのが良いですか? サービスを安定させ、管理と展開を容易にするために何を選択する必要がありますか? 簡単な答えは次のとおりです。Dockerを使用してください。
この記事では、コンテナーを紹介し、Kubernetesについて説明し、CircleCIを使用してアプリをコンテナー化してKubernetesクラスターにデプロイする方法を説明します。
Docker? Dockerとは何ですか?
Dockerは、DevOps(およびあなたの生活)をより簡単にするために設計されたツールです。 Dockerを使用すると、開発者はコンテナーでアプリケーションを作成、デプロイ、実行できます。 コンテナを使用すると、開発者は、ライブラリやその他の依存関係など、必要なすべてのパーツを含むアプリケーションをパッケージ化し、すべてを1つのパッケージとして出荷できます。
開発者はコンテナを使用して、イメージを任意のOSに簡単に(再)デプロイできます。 Dockerをインストールしてコマンドを実行するだけで、アプリケーションが稼働します。 ああ、ホストOSの新しいバージョンのライブラリとの不整合について心配する必要はありません。 さらに、同じホストでより多くのコンテナーを起動できます。同じアプリですか、それとも別のアプリですか。 関係ありません。
Dockerは素晴らしいツールのようです。 しかし、どのように、どこでコンテナを起動する必要がありますか?
コンテナを実行する方法と場所には多くのオプションがあります。AWSElasticContainerService(AWS Fargateまたは水平および垂直の自動スケーリングを備えたリザーブドインスタンス)。 AzureまたはGoogleCloudで事前定義されたDockerイメージを使用するクラウドインスタンス(テンプレート、インスタンスグループ、自動スケーリングを使用)。 Dockerを使用して独自のサーバー上で; または、もちろん、Kubernetes! Kubernetesは、2014年にGoogleのエンジニアによって仮想化とコンテナ用に特別に作成されました。
Kubernetes? それは何ですか?
Kubernetesは、コンテナの実行、コンテナの管理、デプロイの自動化、デプロイのスケーリング、イングレスの作成と設定、ステートレスまたはステートフルアプリケーションのデプロイなどを可能にするオープンソースシステムです。 基本的に、1つ以上のインスタンスを起動し、Kubernetesをインストールして、それらをKubernetesクラスターとして操作できます。 次に、KubernetesクラスターのAPIエンドポイントを取得し、 kubectl
(Kubernetesクラスターを管理するためのツール)を構成すると、Kubernetesを提供する準備が整います。
では、なぜそれを使用する必要があるのでしょうか。
Kubernetesを使用すると、計算リソースを最大限に活用できます。 Kubernetesを使用すると、Kubernetesが帆を埋めて、船のキャプテン(インフラストラクチャ)になります。 Kubernetesを使用すると、サービスはHAになります。 そして最も重要なことは、Kubernetesを使用すると、かなりのお金を節約できます。
有望に見えます! 特にそれがお金を節約するなら! もっと話しましょう!
Kubernetesは日々人気を集めています。 さらに深く掘り下げて、内部にあるものを調べてみましょう。
フードの下で:Kubernetesとは何ですか?
Kubernetesはシステム全体の名前ですが、あなたの車のように、Kubernetesを機能させるために完全に調和して機能する多くの小さな部品があります。 それらが何であるかを学びましょう。
マスターノード–Kubernetesクラスター全体のコントロールパネル。 マスターのコンポーネントは、クラスター内の任意のノードで実行できます。 主なコンポーネントは次のとおりです。
- APIサーバー:すべてのRESTコマンドのエントリポイントであり、ユーザーがアクセスできるマスターノードの唯一のコンポーネントです。
- データストア: Kubernetesクラスターで使用される強力で一貫性のある高可用性のKey-Valueストレージ。
- スケジューラー:新しく作成されたポッドを監視し、それらをノードに割り当てます。 ノードへのポッドとサービスのデプロイは、スケジューラーが原因で発生します。
- コントローラーマネージャー:クラスター内のルーチンタスクを処理するすべてのコントローラーを実行します。
- ワーカーノード:プライマリノードエージェント。ミニオンノードとも呼ばれます。 ポッドはここで実行されます。 ワーカーノードには、コンテナー間のネットワークを管理し、マスターノードと通信し、スケジュールされたコンテナーにリソースを割り当てるために必要なすべてのサービスが含まれています。
- Docker:各ワーカーノードで実行され、イメージと開始コンテナーをダウンロードします。
- Kubelet:ポッドの状態を監視し、コンテナーが稼働していることを確認します。 また、データストアと通信し、サービスに関する情報を取得し、新しく作成されたサービスに関する詳細を書き込みます。
- Kube-proxy:単一のワーカーノード上のサービスのネットワークプロキシとロードバランサー。 トラフィックルーティングを担当します。
- Kubectl:ユーザーがKubernetesAPIサーバーと通信するためのCLIツール。
ポッドとサービスとは何ですか?
ポッドはKubernetesクラスターの最小単位であり、巨大な建物の壁にある1つのレンガのようなものです。 ポッドは、一緒に実行する必要があり、リソース(Linux名前空間、cgroup、IPアドレス)を共有できるコンテナーのセットです。 ポッドは長生きすることを目的としていません。
サービスは、多数のポッドの上に抽象化されたものであり、通常、他のサービスが仮想IPアドレスを介してサービスと通信するには、その上にプロキシが必要です。
簡単な展開例
Kubernetesを実行するためのプラットフォームとして、単純なRubyonRailsアプリケーションとGKEを使用します。 実際には、AWSまたはAzureでKubernetesを使用したり、独自のハードウェアでクラスターを作成したり、 minikube
を使用してローカルでKubernetesを実行したりできます。これらのオプションはすべてこのページにあります。
このアプリのソースファイルは、このGitHubリポジトリにあります。
新しいRailsアプリを作成するには、以下を実行します。
rails new blog
config/database.yml file
で本番用にMySQL接続を構成するには:
production: adapter: mysql2 encoding: utf8 pool: 5 port: 3306 database: <%= ENV['DATABASE_NAME'] %> host: 127.0.0.1 username: <%= ENV['DATABASE_USERNAME'] %> password: <%= ENV['DATABASE_PASSWORD'] %>
Articleモデル、コントローラー、ビュー、および移行を作成するには、以下を実行します。
rails g scaffold Article title:string description:text
Gemfileにgemを追加するには:
gem 'mysql2', '< 0.6.0', '>= 0.4.4' gem 'health_check'
Dockerイメージを作成するには、Dockerfileを取得して実行します。
docker build -t REPO_NAME/IMAGE_NAME:TAG . && docker push REPO_NAME/IMAGE_NAME:TAG
Kubernetesクラスターを作成するときが来ました。 GKEページを開き、Kubernetesクラスターを作成します。 クラスターが作成されたら、[接続ボタン]をクリックしてコマンドをコピーします。gCloudCLIツール(方法)とkubectlがインストールおよび構成されていることを確認してください。 コピーしたコマンドをPCで実行し、Kubernetesクラスターへの接続を確認します。 kubectl cluster-info
を実行します。
アプリをk8sクラスターにデプロイする準備が整いました。 MySQLデータベースを作成しましょう。 gCloudコンソールでSQLページを開き、アプリケーションのMySQLDBインスタンスを作成します。 インスタンスの準備ができたら、ユーザーとDBを作成し、インスタンス接続名をコピーします。
また、サイドカーコンテナからMySQL DBにアクセスするために、[ APIとサービス]ページでサービスアカウントキーを作成する必要があります。 そのプロセスの詳細については、こちらをご覧ください。 ダウンロードしたファイルの名前をservice-account.json
に変更します。 後でそのファイルに戻ります。
アプリケーションをKubernetesにデプロイする準備ができましたが、最初に、アプリケーションのシークレットを作成する必要があります。これは、機密データを保存するために作成されたKubernetesのシークレットオブジェクトです。 以前にダウンロードservice-account.json
ファイルをアップロードします。

kubectl create secret generic mysql-instance-credentials \ --from-file=credentials.json=service-account.json
アプリケーションのシークレットを作成します。
kubectl create secret generic simple-app-secrets \ --from-literal=username=$MYSQL_PASSWORD \ --from-literal=password=$MYSQL_PASSWORD \ --from-literal=database-name=$MYSQL_DB_NAME \ --from-literal=secretkey=$SECRET_RAILS_KEY
値を置き換えるか、環境変数を自分の値に設定することを忘れないでください。
デプロイメントを作成する前に、デプロイメントファイルを見てみましょう。 3つのファイルを1つに連結しました。 最初の部分は、ポート80を公開し、ポート80に着信するすべての接続を3000に転送するサービスです。このサービスには、接続を転送するポッドをサービスが認識するセレクターがあります。
ファイルの次の部分はデプロイメントです。これは、デプロイメント戦略(ポッド内で起動されるコンテナー、環境変数、リソース、プローブ、各コンテナーのマウント、およびその他の情報)を記述しています。
最後の部分は、水平ポッドオートスケーラーです。 HPAの構成は非常に単純です。 デプロイメントセクションでコンテナのリソースを設定しないと、 HPAが機能しないことに注意してください。
GKE編集ページでKubernetesクラスターの垂直オートスケーラーを設定できます。 また、非常にシンプルな構成になっています。
それをGKEクラスターに出荷する時が来ました! まず、ジョブを介して移行を実行する必要があります。 実行する:
kubectl apply -f rake-tasks-job.yaml
–このジョブはCI/CDプロセスに役立ちます。
kubectl apply -f deployment.yaml
–サービス、デプロイメント、およびHPAを作成します。
次に、次のコマンドを実行してポッドを確認しますkubectl get pods -w
NAME READY STATUS RESTARTS AGE sample-799bf9fd9c-86cqf 2/2 Running 0 1m sample-799bf9fd9c-887vv 2/2 Running 0 1m sample-799bf9fd9c-pkscp 2/2 Running 0 1m
次に、アプリケーションの入力を作成しましょう。
- 静的IPを作成します
gcloud compute addresses create sample-ip --global
- 入力(ファイル)を作成します:
kubectl apply -f ingress.yaml
- 入力が作成されていることを確認し、IPを取得します
kubectl get ingress -w
- アプリケーションのドメイン/サブドメインを作成します。
CI / CD
CircleCIを使用してCI/CDパイプラインを作成しましょう。 実際、CircleCIを使用してCI / CDパイプラインを作成するのは簡単ですが、このようなテストなしの迅速で汚い完全自動展開プロセスは小さなプロジェクトでは機能しますが、深刻な場合はこれを行わないでください。 、新しいコードに本番環境で問題がある場合は、お金を失うことになります。 そのため、堅牢な展開プロセスの設計、完全なロールアウトの前にカナリアタスクを起動する、カナリアの開始後にログのエラーを確認するなどを検討する必要があります。
現在、小規模で単純なプロジェクトがあるので、完全に自動化された、テストなしのCI/CD展開プロセスを作成しましょう。 まず、CircleCIをリポジトリに統合する必要があります。すべての手順はここにあります。 次に、CircleCIシステムの手順を含む構成ファイルを作成する必要があります。 構成は非常に単純に見えます。 主なポイントは、GitHubリポジトリにはmaster
とproduction
の2つのブランチがあるということです。
- マスターブランチは、新しいコードの開発用です。 誰かが新しいコードをマスターブランチにプッシュすると、CircleCIはマスターブランチのワークフロー(コードのビルドとテスト)を開始します。
- 本番ブランチは、新しいバージョンを本番環境にデプロイするためのものです。 本番ブランチのワークフローは次のとおりです。新しいコードをプッシュして(またはさらに良いことに、マスターブランチから本番にPRを開いて)、新しいビルドおよびデプロイメントプロセスをトリガーします。 ビルド中に、CircleCIは新しいDockerイメージを作成し、それをGCRにプッシュして、デプロイメント用の新しいロールアウトを作成します。 ロールアウトが失敗した場合、CircleCIはロールバックプロセスをトリガーします。
ビルドを実行する前に、CircleCIでプロジェクトを構成する必要があります。 APIで新しいサービスアカウントを作成し、GCloudのサービスページで次の役割を果たします。GCRとGKEへのフルアクセス、ダウンロードしたJSONファイルを開いてコンテンツをコピーし、CircleCIのプロジェクト設定で名前を付けて新しい環境変数を作成します。 GCLOUD_SERVICE_KEY
を選択し、サービスアカウントファイルの内容を値として貼り付けます。 また、次のenv変数を作成する必要があります: GOOGLE_PROJECT_ID
(GCloudコンソールのホームページにあります)、 GOOGLE_COMPUTE_ZONE
(GKEクラスターのゾーン)、およびGOOGLE_CLUSTER_NAME
(GKEクラスター名)。
CircleCIでの最後のステップ(デプロイ)は次のようになります。
kubectl patch deployment sample -p '{"spec":{"template":{"spec":{"containers":[{"name":"sample","image":"gcr.io/test-d6bf8/simple:'"$CIRCLE_SHA1"'"}]}}}}' if ! kubectl rollout status deploy/sample; then echo "DEPLOY FAILED, ROLLING BACK TO PREVIOUS" kubectl rollout undo deploy/sample # Deploy failed -> notify slack else echo "Deploy succeeded, current version: ${CIRCLE_SHA1}" # Deploy succeeded -> notify slack fi deployment.extensions/sample patched Waiting for deployment "sample" rollout to finish: 2 out of 3 new replicas have been updated... Waiting for deployment "sample" rollout to finish: 2 out of 3 new replicas have been updated... Waiting for deployment "sample" rollout to finish: 2 out of 3 new replicas have been updated... Waiting for deployment "sample" rollout to finish: 1 old replicas are pending termination... Waiting for deployment "sample" rollout to finish: 1 old replicas are pending termination... Waiting for deployment "sample" rollout to finish: 1 old replicas are pending termination... Waiting for deployment "sample" rollout to finish: 2 of 3 updated replicas are available... Waiting for deployment "sample" rollout to finish: 2 of 3 updated replicas are available... deployment "sample" successfully rolled out Deploy succeeded, current version: 512eabb11c463c5431a1af4ed0b9ebd23597edd9
結論
新しいKubernetesクラスタを作成するプロセスはそれほど難しくないようです。 そして、CI / CDプロセスは本当に素晴らしいです!
はい! Kubernetesは素晴らしいです! Kubernetesを使用すると、システムがより安定し、管理しやすくなり、システムのキャプテンになります。 言うまでもなく、Kubernetesはシステムを少しゲーム化し、マーケティングに+100ポイントを与えます。
基本を理解したので、さらに進んでこれをより高度な構成に変えることができます。 今後の記事でさらに取り上げる予定ですが、それまでの間、課題があります。クラスター内にステートフルDB(バックアップを作成するためのサイドカーポッドを含む)を配置して、アプリケーション用の堅牢なKubernetesクラスターを作成し、Jenkinsをインストールします。 CI / CDパイプライン用の同じKubernetesクラスターを使用し、Jenkinsがビルドのスレーブとしてポッドを使用できるようにします。 入力用のSSL証明書を追加/取得するには、certmanagerを使用します。 Stackdriverを使用して、アプリケーションの監視およびアラートシステムを作成します。
Kubernetesは拡張が簡単で、ベンダーロックインがなく、インスタンスの料金を支払っているので、コストを節約できるので優れています。 ただし、すべての人がKubernetesの専門家であるとは限らず、新しいクラスターをセットアップする時間もあります。別の見方をすれば、仲間のToptaler Amin Shah Gilaniが、Heroku、GitLab CI、および彼がすでに理解している大量の自動化を使用することを主張しています。効果的な初期デプロイパイプラインを構築する方法で、より多くのコードを記述し、より少ない操作タスクを実行するため。
- 数学を行う:オーケストレーターを使用したマイクロサービスアプリケーションの自動スケーリング
- K8s / Kubernetes:AWS vs. GCP vs. Azure
- Kubernetesサービスメッシュの比較