Upgrade to Pro — share decks privately, control downloads, hide ads and more …

コンテナ研修(Kubernetes基礎編)【ミクシィ22新卒技術研修】

 コンテナ研修(Kubernetes基礎編)【ミクシィ22新卒技術研修】

22新卒技術研修で実施したコンテナ研修の講義資料(Kubernetes基礎編)です。
動画も後日公開予定です。

コンテナ基礎編
https://speakerdeck.com/mixi_engineers/2022-container-training-number-01

※ハンズオン環境は提供していないので、ハンズオンを実際に試していただくことはできません。

B16717ef4b7aab0b253d933c3934f280?s=128

mixi_engineers
PRO

April 22, 2022
Tweet

More Decks by mixi_engineers

Other Decks in Programming

Transcript

  1. コンテナ研修 コンテナをKubernetesにデプロイしてみよう 浅野 大我

  2. 今回の流れ - Kubernetesとは - Kubernetesリソースを理解しよう - Kubernetes Controller、Reconcile Loopについて -

    Namespace, Deployment, Service … - Google Kubernetes Engine (GKE)とは - Kubernetesにアプリをデプロイしてみよう - Deploymentをデプロイしてみよう - Serviceを使ってみよう - Ingressを使ってみよう - Kubernetes Operator (cert-manager)をデプロイしてみよう - クラスタの様子を見てみよう - kubectl get, top, apply - 付録: kubectl apply 近況 2022 - Server-side apply, Strategic Merge Strategy
  3. Kubernetesとは

  4. Kubernetesとは? - GoogleのBorgと呼ばれる実行基盤がある - これを元にしたOSSで、GoogleやCNCFといっ た団体が管理、メンテナンスしている - Borgはコンテナオーケストレーションツール - ホストマシンを意識せずに、効率よくコンテナ

    (アプリケーション)を配置したい - 耐障害性を考えると、ホストマシンを意識しな いようにしたい - Googleではその考えを元にBorgが開発され、運 用されている - Googleの謎技術がOSSになり、一般的に使われ るようになった - 謎技術: Colossus、Andromeda、Zanzibar...
  5. どうしてコンテナオーケストレーションツール? - Borgの論文によるメリットは以下 - リソース管理、障害への処理を隠してエンジニアをアプリケーション開発に集中させる - 高い信頼性と可用性を保つ - 数万台オーダーのマシンでワークロードを効率的に実行させる -

    リソース管理を隠す - YAMLファイルを使ってあらゆるリソースを表現することができる - Kubernetesはkube-schedulerを使ってコンテナを指定したノードへ効率よく配置することができる - 障害への処理 - ノードに障害が発生した際、コンテナは自動的に回復する - 信頼性、可用性 - Kubernetesはetcdと呼ばれる分散ストレージを使って状態を管理している - マルチマスター構成にすることでSPOF(単一障害点)を減らすことができる - Borgは99.999%の可用性を維持している - 数万台オーダーのマシンでワークロードを効率的に実行させる - スケジューラーの実装次第で効率よく配置できる - Gmail、Google Docs、検索、BigTableなどで使われている(らしい)
  6. Kubernetesを簡単に理解する - nginxコンテナを3つ起動する...とする - Pod - コンテナをまとめた単位 - Podの中で複数のコンテナが起動することもあ る

    - ReplicaSet - Podの集合体 - 規定されたPodの数を保つように管理している - Deployment - ReplicaSetを管理している - 指定された構成やReplicaSet自体のアップデー トを担う - リソースをどこに作って、誰がコンテナを作 る? ReplicaSet Deployment
  7. Kubernetesを簡単に理解する - Node に対して Master / Worker という役割を 与える -

    Node: 実際のKubernetesクラスタが動作するマ シン - Master: Kubernetesを司るコントロールプレー ンとして指定されたノード - kube-apiserverはKubernetesを制御するAPI サーバー - リソースの登録や状態の登録を行う - kube-scheduler - Nodeに対してPod(コンテナ類)を割り当てる スケジューラー - Nodeの空き状況を見ていい感じにPodをスケ ジュールする ReplicaSet Deployment
  8. Kubernetesを簡単に理解する - kube-controller-manager - Kubernetesにビルトインされたリソースを監 視、管理するコントローラー - 例えば、 - コンテナ(Deployment,

    Pod, ReplicaSet) - ネットワーク(Service) - ボリューム(Volume) - これらが登録された際に、状態を見て指定され たオブジェクトを作る(=リコンサイルする) - コントローラーが実際にオブジェクトを作るフ ローを見てみる
  9. Kubernetesコントローラーを理解しよう

  10. Kubernetes コントローラーを理解する - Deployment ControllerがDeployment リソースの作成を検知 - Deployment ControllerがReplicaSet リソースを作成

    - ReplicaSet ControllerがReplicaSet リソースの作成を検知 - ReplicaSet ControllerがPod リソースを作成 - 削除時は逆 - オブジェクトの追加や削除をReconcile Loopで行う https://book.kubebuilder.io/
  11. Kubernetesリソース(オブジェクト) を理解しよう

  12. 今回の流れ Cluster Resources Namespaced Resources

  13. Kubernetesリソースを理解しよう apiVersion: apps/v1 kind: Deployment metadata: name: nginx-deployment labels: app:

    nginx spec: replicas: 3 selector: matchLabels: app: nginx template: metadata: labels: app: nginx spec: containers: - name: nginx image: nginx:1.14.2 ports: - containerPort: 80 Deployment Controller PodとReplicaSetを理想的 な状態に保つ
  14. 実際に見てみよう $ kubectl get pod –all-namespaces

  15. どんなPodがデプロイされているのか? NAMESPACE NAME READY STATUS RESTARTS AGE kube-system anet-operator-68784b696b-shwz9 1/1

    Running 0 23h kube-system anetd-8nvcc 1/1 Running 0 23h kube-system anetd-tpfhn 1/1 Running 0 23h kube-system anetd-xtkkm 1/1 Running 0 23h kube-system gke-metadata-server-96927 1/1 Running 0 23h kube-system gke-metadata-server-cxszl 1/1 Running 0 23h kube-system gke-metadata-server-mlrpz 1/1 Running 0 23h kube-system konnectivity-agent-6997b6f8c8-5t786 1/1 Running 0 23h kube-system konnectivity-agent-6997b6f8c8-hwv8s 1/1 Running 0 23h kube-system konnectivity-agent-6997b6f8c8-q84m7 1/1 Running 0 23h kube-system konnectivity-agent-autoscaler-ddccb8b95-nnr25 1/1 Running 0 23h kube-system kube-dns-599484b884-cwx95 3/3 Running 0 23h kube-system kube-dns-599484b884-whxfl 3/3 Running 0 23h kube-system kube-dns-autoscaler-844c9d9448-bq8pm 1/1 Running 0 23h kube-system l7-default-backend-69fb9fd9f9-crw8k 1/1 Running 0 23h kube-system metrics-server-v0.4.5-bbb794dcc-d5pqt 2/2 Running 0 23h kube-system netd-4jgfp 1/1 Running 0 23h kube-system netd-6vjsd 1/1 Running 0 23h kube-system netd-pr97w 1/1 Running 0 23h kube-system pdcsi-node-988v7 2/2 Running 0 23h kube-system pdcsi-node-g44pq 2/2 Running 0 23h kube-system pdcsi-node-qkgkq 2/2 Running 0 23h
  16. Kubernetesリソースを理解しよう apiVersion: v1 kind: Service metadata: name: my-service spec: selector:

    app: MyApp ports: - protocol: TCP port: 80 targetPort: 9376 Service Controller Podを外部に公開するため のコントローラー
  17. 実際に見てみよう $ kubectl get svc –all-namespaces

  18. どんなServiceがデプロイされているのか? $ kubectl get svc --all-namespaces NAMESPACE NAME TYPE CLUSTER-IP

    EXTERNAL-IP PORT(S) AGE default kubernetes ClusterIP 10.112.0.1 <none> 443/TCP 23h kube-system default-http-backend NodePort 10.112.12.179 <none> 80:31114/TCP 23h kube-system kube-dns ClusterIP 10.112.0.10 <none> 53/UDP,53/TCP 23h kube-system metrics-server ClusterIP 10.112.2.112 <none> 443/TCP 23h
  19. Kubernetesリソース(オブジェクト) を理解しよう - Kubernetesのリソース、オブジェクト、APIの分類について理解した - Cluster ResourceとNamespaced Resource - Kubernetesコントローラーの役割について、コマンドを使いながら理解した

    - Deployment - Service
  20. 実際に見てみよう $ kubectl get svc –all-namespaces

  21. Google Kubernetes Engine (GKE) とは

  22. Google Kubernetes Engine (GKE)とは - Google Kuberntes Engine (GKE)はマネージドKubernetesサービスの一つ -

    Kubernetesのコントロールプレーン部分の定期的なアップデートや、コントローラーを提供してく れる - ノードの可用性などを気にせずにKubernetesの恩恵を受けることができる - クラスタネットワーキングや、ノードのカスタマイズがある程度柔軟ではあるが・・・ - アップデートなどの面倒を見る必要はある - ワーカーノードの効率的な活用は自分たちでやる必要がある - 最近ではそのレベルの面倒を見てくれるGKE Autopliotもある - しかし構成が柔軟に変更できないなどの制約もある - Pod単位の課金になる - 今回はStandardと呼ばれる方を扱います
  23. Kubernetesにアプリをデプロイしよう

  24. Kubernetesリソース(オブジェクト) を理解しよう - 簡単なGoで書かれたWebアプリケーション - Deployment、Serviceからなる構成

  25. Kubernetesリソース(オブジェクト) を理解しよう - GKE -> Kubernetes - Network Endpoint =

    Pod - Network Endpoint Group = Service - 負荷分散 (LB) = Ingress - https://medium.com/google-cloud-jp/neg-%E3 %81%A8%E3%81%AF%E4%BD%95%E3%81%8B- cc1e2bbc979e
  26. Kubernetesのリソース: Ingress - Serviceを、さらに外部からのアクセスを管理 するリソース - Serviceそのものはネットワークを管理するも の - type:

    LoadBalancerを使うとPodへL2でアク セスさせることができる - IngressはL7をカバーする - ロードバランサーの設定などができる(ざっ くり) - パスベースでどこへルーティングする - TLS証明書を設定する
  27. Kubernetesのリソース: Secret - パスワードなどを管理するオブジェクトのこ と - Podの環境変数や、コンテナイメージに機密情 報を書き込まないようにするためのもの - Secretを作ってコンテナの環境変数として参

    照させる(他もできる) - 初期状態では暗号化はされていない - Kubernetes RBACを使ってアクセス制御をし たり... - Secretをクラスタ/マニフェスト単位で暗号化 するツールを使う - Secret管理を外部のキーマネジメントシステム にやらせる - 今回は暗号化されていないまま使います
  28. 実際にデプロイしてみよう $ kubectl apply -f namespace.yaml $ kubectl apply -f

    secret.yaml $ kubectl apply -f deployment.yaml $ kubectl get deployment -n namespace $ kubectl get pod -n my-namespace
  29. 実際にデプロイしてみよう $ kubectl apply -f service.yaml $ kubectl apply -f

    ingress.yaml
  30. コンソールでIngressが負荷分散としてデプロイされていることを確認する

  31. Kubernetesリソース(オブジェクト) を理解しよう - Deploymentを変更したとき、どのように ReplicaSet, Podが作成されるのかを観察してみ る - Deploymentのデプロイ戦略 -

    RollingUpdate (デフォルト) - ローリングアップデートされていく - Recreate - Podを全部停止して、作り直す - https://kubernetes.io/ja/docs/concepts/work loads/controllers/deployment/
  32. Exercise: 環境変数を足してDeploymentが新しいReplicaSetを作る ところを見てみよう

  33. 環境変数を足してDeploymentが新しいReplicaSetを作るところを見る 1. Deploymentに環境変数を足す --- a/kubernetes/deployment.yaml +++ b/kubernetes/deployment.yaml @@ -37,6 +37,8

    @@ spec: secretKeyRef: name: secret key: password + - name: HELLO + value: HOGEHOGE livenessProbe: httpGet: path: /liveness 2. applyする kubectl apply -f deployment.yaml このとき、別窓で kubectl get replicaset -w しておく
  34. Kubernetesリソース(オブジェクト) を理解しよう - kubectlを使ってアプリケーションをデプロイした - Deployment - Service - Ingress

    - Exercise - Deploymentのアップデート戦略について調べる - Deployment以外のPodのコントローラーについて調べてみる - Serviceのタイプについて詳しく調べてみる
  35. Kubernetes Custom Controller を使ってみよう cert-manager

  36. Custom Controllerを使う理由 - なぜKubernetesなのか?の醍醐味 - KubernetesはCustom Controllerを使って Kubernetesの仕組みを使ってあらゆる物(イ ンフラレイヤー)を抽象化できる -

    あるカスタムリソースのObjectから Kubernetes Objectを作成する - 他のクラウドサービスのリソースを作成 することが可能 - Kubernetes Operator / Operator Patternとも 呼ばれる https://operatorhub.io/
  37. いろいろなOperator / Custom Controller - cert-manager - Kubernetes リソースとして証明書の発行や管理が出来るCustom Controller

    - Prometheus Operator - メトリクス収集に必要なPrometheusのデプロイやKubernetes リソースと監視の紐付けが出来るOperator - Grafana Operator - Grafanaのデプロイが簡単にできるOperator - Config Connector (Google Kubernetes Engine) - Kubernetes リソースとしてGoogle Cloudのリソースを管理出来るOperator
  38. TLS証明書と自己署名TLS証明書の比較

  39. TLS証明書の発行はめんどくさい - httpsにしようというのはもはや当たり前 - なぜ当たり前になったのか? - 10年ぐらい前まで - 認証局から証明書を購入する -

    実在確認をした上でCSRを発行し、それを認証局が使って証明書を発行する - 数年前から - 常時SSL(TLS)化というワードが流行り、HTTPは標準はTLS化していこうという波 - Let’s Encryptなどの無料の認証局の台頭 - ACMEというプロトコルを使ってドメインの実在性を確認してそれに対して証明書を発行するように - クラウド事業者が発行する証明書も使えるようになった - HTTP/2ではTLSがほぼ必須に、HTTP/3、QUICではTLSを使うように - ACMEプロトコルはめんどくさい - DNS-01 チャレンジと呼ばれる手順をしないといけない - 定期的な更新も必要 - cert-managerが代わりにやってくれる
  40. 自己署名TLS証明書の発行もめんどくさい - 通信の暗号化において、TLS証明書が信用されている必要はない - その証明書を自分が信頼すればよい - 通称自己署名TLS証明書、オレオレ証明書 - Certificate Authorityを自作する必要がある

    - 作るのがまずめんどくさい - 証明書の管理もめんどくさい - cert-managerが代わりにやってくれる - 今回はこちらの自己署名TLS証明書を作って、実際に先ほど作ったIngressに設定してみる
  41. cert-managerによる証明書管理

  42. 実際にcert-managerをデプロイ してみよう

  43. $ kubectl apply -f https://github.com/cert-manager/cert-manag er/releases/download/v1.8.0/cert-manager.y aml

  44. $ cd ./cert-manager $ kubectl apply -f clusterissuer.yaml $ kubectl

    apply -f issuer.yaml $ kubectl apply -f certificate.yaml $ kubectl apply -f ingress.yaml
  45. Ingressに証明書を設定してみよう metadata: name: ingress namespace: my-namespace + annotations: + cert-manager.io/common-name:

    "ingress.example.com" + cert-manager.io/issuer: "my-ca-issuer" spec: + tls: + - hosts: + - <IPアドレス> + secretName: ingress rules: - http: paths:
  46. TLSが設定されていることを確認しよう $ curl -vvvv -k https://34.149.46.29/ … * TLSv1.2 (OUT),

    TLS handshake, Client hello (1): * TLSv1.2 (IN), TLS handshake, Server hello (2): * TLSv1.2 (IN), TLS handshake, Certificate (11): * TLSv1.2 (IN), TLS handshake, Server key exchange (12): * TLSv1.2 (IN), TLS handshake, Server finished (14): * TLSv1.2 (OUT), TLS handshake, Client key exchange (16): * TLSv1.2 (OUT), TLS change cipher, Change cipher spec (1): * TLSv1.2 (OUT), TLS handshake, Finished (20): * TLSv1.2 (IN), TLS change cipher, Change cipher spec (1): * TLSv1.2 (IN), TLS handshake, Finished (20): * SSL connection using TLSv1.2 / ECDHE-RSA-CHACHA20-POLY1305 * ALPN, server accepted to use h2 * Server certificate: * subject: CN=ingress.example.com * start date: Apr 17 13:02:17 2022 GMT * expire date: Jul 16 13:02:17 2022 GMT * issuer: CN=my-selfsigned-ca * SSL certificate verify result: unable to get local issuer certificate (20), continuing anyway. * Using HTTP2, server supports multi-use * Connection state changed (HTTP/2 confirmed) * Copying HTTP/2 data in stream buffer to connection buffer after upgrade: len=0 * Using Stream ID: 1 (easy handle 0x135809200)
  47. クラスタの様子を見てみよう

  48. metrics-server - KubernetesのPodやNodeのメトリクスを収集できるAPIサーバー - https://github.com/kubernetes-sigs/metrics-server - kube-apiserverには搭載されていないので自前で導入する必要がある - Google Kubernetes

    Engineでは標準でインストールされている - Cloud Operation(Monitoringなど)との連携もオプションで可能 - オンプレなどではこれをPrometheusなどで取得してGrafanaで見る、みたいなことをする - kubectl topなどを叩くとmetrics-serverからの情報を得られる
  49. 実際にPodのCPU利用率、メモリ使用率を見てみよう $ kubectl top pod –all-namespaces

  50. kubectl applyの仕組み

  51. kubectl apply の近況 2022 - kubectl applyはあっても無くても「良い感じ」に反映してくれる - https://qiita.com/tkusumi/items/0bf5417c865ef716b221 -

    https://www.slideshare.net/pfi/metadatamanagedfields-kubernetes-meetup-tokyo-48-25126964 7 - 過去のマニフェストと現在のマニフェストを比較してパッチを作成し適用している - このマージを「Strategic Merge Patch」という - 他のコントローラーからの変更の影響を受けない - kubectlが良い感じにやってくれる、つまりクライアントサイドで差分を計算していた - dry-runを行う際のAdmission Webhookが実行しづらい - サーバーに依存する状況を検証しづらい - サーバー側で検証し、変更を適用するServer-side applyが導入されはじめている