0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

はじめてのk3s

0
Last updated at Posted at 2026-09-21

EC2 を1台だけ立てて、そこに Kubernetes1 を入れ、自分で作った gRPC サーバーのコンテナを動かし、手元の Mac から呼ぶところまでやりました。使ったのは EKS ではなく k3s です。はじめてのgRPC と はじめてのTerraform の続きになります。

1. この記事でやること

Docker は使っているけれど Kubernetes はまだ、という状態から始めます。docker run は打てる、Dockerfile も書いたことがある。でも Pod や Deployment という言葉は聞いたことがある程度。私がまさにその状態でした。

最後にこうなります。

$ GRPC_HOST=203.0.113.45 GRPC_PORT=30051 venv/bin/python3 client.py
こんにちは、三橋 さん

$ kubectl delete pod grpc-hello-5648f8f79f-6d2pf
pod "grpc-hello-5648f8f79f-6d2pf" deleted

$ GRPC_HOST=203.0.113.45 GRPC_PORT=30051 venv/bin/python3 client.py
こんにちは、三橋 さん

真ん中で Pod を消しています。それなのに3回目がそのまま返ってきます。消した Pod は戻ってきません。代わりに新しい Pod が立っていて、そちらが返事をしています。 この記事はその一連を自分の手で作って、落ちていた時間が何秒だったかまで測るところまでです。

出てくる言葉は3つです。Pod はコンテナが入る箱、Deployment は「その箱を常に n 個動かしておく」というルール、Service は箱が入れ替わっても変わらない受付窓口。この3つだけ頭に入れておけば読めます。中身は3章で書きます。

図にするとこうなります。

作業は1日で終わります。AWS に課金が発生するのは EC2 を立てている間だけで、私の場合は9分弱でした。金額は11章にまとめてあります。

2. なぜ EKS ではなく k3s なのか

AWS で Kubernetes といえば EKS です。ただ EKS は、Pod を1つも動かしていなくてもクラスタが存在するだけで1時間 0.10ドルかかります。1か月立てっぱなしにすると管理料だけで約70ドル、そこに EC2 の代金が乗ります。「勉強のために1日触りたい」という用途には重すぎます。

k3s は Rancher が作っている Kubernetes です。Kubernetes そのものを1つの実行ファイルにまとめてあり、curl 1行で入ります。 管理料という考え方がないので、かかるのは EC2 の代金だけです。

機能を削った別物ではありません。kubectl はそのまま使えますし、Pod も Deployment も Service も同じ名前で同じように動きます。私が今回打ったコマンドは、EKS に対してもそのまま通るものばかりです。

EKS k3s
管理料 1クラスタ 1時間 0.10ドル なし
入れ方 AWS のコンソールか eksctl EC2 の中で curl 1行
kubectl 使える 同じものが使える
向いている場面 本番で複数台をまとめて運用する 1台で仕組みを覚える・小さく動かす

覚えたい相手が「Kubernetes の仕組み」なら、k3s で足ります。

3. 書いたファイルは3つ

gRPC サーバーのコードは前回のものをそのまま使いました。Kubernetes のために新しく書いたのは3つだけです。

置き場所を先に決めておきます。どれも手元の Mac で書きます。 EC2 へ送るのは Dockerfile とサーバー側のコードだけで、YAML の2つは手元に置いたまま kubectl から渡します。

ファイル 書く場所 どこで使うか
Dockerfile 手元の Mac EC2 へ scp して、EC2 の中で docker build
server.py・hello_pb2.py・hello_pb2_grpc.py 前回のもの 同上(イメージの中に入る)
deployment.yaml 手元の Mac 手元から kubectl apply で渡す
service.yaml 手元の Mac 同上
client.py 手元の Mac 手元で実行する

3-1. Dockerfile — サーバーをイメージにする

FROM python:3.14-slim

WORKDIR /app

RUN pip install --no-cache-dir grpcio protobuf

COPY hello_pb2.py hello_pb2_grpc.py server.py ./

EXPOSE 50051

CMD ["python3", "server.py"]

中身は4つです。土台の OS、入れるもの、詰めるファイル、起動コマンド。Docker を触ったことがあれば読めるはずで、Kubernetes 固有のものは何も入っていません。

protobuf を明示的に書いているのには理由があります。grpcio だけ入れると、生成コードの hello_pb2.py が読む google.protobuf が見つからずに止まります。前回これで詰まりました。

client.py と hello.proto はイメージに入れていません。サーバー側では使わないからです。

3-2. deployment.yaml — 「常に1つ動かす」というルール

apiVersion: apps/v1
kind: Deployment
metadata:
  name: grpc-hello
spec:
  replicas: 1
  selector:
    matchLabels:
      app: grpc-hello
  template:
    metadata:
      labels:
        app: grpc-hello
    spec:
      containers:
        - name: grpc-hello
          image: grpc-hello:v1
          imagePullPolicy: Never
          ports:
            - containerPort: 50051

Kubernetes の YAML はどれもこの4つで始まります。apiVersion(この書式の版)、kind(何を作るか)、metadata(名前)、spec(中身)。次の service.yaml も同じ形です。

spec の中に template があって、その下にまた metadata と spec が出てきます。下の段は Pod 1個ぶんの設計図です。 上が Deployment の設定、下が「そこから作る Pod はこういうもの」という入れ子になっています。

ここが Docker との一番の違いでした。Pod2 を直接書くこともできますが、そうすると消したときに復活しません。 Deployment3 は「この Pod を常に replicas 個保つ」という係です。9章で Pod を消したときに新しいものが立つのは、この1行があるからです。

2つ注意した点があります。

imagePullPolicy: Never。 これが無いと、k3s は grpc-hello:v1 を Docker Hub へ取りに行って ErrImagePull で止まります。7章で自分の手で読み込ませたイメージを使わせるための指定です。

タグを :v1 にした。 imagePullPolicy を書かなかった場合、タグが :latest だと既定が Always(毎回取りに行く)になります。今回は Never を明示しているので既定は効きませんが、書き忘れたときに取りに行かれないよう、タグの側でも避けておきました。

もう1つ、selector.matchLabels と template.metadata.labels は必ず同じにします。ここが食い違うと Deployment が自分で立てた Pod を見失います。

3-3. service.yaml — 番号が3つ出てきて、ここが一番まぎらわしい

apiVersion: v1
kind: Service
metadata:
  name: grpc-hello
spec:
  type: NodePort
  selector:
    app: grpc-hello
  ports:
    - port: 50051
      targetPort: 50051
      nodePort: 30051
      protocol: TCP

Service4 は受付窓口です。Pod は立て直すたびに IP が変わりますが、Service の側は変わりません。手元の client.py が同じ番号で呼び続けられるのはこれのおかげです。

どの Pod へ流すかは selector で決めます。deployment.yaml で Pod に付けた app: grpc-hello と同じ文字列を書いています。 Service は特定の Pod を IP で覚えているのではなく、この札が付いた Pod をその都度探します。だから Pod が入れ替わっても届きます。

番号が3つ出てきます。最初に読んだとき、どれがどれだか分かりませんでした。

書いた場所 意味
nodePort: 30051 EC2 の外(手元の Mac)から呼ぶ番号
port: 50051 k3s の中から grpc-hello:50051 で呼ぶ番号
targetPort: 50051 Pod の中で server.py が待っている番号

nodePort は 30000〜32767 の範囲しか使えません。 gRPC でよく使う 50051 をそのまま外に出すことができないので、前回まで 50051 直書きだった client.py に手を入れました。

host = os.environ.get("GRPC_HOST", "localhost")
# ポートも環境変数で受ける(k3s の Service は 30000〜32767 しか外に出せない)
port = os.environ.get("GRPC_PORT", "50051")
with grpc.insecure_channel(f"{host}:{port}") as channel:

既定値を 50051 のままにしたので、GRPC_PORT を付けなければ前回と同じ動きのままです。

4. Terraform に足したのは通行許可証2つ

EC2 は前回の Terraform をそのまま使いました。足したのはセキュリティグループ52つだけです。

resource "aws_security_group" "k3s_api" {
  name        = "aws-study-tf-k3s-api-sg"
  description = "k3s api from my home only"

  ingress {
    description = "k3s api"
    from_port   = 6443
    to_port     = 6443
    protocol    = "tcp"
    cidr_blocks = [var.my_ip]
  }

  egress {
    description = "all outbound"
    from_port   = 0
    to_port     = 0
    protocol    = "-1"
    cidr_blocks = ["0.0.0.0/0"]
  }
}

6443 番は、手元の kubectl が EC2 の Kubernetes につなぐ口です。もう1つ同じ形で 30051 番(nodePort のほう)を開けます。どちらも cidr_blocks = [var.my_ip] で自宅の IP からだけに絞っています。

EC2 への付け方はこうです。

vpc_security_group_ids = [
  aws_security_group.study.id,
  aws_security_group.k3s_api.id,
  aws_security_group.k3s_nodeport.id,
]

ここで前回まで付けていた 50051 番と 8080 番を外しました。今回は Service 経由でしか呼ばないので、直接叩く口は要りません。使わない口は開けたままにしない、を守った形です。

terraform plan を打つと、自宅の IP も番号も伏せられて出ます。

+ ingress = (sensitive value)

variables.tf で my_ip に sensitive = true を付けているためです。IP が画面に出ないのは安心ですが、裏返しに「どの番号を開けるつもりか」も plan では確かめられません。そこは main.tf を目で見ることになります。

5. 手元に kubectl を入れて、EC2 を立てる

先に手元の Mac へ kubectl6 を入れます。Kubernetes に指示を出すコマンドで、この先ずっと使います。

入門記事の多くは brew install kubernetes-cli と書いていますが、Intel の Mac ではこれが通りませんでした(理由は12章)。公式のバイナリを直接落とします。

curl -LO https://dl.k8s.io/release/v1.37.0/bin/darwin/amd64/kubectl
curl -LO https://dl.k8s.io/release/v1.37.0/bin/darwin/amd64/kubectl.sha256
echo "$(cat kubectl.sha256)  kubectl" | shasum -a 256 --check
chmod +x kubectl && mv kubectl /usr/local/bin/

60MB で1分でした。Apple Silicon の Mac なら URL の amd64 を arm64 に変えます。

kubectl version --client
Client Version: v1.37.0
Kustomize Version: v5.8.1

ここから課金が始まります。EC2 だけを立てたいので -target で絞ります。

terraform apply -target=aws_instance.study

絞らないと、同じ main.tf に書いてある RDS まで立ちます。

Apply complete! Resources: 7 added, 0 changed, 0 destroyed.

この EC2 は Docker が入った状態で立ち上がります。Terraform の user_data に書いてあるためで、7章で docker build を打つのに要ります。

user_data = <<-EOF
  #!/bin/bash
  dnf install -y docker
  systemctl start docker
  systemctl enable docker
  usermod -aG docker ec2-user
EOF

ssh で入って、k3s を入れます。この1行だけです。

curl -sfL https://get.k3s.io | sudo sh -

公式の案内には | sh - と書いてありますが、Amazon Linux の ec2-user では権限が足りません。sudo を挟みます。

終わると、kubectl が使える状態になっています。

sudo k3s kubectl get nodes
NAME               STATUS   ROLES                  AGE   VERSION
ip-172-31-7-1      Ready    control-plane,master   35s   v1.36.4+k3s1

1台だけの Kubernetes が立ちました。EC2 側に kubectl を別途入れる必要はありません。 k3s の実行ファイルが kubectl も内蔵していて、/usr/local/bin/kubectl がそこへのシンボリックリンクとして作られます。

ログにこんな行が出ます。

Skipping /usr/local/bin/ctr symlink to k3s, command exists in PATH at /usr/bin/ctr

ctr だけはリンクが作られません。Docker が持っている ctr が先にいるためです。これが7章で sudo k3s ctr とフルで打つ理由になります。

6. 手元の kubectl からつなぐ — ここで1回止まりました

毎回 ssh で入るのは面倒なので、手元の Mac から操作できるようにします。つなぎ方の情報は EC2 の /etc/rancher/k3s/k3s.yaml にあります。

このファイルは root しか読めないので、EC2 の中でいったん読める場所へ寄せます。

sudo cp /etc/rancher/k3s/k3s.yaml /tmp/k3s.yaml
sudo chown ec2-user:ec2-user /tmp/k3s.yaml

あとはこれを手元へ持ってきて、server: の 127.0.0.1 を EC2 の IP に書き換えるだけ、のはずでした。

tls: failed to verify certificate: x509: certificate is valid for
10.43.0.1, 127.0.0.1, 172.31.7.1, ::1, not 203.0.113.45

k3s が作った証明書に、EC2 のパブリック IP が入っていません。 入っているのはクラスタ内部の IP と 127.0.0.1 だけです。EC2 の中から使う分には困らないので、既定ではそうなっています。

直し方は、証明書に載せる名前を設定に書いて、作り直させることです。

sudo tee /etc/rancher/k3s/config.yaml <<'EOF'
tls-san:
  - 203.0.113.45
EOF

sudo rm -f /var/lib/rancher/k3s/server/tls/serving-kube-apiserver.crt \
           /var/lib/rancher/k3s/server/tls/serving-kube-apiserver.key

sudo systemctl restart k3s

消した2つは再起動時に作り直されます。87秒で Ready に戻りました。

あらためて k3s.yaml を手元へ持ってきます。

scp -i ~/.ssh/<鍵> ec2-user@203.0.113.45:/tmp/k3s.yaml ~/.kube/config-s8
sed -i '' "s|127.0.0.1|203.0.113.45|" ~/.kube/config-s8

この18行のファイルには、証明書と鍵が3件入っています(certificate-authority-data・client-certificate-data・client-key-data)。作業フォルダに置いて .gitignore する手もありますが、私は ~/.kube/ に置きました。git の外に出してしまえば、うっかり commit する心配そのものが無くなります。

このファイルを使うよう kubectl に教えます。この先の kubectl は全部この設定で打つので、ターミナルを開き直したらもう一度打ちます。

export KUBECONFIG=~/.kube/config-s8
kubectl get nodes
NAME            STATUS   ROLES                  AGE   VERSION
ip-172-31-7-1   Ready    control-plane,master   4m    v1.36.4+k3s1

手元から EC2 の Kubernetes が見えました。ここから先は ssh に戻らなくて済みます。

なお手元の kubectl は v1.37.0、EC2 の k3s は v1.36.4 です。1つ違いですが問題なく動きました。

7. イメージを EC2 で組み立てて、k3s に渡す

コードと Dockerfile を EC2 へ送って、そこで組み立てます。

ssh -i ~/.ssh/<鍵> ec2-user@203.0.113.45 "mkdir -p ~/build"
scp -i ~/.ssh/<鍵> Dockerfile server.py hello_pb2.py hello_pb2_grpc.py ec2-user@203.0.113.45:~/build/

ホーム直下ではなく ~/build/ に置きます。ビルドの対象がそのフォルダごと送られるので、関係ないファイルを巻き込まないためです。

cd ~/build && docker build -t grpc-hello:v1 .

6.9秒で終わりました。ここまでは普通の Docker です。

ここからが Kubernetes 特有のところです。 docker build しただけでは、Pod からこのイメージが見えません。

k3s は Docker ではなく containerd7 で動いています。 Docker が持っているイメージの置き場と、k3s が見る置き場は別物です。同じ EC2 の中にあっても、そのままでは渡りません。

この状態のまま次の章へ進むと、Pod は立ち上がらずに ErrImageNeverPull で止まります。imagePullPolicy: Never を書いているので、Docker Hub へ取りに行くこともしません。

渡すには、いったんファイルに書き出して、k3s 側に読み込ませます。

docker save grpc-hello:v1 -o /tmp/grpc-hello.tar
sudo k3s ctr images import /tmp/grpc-hello.tar

149MB の tar ができて、読み込みは1.9秒でした。ctr ではなく k3s ctr とフルで打つのは、5章で見たとおり素の ctr が Docker 側を向いているためです。

k3s には docker.io/library/grpc-hello:v1 という名前で入ります。deployment.yaml に書いた grpc-hello:v1 はこの形に補われて、ちゃんと一致します。

この方法だと、Docker Hub にも ECR にも1バイトも送っていません。 レジストリを用意しなくても Kubernetes は動かせる、というのが個人的には一番の収穫でした。

8. Pod を立てて、手元から呼ぶ

手元の Mac から2つの YAML を渡します。

kubectl apply -f deployment.yaml -f service.yaml
deployment.apps/grpc-hello created
service/grpc-hello created
kubectl get pods -o wide
NAME                          READY   STATUS    RESTARTS   AGE   IP
grpc-hello-5648f8f79f-6d2pf   1/1     Running   0          1s    10.42.0.9

0.66秒で Running になりました。イメージが既に EC2 の中にあるので、取得の待ち時間がありません。

kubectl get svc
NAME         TYPE       CLUSTER-IP      PORT(S)           AGE
grpc-hello   NodePort   10.43.95.205    50051:30051/TCP   3s

ここで IP が3つ出てきます。EC2 のパブリック IP、Service の 10.43.95.205、Pod の 10.42.0.9。全部別物です。手元から呼ぶときに使うのは1つ目だけで、残り2つは k3s の中の住所です。

呼びます。

GRPC_HOST=203.0.113.45 GRPC_PORT=30051 venv/bin/python3 client.py
こんにちは、三橋 さん

0.44秒。使った client.py は前回のものと同じで、変えたのはポートを環境変数で受ける3行だけです。 呼ぶ側から見ると、相手が Pod になったことは分かりません。

9. Pod を消すと、何秒落ちるのか

ここが今回いちばんやりたかったところです。「Kubernetes は落ちても勝手に上がる」と説明されますが、上がるまでの間はどうなっているのかが気になっていました。

消した直後から呼び続けて測ります。40行です。

import os, subprocess, time
import grpc, hello_pb2, hello_pb2_grpc

IP = os.environ["IP"]
POD = os.environ["POD"]
target = f"{IP}:30051"

def call():
    try:
        with grpc.insecure_channel(target) as ch:
            stub = hello_pb2_grpc.GreeterStub(ch)
            stub.SayHello(hello_pb2.HelloRequest(name="三橋"), timeout=1.5)
        return True
    except Exception:
        return False

print(f"削除前に1回呼ぶ: {'通った' if call() else '通らない'}")
t0 = time.monotonic()
subprocess.run(["kubectl", "delete", "pod", POD, "--wait=false"], check=True, capture_output=True)
print(f"kubectl delete を打った({time.monotonic() - t0:.2f}秒)")

first_fail = recovered = None
while time.monotonic() - t0 < 180:
    ok = call()
    t = time.monotonic() - t0
    if not ok and first_fail is None:
        first_fail = t
        print(f"つながらなくなった: {t:.2f}秒後")
    if first_fail is not None and ok:
        recovered = t
        print(f"また通った: {t:.2f}秒後")
        break

if first_fail is not None and recovered is not None:
    print(f"落ちていた時間: {recovered - first_fail:.2f}秒")
elif first_fail is None:
    print("一度もつながらない瞬間が無かった")
else:
    print("180秒たっても戻らなかった")

打ち方はこうです。Pod の名前は kubectl get pods で出たものを渡します。

IP=203.0.113.45 POD=grpc-hello-5648f8f79f-6d2pf venv/bin/python3 measure_restart.py

結果です。

削除前に1回呼ぶ: 通った
kubectl delete を打った(0.21秒)
つながらなくなった: 1.32秒後
また通った: 1.51秒後
落ちていた時間: 0.19秒

0.19秒でした。 一瞬ではあるものの、確かに落ちています。「勝手に上がる」は「止まらない」ではない、というのが数字で見えました。

新しく立った Pod を見ます。

kubectl get pods -o wide
NAME                          READY   STATUS    RESTARTS   AGE   IP
grpc-hello-5648f8f79f-q824w   1/1     Running   0          12s   10.42.0.10

名前も IP も変わっています(6d2pf → q824w、10.42.0.9 → 10.42.0.10)。それでも client.py は 203.0.113.45:30051 のままで届きました。 Service が受付をしている、というのはこういうことでした。

何が起きたかは記録に残っています。

kubectl get events --sort-by=.lastTimestamp
Killing            Stopping container grpc-hello
SuccessfulCreate   Created pod: grpc-hello-5648f8f79f-q824w
Pulled             Container image "grpc-hello:v1" already present on machine
Created            Created container: grpc-hello
Started            Started container grpc-hello

Pulled という行名が出ますが、中身は already present on machine(もう手元にある)です。取りに行っていません。 imagePullPolicy: Never を書いていても記録の行名は Pulled のままなので、最初に見たときは取りに行ったのかと思いました。7章で読み込ませたものがそのまま使われています。

1つ気づいたことがあります。消した Pod は即座には消えません。

NAME                          READY   STATUS        RESTARTS   AGE
grpc-hello-5648f8f79f-6d2pf   1/1     Terminating   0          3m
grpc-hello-5648f8f79f-q824w   1/1     Running       0          30s

古いほうが30秒ほど Terminating のまま残りました。Kubernetes は終了の合図(SIGTERM)を送ってから既定で30秒待ちます。私の server.py は wait_for_termination() で待っているだけで、その合図を受け取って自分から終わる作りになっていません。だから猶予の30秒をまるまる使い切ってから止められます。

新しい Pod は先に立ち上がっているので、外から見ると 0.19秒で復旧しています。とはいえ、止まるほうと立つほうは別々に進むというのは、表の数字だけ見ていると気づけませんでした。

10. 消す

EC2 が要るのはここまでです。

terraform destroy
Destroy complete! Resources: 7 destroyed.

消えたことは自分の目で確かめます。

aws ec2 describe-instances \
  --filters "Name=instance-state-name,Values=running,stopped" \
  --query 'Reservations[].Instances[].[InstanceId,State.Name]' --output text

aws ec2 describe-volumes --query 'Volumes[].[VolumeId,Size,State]' --output text

どちらも何も返らなければ終わりです。EC2 は「停止」だけだとディスク代が止まりません(30GB で1日約14円)。destroy まで通します。

11. かかった時間とお金

本文で後回しにした数字をここに並べます。

時間

何に 実測
terraform apply(EC2 と周辺あわせて7個) 34秒
k3s のインストール 30.9秒
証明書の作り直し(6章) 87秒
docker build 6.9秒
k3s ctr images import(149MB) 1.9秒
Pod が Running になるまで 0.66秒
client.py の返事 0.44秒
kubectl delete から復旧まで 1.51秒
そのうち、つながらなかった時間 0.19秒
terraform destroy 2分3.8秒

Kubernetes を入れる作業そのものは31秒で終わります。時間を使ったのは証明書の件と、イメージの受け渡しでした。

お金

EC2 を立てていたのは 8分34秒でした。

何に 概算
m7i-flex.large 1時間 約18.5円
ディスク gp3 30GB 1日 約14円
今回の合計(8分34秒) 約2.7円

始める前は「2〜3時間で37〜55円くらい」と見込んでいたので、20分の1で済みました。手順が決まっていれば早く終わります。

EKS で同じことをすると、クラスタの管理料が1時間 0.10ドル(約15円)です。8分でも1時間ぶんから課金されるので、EC2 代と合わせて18円ほど。金額の差は小さいのですが、「クラスタを作る・消す」に十数分かかるぶん、気軽に消せなくなるのが実際のところでした。

消し忘れたとき

1か月立てっぱなしにすると、EC2 が約13,300円、ディスクが約420円です。学習用なら使うたびに作って消すほうが安くつきます。

12. つまずいたところ

つまずき 分かったこと
1 brew install kubernetes-cli が終わらない Intel Mac には組み立て済みのファイルが用意されていない。Go のコンパイラから入れてソースを組み立て始める。公式のバイナリを curl で落とせば1分
2 手元の kubectl が証明書で拒まれる k3s の証明書にはパブリック IP が入っていない。tls-san に書いて作り直す
3 Pod が ErrImagePull で止まる docker build したイメージは k3s から見えない。docker save → k3s ctr images import で渡す
4 kubectl apply --dry-run=client が使えない ファイルの形だけ確かめたくても、リソースの種類を知るのにクラスタへの接続が要る
5 消した Pod が30秒残る 終了の合図を受け取って自分から終わる作りでないと、猶予の30秒を待たされる

1つ目は Kubernetes と関係ないところです。Intel の Mac を使っていると、入門記事に書いてある brew install がそのまま通らないことがあります。前回の Terraform でも同じことがありました。

brew install kubernetes-cli を打つと、Intel Mac 向けの組み立て済みファイルが用意されていないため、Go のコンパイラ・bash・coreutils を先に入れてからソースを組み立て始めます。10分待っても終わらず、ncurses を組み立てている途中でした。5章の公式バイナリなら1分です。

ただし公式バイナリは Homebrew の管理外になるので、brew upgrade では上がりません。 版を上げるときは同じ手順で置き換えます。

3つ目が、Docker から来た人がいちばん引っかかるところだと思います。同じサーバーの中にイメージがあるのに使えないというのは、言われるまで思いつきませんでした。Kubernetes が Docker とは別のコンテナの仕組みで動いている、というのが体感できた場面です。

  1. Kubernetes。コンテナを何台ものサーバーにまたがって動かし、落ちたら立て直し、数を保つための仕組み。読み方は「クバネティス」で、k と s の間に8文字あるので k8s と略されます。 ↩

  2. Pod。Kubernetes がコンテナを動かす最小の単位。1つの Pod に複数のコンテナを入れることもできますが、今回は1つです。 ↩

  3. Deployment。「この Pod を常に n 個保つ」というルールを書いたもの。Pod が消えたら新しく立て、数が多ければ減らします。 ↩

  4. Service。Pod への入口になる受付窓口。Pod が入れ替わっても Service 側の宛先は変わりません。今回使った NodePort は、サーバーの特定の番号を外に開ける型です。 ↩

  5. セキュリティグループ。AWS の通行許可証にあたるもので、どの IP からどの番号を通すかを書きます。 ↩

  6. kubectl。Kubernetes に指示を出すコマンド。「クーベコントロール」「キューブシーティーエル」など読み方は人によって違います。 ↩

  7. containerd。コンテナを実際に動かす部分。Docker もこれを内部で使っていますが、置き場は Docker と k3s で別々に持っています。 ↩

0
0
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
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?