概要
Kubernetesは、コンテナ化されたアプリケーションのデプロイ、スケーリング、管理を自動化するためのオープンソースのコンテナオーケストレーションプラットフォームである。
Kubernetesという名前は、ギリシャ語で操舵手や水先案内人を意味し、K8sという略称でも広く知られている。
Kubernetesは、Googleが2014年にオープンソース化したプロジェクトであり、Google内部で運用されていたBorgシステムの設計思想を基に開発された。
現在は、Cloud Native Computing Foundation (CNCF) によって管理されており、世界中の開発者コミュニティによって継続的に開発が進められている。
Kubernetesは、以下の主要機能を提供する。
| 機能名 | 説明 |
|---|---|
| 自動スケーリング | アプリケーションの負荷に応じて、コンテナの数を自動的に増減させる。 |
| 自己修復機能 | コンテナの障害を検出し、自動的に再起動やスケジューリングを実行する。 |
| サービスディスカバリとロードバランシング | コンテナに対するネットワークトラフィックを分散し、安定したサービス提供を実現する。 |
| ストレージオーケストレーション | ローカルストレージ、クラウドプロバイダー、ネットワークストレージ等、様々なストレージシステムを自動的にマウントする。 |
| 自動ロールアウトとロールバック | アプリケーションの更新を段階的に展開し、問題が発生した場合は自動的に以前のバージョンに戻す。 |
| シークレット管理と設定管理 | 機密情報や設定データを安全に管理し、コンテナに提供する。 |
Kubernetesは、宣言的な構成管理をサポートしており、YAML形式のマニフェストファイルによって、インフラストラクチャの状態を定義できる。
この宣言的アプローチにより、Infrastructure as Code (IaC) の実現が容易になる。
Kubernetesの基本
Kubernetesをデプロイするとクラスタが展開される。
Kubernetesクラスタは、コンテナ化されたソフトウェアを実行するノード (Node) と呼ばれるワーカーマシンの集合である。
ソフトウェアのコンポーネントはPodと呼ばれ、下図のように、このPodがノードに1つ以上の含まれて展開される。
ノードの制御は、kubeletと呼ばれるエージェントで行われており、ノードへのアクセスはkube-proxyと呼ばれるプロキシを介して行われる。
また、コントロールプレーンと呼ばれるコンポーネントは、クラスタを制御する機能を持つ。
| コンポーネントタイプ | コンポーネント名 | 説明 |
|---|---|---|
| コントロールプレーンコンポーネント | kube-apiserver | Kubernetes APIを外部に提供する。Kubernetesコントロールプレーンのフロントエンド |
| コントロールプレーンコンポーネント | etcd | 一貫性、高可用性を持ったキーバリューストアで、Kubernetesの全てのクラスター情報の保存場所 |
| コントロールプレーンコンポーネント | kube-scheduler | Podにノードが割り当てられているかどうかを確認して、割り当てを行う。 |
| コントロールプレーンコンポーネント | kube-controller-manager | 通知やPodの数を監視する複数のコントローラプロセスを実行する。 |
| コントロールプレーンコンポーネント | cloud-controller-manager | 基盤であるクラウドプロバイダーと対話するコントローラを実行する。 |
| ノードコンポーネント | kubelet | クラスタ内の各ノードで実行されるエージェント。各コンテナがPodで実行されていることを保証する。 |
| ノードコンポーネント | kube-proxy | クラスター内の各nodeで動作しているネットワークプロキシ |
| コンテナランタイム | コンテナランタイム | コンテナの実行を担当する。 |
主要コンセプト
Pod
Podは、Kubernetesにおける最小のデプロイ単位である。
Podは、1つ以上のコンテナを含むことができ、同一Pod内のコンテナは同じネットワークネームスペースとストレージを共有する。
通常、1つのPodには1つの主要コンテナと、必要に応じてサイドカーコンテナが含まれる。
Pod内のコンテナは、localhostを介して相互に通信でき、同じIPアドレスとポート空間を共有する。
基本的なPodマニフェストの例を以下に示す。
apiVersion: v1
kind: Pod
metadata:
name: nginx-pod
spec:
containers:
- name: nginx
image: nginx:1.21
ports:
- containerPort: 80
ReplicaSet
ReplicaSetは、指定された数のPodレプリカが常に実行されていることを保証するリソースである。
ReplicaSetは、Podの数を維持するための自己修復機能を提供し、Podが障害で停止した場合は自動的に新しいPodを起動する。
ただし、ReplicaSetは通常、直接使用するのではなく、Deploymentを通じて管理することが推奨される。
ReplicaSetは、セレクタに基づいてPodを管理し、ラベルマッチングによって制御対象のPodを識別する。
Deployment
Deploymentは、ReplicaSetとPodの宣言的な更新を提供するリソースである。
Deploymentは、以下の機能を提供する。
- ローリングアップデート
- 段階的にPodを更新し、ダウンタイムを最小化する。
- ロールバック
- 問題が発生した場合、以前のバージョンに自動的に戻す。
- スケーリング
- Podのレプリカ数を簡単に増減させる。
Deploymentマニフェストの例を以下に示す。
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
spec:
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.21
ports:
- containerPort: 80
StatefulSet
StatefulSetは、ステートフルアプリケーションを管理するためのリソースである。
StatefulSetは、以下の保証を提供する。
- 安定したネットワークID
- Podに対して、予測可能で一貫した名前とホスト名が割り当てられる。
- 安定した永続ストレージ
- 各Podに対して、専用の永続ボリュームが割り当てられる。
- 順序付けられたデプロイとスケーリング
- Podが順序通りに起動および停止される。
StatefulSetは、データベース、分散ストレージ、メッセージキュー等、ステートフルな性質を持つアプリケーションに適している。
DaemonSet
DaemonSetは、クラスタ内のすべてのノード (または一部のノード) で、特定のPodを実行することを保証するリソースである。
DaemonSetは、以下の用途に使用される。
- クラスタストレージデーモン
- ログ収集デーモン
- ノード監視デーモン
新しいノードがクラスタに追加されると、DaemonSetは自動的にそのノードにPodを配置する。
ノードがクラスタから削除されると、そのノード上のPodもガベージコレクションされる。
Job / CronJob
Jobは、1つ以上のPodを作成し、指定された数のPodが正常に完了するまで実行を継続するリソースである。
Jobは、バッチ処理やワンタイムタスクに使用され、完了すると終了する。
Podが正常に完了すると、Jobは完了したPodの数を追跡し、指定された完了数に達すると、Job自体が完了とみなされる。
CronJobは、スケジュールに基づいてJobを定期的に実行するリソースである。
Linuxのcronと同様に、Cron形式のスケジュール表記を使用する。
Jobマニフェストの例を以下に示す。
apiVersion: batch/v1
kind: Job
metadata:
name: batch-job
spec:
template:
spec:
containers:
- name: worker
image: busybox
command: ["echo", "Hello Kubernetes"]
restartPolicy: Never
backoffLimit: 4
Service
Serviceは、Podのグループに対してネットワークアクセスを提供するリソースである。
Kubernetesでは、Podは動的に作成および削除されるため、IPアドレスが変動する。
Serviceは、Podのグループに対して安定したIPアドレスとDNS名を提供し、トラフィックをロードバランシングする。
Serviceには、以下の4つのタイプがある。
| サービスタイプ | 説明 |
|---|---|
| ClusterIP (デフォルト) | クラスタ内部のみからアクセス可能な仮想IPを割り当てる。 外部からはアクセスできない。 |
| NodePort | 各ノードの特定ポート (30000-32767の範囲) を介して、Serviceを外部に公開する。 クラスタ外部から、ノードのIPアドレスとNodePortを使用してアクセスできる。 |
| LoadBalancer | クラウドプロバイダーのロードバランサーを使用して、Serviceを外部に公開する。 外部ロードバランサーが自動的にプロビジョニングされる。 |
| ExternalName | Serviceを外部のDNS名にマッピングする。 CNAMEレコードを返す。 |
Serviceマニフェストの例を以下に示す。
apiVersion: v1
kind: Service
metadata:
name: nginx-service
spec:
selector:
app: nginx
ports:
- protocol: TCP
port: 80
targetPort: 80
type: ClusterIP
Ingress
Ingressは、クラスタ外部からクラスタ内のServiceへのHTTPおよびHTTPSルートを公開するリソースである。
Ingressは、以下の機能を提供する。
- URLベースのルーティング
- パスやホスト名に基づいて、トラフィックを異なるServiceに振り分ける。
- ロードバランシング
- SSL/TLS終端
- HTTPSの終端処理を一元化する。
Ingressを機能させるためには、Ingressコントローラ (NGINX Ingress Controller、Traefik等) をクラスタにデプロイする必要がある。
Ingressマニフェストの例を以下に示す。
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: nginx-ingress
spec:
rules:
- host: example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: nginx-service
port:
number: 80
Namespace
Namespaceは、単一のクラスタ内でリソースをグループ化し、論理的に分離するためのメカニズムである。
Namespaceは、以下の用途で使用される。
- マルチテナント環境の構築
- 環境の分離 (開発、ステージング、本番)
- リソースクォータの適用
- アクセス制御の範囲設定
Kubernetesには、デフォルトで以下のNamespaceが存在する。
| Namespace名 | 説明 |
|---|---|
| default | デフォルトのNamespace 特に指定しない場合、リソースはここに作成される。 |
| kube-system | Kubernetesシステムコンポーネントが配置されるNamespace |
| kube-public | 全てのユーザから読み取り可能なNamespace |
| kube-node-lease | ノードのリース情報を保持するNamespace |
ConfigMap / Secret
ConfigMapは、非機密の設定データをキーバリューペアとして保存するリソースである。
ConfigMapは、設定ファイルや環境変数をコンテナイメージから分離し、アプリケーションの可搬性を向上させる。
ConfigMapのデータは、環境変数、コマンドライン引数、またはボリュームとしてPodにマウントできる。
Secretは、パスワード、トークン、SSH鍵等の機密情報を保存するリソースである。
Secretのデータは、Base64エンコードされて保存されるが、これは暗号化ではないため、etcdの暗号化を有効にすることが推奨される。
Secretは、環境変数またはボリュームとしてPodにマウントできる。
ConfigMapマニフェストの例を以下に示す。
apiVersion: v1
kind: ConfigMap
metadata:
name: app-config
data:
database_url: "mysql://db:3306/mydb"
log_level: "info"
Secretマニフェストの例を以下に示す。
apiVersion: v1
kind: Secret
metadata:
name: db-secret
type: Opaque
data:
username: YWRtaW4=
password: cGFzc3dvcmQ=
Volume / PersistentVolume / PersistentVolumeClaim
Volumeは、Podに対してストレージを提供するメカニズムである。
コンテナのファイルシステムは一時的であり、コンテナが再起動するとデータが失われる。
Volumeを使用することで、データの永続化とコンテナ間のデータ共有が可能になる。
PersistentVolume (PV) は、クラスタレベルでプロビジョニングされた永続的なストレージリソースである。
PVは、管理者によって手動でプロビジョニングされるか、StorageClassを使用して動的にプロビジョニングされる。
PVは、Pod のライフサイクルとは独立しており、Podが削除されてもデータは保持される。
PersistentVolumeClaim (PVC) は、ユーザがストレージをリクエストするためのリソースである。
PVCは、必要なストレージのサイズとアクセスモードを指定し、条件に合致するPVをバインドする。
Podは、PVCをVolumeとして参照することで、永続的なストレージを使用できる。
マニフェストファイル
Kubernetesでは、リソースの定義をYAML形式またはJSON形式のマニフェストファイルで記述する。
マニフェストファイルは、宣言的な構成管理を実現し、Infrastructure as Code (IaC) の基盤となる。
基本構造
Kubernetesのマニフェストファイルは、以下の4つの必須フィールドを持つ。
| フィールド名 | 説明 |
|---|---|
| apiVersion | 使用するKubernetes APIのバージョンを指定する。 リソースの種類によって異なる。(例: v1, apps/v1, batch/v1) |
| kind | 作成するリソースの種類を指定する。(例: Pod, Deployment, Service) |
| metadata | リソースの識別情報を定義する。(名前、ラベル、アノテーション等) |
| spec | リソースの期待される状態 (desired state) を定義する。 リソースの種類によって内容が異なる。 |
基本的なマニフェスト構造の例を以下に示す。
apiVersion: v1
kind: Pod
metadata:
name: example-pod
labels:
app: example
spec:
containers:
- name: nginx
image: nginx:latest
Podのマニフェスト
Podマニフェストの例を以下に示す。
apiVersion: v1
kind: Pod
metadata:
name: webapp-pod
labels:
app: webapp
environment: production
spec:
containers:
- name: webapp
image: nginx:1.21
ports:
- containerPort: 80
env:
- name: ENV_NAME
value: "production"
resources:
requests:
memory: "64Mi"
cpu: "250m"
limits:
memory: "128Mi"
cpu: "500m"
volumeMounts:
- name: config-volume
mountPath: /etc/config
volumes:
- name: config-volume
configMap:
name: app-config
restartPolicy: Always
上記マニフェストの主要な要素を以下に示す。
| フィールド名 | 説明 |
|---|---|
| labels | リソースの識別と選択に使用するキーバリューペア |
| ports | コンテナが公開するポート番号 |
| env | コンテナ内の環境変数 |
| resources | CPUとメモリのリクエストとリミット |
| volumeMounts | コンテナにマウントするボリューム |
| restartPolicy | コンテナの再起動ポリシー (Always, OnFailure, Never) |
Deploymentのマニフェスト
Deploymentマニフェストの例を以下に示す。
apiVersion: apps/v1
kind: Deployment
metadata:
name: webapp-deployment
labels:
app: webapp
spec:
replicas: 3
selector:
matchLabels:
app: webapp
strategy:
type: RollingUpdate
rollingUpdate:
maxSurge: 1
maxUnavailable: 1
template:
metadata:
labels:
app: webapp
spec:
containers:
- name: webapp
image: nginx:1.21
ports:
- containerPort: 80
livenessProbe:
httpGet:
path: /health
port: 80
initialDelaySeconds: 30
periodSeconds: 10
readinessProbe:
httpGet:
path: /ready
port: 80
initialDelaySeconds: 5
periodSeconds: 5
上記マニフェストの主要な要素を以下に示す。
| フィールド名 | 説明 |
|---|---|
| replicas | 起動するPodのレプリカ数。 |
| selector | Deploymentが管理するPodを選択するためのラベルセレクタ。 |
| strategy | 更新戦略 (RollingUpdate または Recreate)。 |
| maxSurge | 更新中に作成できる追加Podの最大数。 |
| maxUnavailable | 更新中に使用不可になってもよいPodの最大数。 |
| livenessProbe | コンテナの生存確認プローブ。 |
| readinessProbe | コンテナの準備完了確認プローブ。 |
Serviceのマニフェスト
ClusterIPタイプのServiceマニフェストの例を以下に示す。
apiVersion: v1
kind: Service
metadata:
name: webapp-service
spec:
selector:
app: webapp
ports:
- name: http
protocol: TCP
port: 80
targetPort: 80
type: ClusterIP
NodePortタイプのServiceマニフェストの例を以下に示す。
apiVersion: v1
kind: Service
metadata:
name: webapp-nodeport
spec:
selector:
app: webapp
ports:
- name: http
protocol: TCP
port: 80
targetPort: 80
nodePort: 30080
type: NodePort
上記マニフェストの主要な要素を以下に示す。
| フィールド名 | 説明 |
|---|---|
| selector | トラフィックを転送するPodを選択するためのラベルセレクタ。 |
| port | Service が公開するポート番号。 |
| targetPort | トラフィックを転送する先のコンテナのポート番号。 |
| nodePort | 各ノードで公開されるポート番号 (NodePortタイプの場合のみ)。 |
Kubernetesのインストール
クラスタのマイナーバージョン差が1つ以内のkubectlのバージョンを使用する必要がある。
例えば、kubectl v1.23のクライアントは、v1.22、v1.23、v1.24と通信することができる。
最新の互換性のあるバージョンのkubectlを使用することにより、予期せぬ問題を回避することができる。
kubectlのインストール
Linux x86-64環境におけるkubectlのインストール手順を以下に示す。
最新バージョンのkubectlをダウンロードする。
curl -LO "https://dl.k8s.io/release/$(curl -L -s https://dl.k8s.io/release/stable.txt)/bin/linux/amd64/kubectl"
ダウンロードしたバイナリを検証する。
curl -LO "https://dl.k8s.io/release/$(curl -L -s https://dl.k8s.io/release/stable.txt)/bin/linux/amd64/kubectl.sha256" echo "$(cat kubectl.sha256) kubectl" | sha256sum --check
kubectlをインストールする。
sudo install -o root -g root -m 0755 kubectl /usr/local/bin/kubectl
環境変数 PATH に、/usr/local/bin が含まれていることを確認する。
インストールされたバージョンを確認する。
kubectl version --client
kubectl convertプラグインのインストール
kubectl convertプラグインは、異なるAPIバージョン間でマニフェストファイルを変換するためのツールである。
最新バージョンのkubectl-convertをダウンロードする。
curl -LO "https://dl.k8s.io/release/$(curl -L -s https://dl.k8s.io/release/stable.txt)/bin/linux/amd64/kubectl-convert"
ダウンロードしたバイナリを検証する。
curl -LO "https://dl.k8s.io/release/$(curl -L -s https://dl.k8s.io/release/stable.txt)/bin/linux/amd64/kubectl-convert.sha256" echo "$(cat kubectl-convert.sha256) kubectl-convert" | sha256sum --check
kubectl-convertをインストールする。
sudo install -o root -g root -m 0755 kubectl-convert /usr/local/bin/kubectl-convert
インストールを確認する。
kubectl convert --help
クラスタの構築
Kubernetesクラスタを構築するための主要な方法について説明する。
開発環境では、minikubeやkindが広く使用され、本番環境では、kubeadmやマネージドKubernetesサービスが選択される。
minikube
minikubeは、ローカル開発環境でKubernetesクラスタを簡単に構築できるツールである。
minikubeは、単一ノードのKubernetesクラスタを、仮想マシンまたはコンテナ内に作成する。
開発、学習、テスト目的に最適であり、本番環境での使用は推奨されない。
minikubeの要件を以下に示す。
- 2[GB]以上のRAM
- 2つ以上のCPU
- 20[GB]のディスクスペース
- コンテナまたは仮想マシン環境 (Docker、QEMU、Hyperkit、Hyper-V、KVM、Parallels、Podman、VirtualBox、VMware Fusion/Workstation)
Linux x86-64環境におけるminikubeのインストール手順を以下に示す。
最新バージョンのminikubeをダウンロードしてインストールする。
curl -LO https://storage.googleapis.com/minikube/releases/latest/minikube-linux-amd64 sudo install minikube-linux-amd64 /usr/local/bin/minikube
minikubeクラスタを起動する。
minikube start
クラスタの状態を確認する。
kubectl cluster-info kubectl get nodes
minikubeの主要なコマンドを以下に示す。
| コマンド | 説明 |
|---|---|
| minikube start | クラスタを起動 |
| minikube stop | クラスタを停止 |
| minikube delete | クラスタを削除 |
| minikube dashboard | Kubernetes Dashboardを開く |
| minikube pause | クラスタを一時停止 |
| minikube unpause | クラスタの一時停止を解除 |
kind
kind (Kubernetes IN Docker) は、Docker コンテナをノードとして使用するローカルKubernetesクラスタツールである。
kindは、主にKubernetes自体のテストに使用されるが、ローカル開発やCI環境でも有用である。
kindは、複数ノードクラスタの構築が容易であり、minikubeよりも軽量で高速に起動する。
kindのインストール手順を以下に示す。
go install sigs.k8s.io/kind@v0.20.0
kindクラスタを作成する。
kind create cluster
特定の名前でクラスタを作成する。
kind create cluster --name my-cluster
クラスタを削除する。
kind delete cluster --name my-cluster
kubeadm
kubeadmは、本番環境対応のKubernetesクラスタを構築するための公式ツールである。
kubeadmは、クラスタの初期化、ノードの参加、証明書管理等、クラスタのライフサイクル管理機能を提供する。
kubeadmを使用する前に、各ノードでコンテナランタイム (containerd、CRI-O等) をインストールする必要がある。
kubeadmの前提条件を以下に示す。
- Linux ホスト
- 2[GB]以上のRAM (マスターノードには4 GB推奨)
- 2つ以上のCPU (マスターノードには4つ推奨)
- ノード間の完全なネットワーク接続
- 各ノードでユニークなホスト名、MACアドレス、product_uuid
- 特定のポートがファイアウォールで開放されている
- スワップが無効化されている
kubeadmでクラスタを初期化する手順を以下に示す。
マスターノードでクラスタを初期化する。
sudo kubeadm init --pod-network-cidr=10.244.0.0/16
初期化が完了すると、kubeconfigの設定と、ワーカーノードを参加させるためのコマンドが表示される。
kubeconfigを設定する。
mkdir -p $HOME/.kube sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config sudo chown $(id -u):$(id -g) $HOME/.kube/config
Podネットワークアドオンをインストールする。
kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
ワーカーノードをクラスタに参加させる。
sudo kubeadm join <マスターノードIP>:6443 --token <トークン> --discovery-token-ca-cert-hash sha256:<ハッシュ>
k3s
k3sは、軽量なKubernetesディストリビューションであり、エッジコンピューティング、IoT、ARM環境に最適化されている。
k3sは、完全なKubernetes機能を提供しながら、バイナリサイズが約100[MB]と非常に小さい。
k3sは、単一バイナリとして配布され、依存関係が最小限であるため、インストールが容易である。
k3sのインストール手順を以下に示す。
curl -sfL https://get.k3s.io | sh -
インストールが完了すると、k3sサービスが自動的に起動する。
kubectlでクラスタにアクセスする。
sudo k3s kubectl get nodes
または、kubeconfigを一般ユーザがアクセスできるようにする。
mkdir -p $HOME/.kube sudo cp /etc/rancher/k3s/k3s.yaml $HOME/.kube/config sudo chown $(id -u):$(id -g) $HOME/.kube/config
kubectlコマンド
kubectlは、Kubernetesクラスタを操作するためのコマンドラインツールである。
kubectlを使用することで、アプリケーションのデプロイ、クラスタリソースの検査と管理、ログの確認等が可能になる。
基本構文
kubectlコマンドの基本構文を以下に示す。
kubectl [command] [TYPE] [NAME] [flags]
| 項目 | 説明 |
|---|---|
| command | 実行する操作 (get、create、apply、delete等) |
| TYPE | リソースタイプ (pod、deployment、service等) |
| NAME | リソース名 |
| flags | オプションフラグ |
kubectlは、kubeconfigファイル (デフォルトでは ~/.kube/config) を使用してクラスタに接続する。
kubeconfigファイルには、クラスタ、ユーザ、コンテキストの情報が含まれる。
主要コマンド
kubectlの主要なコマンドを以下に示す。
| コマンド | 説明 | 使用例 |
|---|---|---|
| get | リソースの一覧を取得 | kubectl get pods |
| describe | リソースの詳細情報を表示 | kubectl describe pod nginx |
| logs | Podのログを表示 | kubectl logs nginx |
| apply | マニフェストファイルを適用 | kubectl apply -f deployment.yaml |
| create | リソースを作成 | kubectl create deployment nginx --image=nginx |
| delete | リソースを削除 | kubectl delete pod nginx |
| exec | Pod内でコマンドを実行 | kubectl exec -it nginx -- bash |
| port-forward | ローカルポートをPodに転送 | kubectl port-forward nginx 8080:80 |
| scale | レプリカ数を変更 | kubectl scale deployment nginx --replicas=5 |
| rollout | ロールアウトを管理 | kubectl rollout status deployment nginx |
| top | リソース使用状況を表示 | kubectl top nodes |
| config | kubeconfigを管理 | kubectl config view |
- リソース取得コマンドの使用例
kubectl get pods kubectl get deployments kubectl get services kubectl get nodes
- 全てのNamespaceのリソースを取得する。
kubectl get pods --all-namespaces kubectl get pods -A
- 詳細情報をYAML形式で出力する。
kubectl get pod nginx -o yaml kubectl get deployment nginx -o json
- リソースの詳細情報を表示する。
kubectl describe pod nginx kubectl describe deployment nginx
- マニフェストファイルを適用する。
kubectl apply -f deployment.yaml kubectl apply -f https://example.com/deployment.yaml
- ディレクトリ内のすべてのマニフェストを適用する。
kubectl apply -f ./manifests/
- リソースを削除する。
kubectl delete pod nginx kubectl delete -f deployment.yaml
- Pod内でコマンドを実行する。
kubectl exec -it nginx -- bash kubectl exec nginx -- ls /etc
- Podのログを表示する。
kubectl logs nginx kubectl logs -f nginx kubectl logs --tail=100 nginx
- ローカルポートをPodに転送する。
kubectl port-forward nginx 8080:80 kubectl port-forward service/nginx 8080:80
- Deploymentをスケールする。
kubectl scale deployment nginx --replicas=5
- ロールアウトステータスを確認する。
kubectl rollout status deployment nginx kubectl rollout history deployment nginx
- ロールバックを実行する。
kubectl rollout undo deployment nginx kubectl rollout undo deployment nginx --to-revision=2
- リソース使用状況を表示する。
kubectl top nodes kubectl top pods
Helm
Helmは、Kubernetesのパッケージマネージャーであり、Kubernetesアプリケーションを定義、インストール、アップグレードするためのツールである。
Helmは、チャートと呼ばれるパッケージ形式を使用し、複雑なKubernetesアプリケーションを簡単にデプロイできる。
Helmチャートは、再利用可能なテンプレートとして機能し、変数の値を変更することで、異なる環境に対応できる。
Helmのインストール
Linux環境におけるHelmのインストール手順を以下に示す。
バイナリをダウンロードしてインストールする。
curl https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-3 | bash
または、パッケージマネージャーを使用してインストールする。
sudo snap install helm --classic
インストールを確認する。
helm version
基本コマンド
Helmの主要なコマンドを以下に示す。
| コマンド | 説明 | 使用例 |
|---|---|---|
| repo add | チャートリポジトリを追加 | helm repo add stable https://charts.helm.sh/stable |
| repo update | リポジトリ情報を更新 | helm repo update |
| search repo | リポジトリからチャートを検索 | helm search repo nginx |
| install | チャートをインストール | helm install my-nginx bitnami/nginx |
| list | インストール済みリリースを表示 | helm list |
| upgrade | リリースをアップグレード | helm upgrade my-nginx bitnami/nginx |
| rollback | リリースをロールバック | helm rollback my-nginx 1 |
| uninstall | リリースをアンインストール | helm uninstall my-nginx |
| status | リリースの状態を表示 | helm status my-nginx |
| get values | リリースの値を取得 | helm get values my-nginx |
- チャートリポジトリを追加する。
helm repo add bitnami https://charts.bitnami.com/bitnami helm repo update
- チャートをインストールする。
helm install my-nginx bitnami/nginx
- カスタム値でインストールする。
helm install my-nginx bitnami/nginx --set replicaCount=3 helm install my-nginx bitnami/nginx -f custom-values.yaml
- インストール済みリリースを表示する。
helm list helm list --all-namespaces
- リリースをアップグレードする。
helm upgrade my-nginx bitnami/nginx --set replicaCount=5
- リリースをアンインストールする。
helm uninstall my-nginx
- Helmチャートの基本的なディレクトリ構造を以下に示す。
mychart/ Chart.yaml values.yaml templates/ deployment.yaml service.yaml ingress.yaml
| ファイル/ディレクトリ名 | 説明 |
|---|---|
| Chart.yaml | チャートのメタデータ (名前、バージョン等) |
| values.yaml | チャートのデフォルト設定値 |
| templates/ | Kubernetesマニフェストのテンプレート |
ネットワーク
Kubernetesのネットワークモデルは、全てのPodが一意のIPアドレスを持ち、Podが異なるノードにあっても、NATなしで直接通信できるフラットなネットワーク空間を提供する。
Kubernetesのネットワークモデルは、以下に示す要件を満たす必要がある。
- 全てのPodは、NATなしで他のすべてのPodと通信できる。
- 全てのノードは、NATなしですべてのPodと通信できる。
- Podが認識する自身のIPアドレスは、他のPodから見たIPアドレスと同じである。
このネットワークモデルは、CNI (Container Network Interface) プラグインによって実装される。
CNIプラグイン
下表に、主要なCNIプラグインを示す。
| プラグイン名 | 説明 |
|---|---|
| Calico | ネットワークポリシーとルーティングを提供する高性能なネットワークプラグイン BGPベースのルーティングとVXLANオーバーレイネットワークの両方をサポートする。 |
| Flannel | シンプルで軽量なオーバーレイネットワークプラグイン VXLANやhost-gwモードをサポートする。 |
| Cilium | eBPFベースの高性能なネットワークおよびセキュリティプラグイン L7レベルのネットワークポリシーと可視化を提供する。 |
| Weave Net | メッシュネットワークを構築し、暗号化をサポートする。 |
- Flannelをインストールする例
kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
- Calicoをインストールする例
kubectl apply -f https://docs.projectcalico.org/manifests/calico.yaml
NetworkPolicy
NetworkPolicyは、Podのネットワークトラフィックを制御するためのリソースである。
NetworkPolicyを使用することで、特定のPod間の通信を許可または拒否できる。
NetworkPolicyは、ファイアウォールルールに似た機能を提供し、マイクロサービス環境におけるセキュリティを向上させる。
NetworkPolicyマニフェストの例を以下に示す。
以下のNetworkPolicyは、app=frontendラベルを持つPodからのみ、app=backendラベルを持つPodのポート8080へのアクセスを許可する。
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: allow-frontend
spec:
podSelector:
matchLabels:
app: backend
policyTypes:
- Ingress
ingress:
- from:
- podSelector:
matchLabels:
app: frontend
ports:
- protocol: TCP
port: 8080
CoreDNS
CoreDNSは、Kubernetesクラスタ内のDNSサーバであり、Serviceの名前解決を提供する。
CoreDNSは、Kubernetesのデフォルトのクラスタ内DNSとして使用され、Pod内からServiceをDNS名で参照できるようにする。
Serviceの名前解決の形式を以下に示す。
- 同一Namespace内のService
- <service-name>
- 異なるNamespace内のService
- <service-name>.<namespace>.svc.cluster.local
例えば、defaultNamespace内のnginx-serviceという名前のServiceは、以下に示すように参照することができる。
curl http://nginx-service curl http://nginx-service.default.svc.cluster.local
ストレージ
Kubernetesは、様々な種類のストレージバックエンドをサポートし、コンテナに永続的なストレージを提供する。
Volumeの種類
Kubernetesでサポートされる主要なVolumeタイプを以下に示す。
| ボリュームタイプ | 説明 |
|---|---|
| emptyDir | Podが作成されると同時に作成され、Podが削除されると削除される一時的なディレクトリ 同一Pod内のコンテナ間でデータを共有するために使用される。 |
| hostPath | ホストノードのファイルシステムのディレクトリをPodにマウントする。 ノードのログやシステムファイルにアクセスする場合に使用される。 |
| configMap | ConfigMapをVolumeとしてマウントし、設定ファイルをPodに提供する。 |
| secret | SecretをVolumeとしてマウントし、機密情報をPodに提供する。 |
| persistentVolumeClaim | PersistentVolumeClaimを使用して、永続的なストレージをPodにマウントする。 |
emptyDirの使用例を以下に示す。
apiVersion: v1
kind: Pod
metadata:
name: test-pod
spec:
containers:
- name: container1
image: busybox
volumeMounts:
- name: shared-data
mountPath: /data
volumes:
- name: shared-data
emptyDir: {}
PersistentVolume / PersistentVolumeClaim
PersistentVolume (PV) とPersistentVolumeClaim (PVC) は、永続的なストレージを抽象化し、管理する仕組みである。
- PVマニフェストの例
apiVersion: v1 kind: PersistentVolume metadata: name: pv-example spec: capacity: storage: 10Gi accessModes: - ReadWriteOnce persistentVolumeReclaimPolicy: Retain storageClassName: manual hostPath: path: /mnt/data
- PVCマニフェストの例
apiVersion: v1 kind: PersistentVolumeClaim metadata: name: pvc-example spec: accessModes: - ReadWriteOnce resources: requests: storage: 5Gi storageClassName: manual
- PVCをPodで使用する例
apiVersion: v1 kind: Pod metadata: name: pod-with-pvc spec: containers: - name: app image: nginx volumeMounts: - name: storage mountPath: /usr/share/nginx/html volumes: - name: storage persistentVolumeClaim: claimName: pvc-example
アクセスモードを以下に示す。
| アクセスモード | 説明 |
|---|---|
| ReadWriteOnce (RWO) | 単一のノードから読み書き可能 |
| ReadOnlyMany (ROX) | 複数のノードから読み取り専用でアクセス可能 |
| ReadWriteMany (RWX) | 複数のノードから読み書き可能 |
StorageClass
StorageClassは、動的プロビジョニングのためのストレージの種類を定義するリソースである。
StorageClassを使用することで、PVCが作成されたときに、自動的にPVがプロビジョニングされる。
- StorageClassマニフェストの例
apiVersion: storage.k8s.io/v1 kind: StorageClass metadata: name: fast provisioner: kubernetes.io/gce-pd parameters: type: pd-ssd replication-type: regional-pd
- 動的プロビジョニングを使用するPVCの例
apiVersion: v1 kind: PersistentVolumeClaim metadata: name: dynamic-pvc spec: accessModes: - ReadWriteOnce resources: requests: storage: 10Gi storageClassName: fast
セキュリティ
Kubernetesは、多層的なセキュリティ機能を提供し、クラスタとアプリケーションを保護する。
RBAC
RBAC (Role-Based Access Control) は、ユーザやサービスアカウントのクラスタリソースへのアクセスを制御する仕組みである。
RBACは、以下の4つの主要なリソースで構成される。
| リソースタイプ | 説明 |
|---|---|
| Role | 特定のNamespace内でのリソースへのアクセス権限を定義する。 |
| ClusterRole | クラスタ全体でのリソースへのアクセス権限を定義する。 |
| RoleBinding | RoleをユーザまたはServiceAccountにバインドする。 |
| ClusterRoleBinding | ClusterRoleをユーザまたはServiceAccountにバインドする。 |
- Roleマニフェストの例
apiVersion: rbac.authorization.k8s.io/v1 kind: Role metadata: namespace: default name: pod-reader rules: - apiGroups: [""] resources: ["pods"] verbs: ["get", "watch", "list"]
- RoleBindingマニフェストの例
apiVersion: rbac.authorization.k8s.io/v1 kind: RoleBinding metadata: name: read-pods namespace: default subjects: - kind: User name: alice apiGroup: rbac.authorization.k8s.io roleRef: kind: Role name: pod-reader apiGroup: rbac.authorization.k8s.io
- ClusterRoleマニフェストの例
apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: cluster-admin rules: - apiGroups: ["*"] resources: ["*"] verbs: ["*"]
ServiceAccount
ServiceAccountは、Pod内で実行されるプロセスにアイデンティティを提供するリソースである。
各Namespaceには、デフォルトでdefaultという名前のServiceAccountが存在する。
Podは、ServiceAccountを使用してKubernetes APIにアクセスする時の認証情報を取得する。
ServiceAccountマニフェストの例を以下に示す。
apiVersion: v1
kind: ServiceAccount
metadata:
name: app-sa
namespace: default
PodでServiceAccountを使用する例を以下に示す。
apiVersion: v1
kind: Pod
metadata:
name: app-pod
spec:
serviceAccountName: app-sa
containers:
- name: app
image: nginx
Pod Security Standards
Pod Security Standardsは、Podのセキュリティプロファイルを定義する標準である。
Pod Security Standardsは、3つのレベルを定義する。
| レベル名 | 説明 |
|---|---|
| Privileged | 制限なし。信頼されたワークロード向け。 |
| Baseline | 既知の権限昇格を防ぐための最小限の制限。 |
| Restricted | 強化されたセキュリティ。セキュリティのベストプラクティスに従う。 |
Namespaceレベルでセキュリティポリシーを適用する例を以下に示す。
kubectl label namespace default pod-security.kubernetes.io/enforce=baseline kubectl label namespace default pod-security.kubernetes.io/warn=restricted
モニタリングとロギング
Kubernetesクラスタの健全性とアプリケーションのパフォーマンスを監視するために、モニタリングとロギングが重要である。
Kubernetes Dashboard
Kubernetes Dashboardは、Kubernetesクラスタを管理するためのWebベースのUIである。
Kubernetes Dashboardをインストールする。
kubectl apply -f https://raw.githubusercontent.com/kubernetes/dashboard/v2.7.0/aio/deploy/recommended.yaml
Dashboardにアクセスするために、プロキシを起動する。
kubectl proxy
Webブラウザを起動して、以下に示すURLにアクセスする。
http://localhost:8001/api/v1/namespaces/kubernetes-dashboard/services/https:kubernetes-dashboard:/proxy/
Metrics Server
Metrics Serverは、クラスタのリソース使用状況を収集し、kubectl topコマンドで表示するためのコンポーネントである。
Metrics Serverをインストールする。
kubectl apply -f https://github.com/kubernetes-sigs/metrics-server/releases/latest/download/components.yaml
ノードのリソース使用状況を表示する。
kubectl top nodes
Podのリソース使用状況を表示する。
kubectl top pods kubectl top pods --all-namespaces
Prometheus / Grafana
Prometheusは、時系列データベースであり、Kubernetesクラスタのメトリクスを収集し、保存する。
Grafanaは、Prometheusから収集したデータを可視化するためのダッシュボードツールである。
PrometheusとGrafanaは、kube-prometheus-stackのHelmチャートを使用して簡単にインストールできる。
helm repo add prometheus-community https://prometheus-community.github.io/helm-charts helm repo update helm install prometheus prometheus-community/kube-prometheus-stack
Grafanaにアクセスするために、ポートフォワーディングを設定する。
kubectl port-forward svc/prometheus-grafana 3000:80
Webブラウザで http://localhost:3000 にアクセスして、デフォルトの認証情報 (admin / prom-operator) でログインする。