selmertsxの素振り日記

ひたすら日々の素振り内容を書き続けるだけの日記

Minikube Tutorial をまるっとやる

最初に

このドキュメントは、このチュートリアルをまるっとやったことの記録。 kubernetes.io

まとめ

  • minikubeはlocalのimageを簡単に参照可能である
  • minikubeが具体的にどこからどこまで担保してくれてるのかよく分かってない。
  • kubectl はcontextを切り替えることで、gkeかminikubeかを選択して操作する
    • kubectl config use-context コマンド
  • kubernetesを使うために、わざわざyamlを使う必要は無かった

minikube

このチュートリアルのゴールは簡単なnode.jsのアプリケーションがkubenetesで動くところまで。 このチュートリアルは、machine上で開発したコードを、Docker imageに落とし込み、Minikube上で動かしていくよ。

Objecitves

  • hello world する簡単なnode.jsアプリを動かす
  • そのアプリケーションを minikubeに乗っける
  • applicationのlogを見る
  • applicationのimageをupdateする

Create a Minikube cluster

このチュートリアルでは、minikubeをlocal clusterで動かしてく。ここでは Docker for Macを使ってると仮定する。

brew cask install minikube
brew install kubernetes-cli

もしkubectlコマンドを、すでにgcloudからinstallしてたら、下記の手順を踏むこと。

gcloud components install kubectl
curl -LO https://storage.googleapis.com/minikube/releases/latest/docker-machine-driver-hyperkit \
&& chmod +x docker-machine-driver-hyperkit \
&& sudo mv docker-machine-driver-hyperkit /usr/local/bin/ \
&& sudo chown root:wheel /usr/local/bin/docker-machine-driver-hyperkit \
&& sudo chmod u+s /usr/local/bin/docker-machine-driver-hyperkit

下記URLを実行して、プロセスなしでアクセス可能なのか確認する

curl --proxy "" https://cloud.google.com/container-registry/

もし proxyが必要なければ、minikube start --vm-driver=hyperkit を実行すること。 --vm-driver=hyperkitはDocker for Macを使っているというフラグ。デフォルトはVirtualBox

https://github.com/kubernetes/minikube/blob/master/docs/drivers.md#hyperkit-driver

➜ minikube start --vm-driver=hyperkit
Starting local Kubernetes v1.10.0 cluster...
Starting VM...
Getting VM IP address...
Moving files into cluster...
Downloading kubelet v1.10.0
Downloading kubeadm v1.10.0
Finished Downloading kubeadm v1.10.0
Finished Downloading kubelet v1.10.0

minikube switch

kubectl config use-context minikube

➜ kubectl config get-contexts
CURRENT   NAME                                             CLUSTER                                          AUTHINFO                                         NAMESPACE
          xxx_pomodoro   xxx_pomodoro   xxx_pomodoro pomodoro
*         minikube                                         minikube                                         minikube

minikube dashboard

minikube dashboard

で色々見れる。便利。

f:id:selmertsx:20180720185617p:plain

Create your Node.js application

var http = require('http');
var handleRequest = function(request, response) {
  console.log('Received request for URL: ' + request.url);
  response.writeHead(200);
  response.end('Hello World!');
};
var www = http.createServer(handleRequest);
www.listen(8080);

こんなコードを用意した。

➜  k8s git:(master) node server.js
➜  k8s git:(master) curl localhost:8080
Hello World!%

で動くことを確認。

Create a Docker container image

FROM node:8.11.3
EXPOSE 8080
COPY server.js .
CMD node server.js

node imageはLTSの8.11.3を選択。 このチュートリアルでは、docker image をregistryにpushする代わりにminikubeを利用するので、 Docker hostと同じ場所でimageをbuildする必要がある。

そのため、下記のコマンドを実行する

eval $(minikube docker-env)

その後、docker imageをbuild.

docker build -t hello-node:v1 .

これでminikubeはimageをbuild出来るようになる。

Create a Deployment

kubenets podは、何か1つの目的に合わせてまとめられた、1つ、または複数のコンテナのグループである。 このチュートリアルにおいてPodは一つのコンテナでのみ出来ている。 KubeのDeploymentはPodの健康状態をcheckし、Pod Containerが死んだらrestartする。 Deploymentは、podを作ったりスケールする上で推奨される方法である。

kubectl run commandを使って、podを管理するためのDeploymentを作る。 Podは hello-node:v1 Docker imageを元にしたContainerを実行する。 local imageの利用を優先するために、--image-pull-policyフラグをNeverにセットする。

➜  k8s git:(master) ✗ kubectl run hello-node --image=hello-node:v1 --port=8080 --image-pull-policy=Never
deployment.apps/hello-node created
➜  k8s git:(master) ✗ kubectl get deployments
NAME         DESIRED   CURRENT   UP-TO-DATE   AVAILABLE   AGE
hello-node   1         1         1            1           18s
➜  k8s git:(master) ✗ kubectl get pods
NAME                          READY     STATUS    RESTARTS   AGE
hello-node-57c6b66f9c-7d26q   1/1       Running   0          31s

何か気になることがあったらkubectlコマンドを実行するとよいよ。 https://kubernetes.io/docs/reference/kubectl/overview/

Create a Service

デフォルトでは、PodはKubenetesクラスタ内の内部IP addressからしかアクセスできません。 K8s Virtual networkの外から、hello-node Containerにアクセス可能にするためには、PodsをServiceとして公開しなければならない。 開発環境においてはkubectl exposeコマンドでそれができる。

➜  k8s git:(master) ✗ kubectl expose deployment hello-node --type=LoadBalancer
service/hello-node exposed
➜  k8s git:(master) ✗ kubectl get services
NAME         TYPE           CLUSTER-IP      EXTERNAL-IP   PORT(S)          AGE
hello-node   LoadBalancer   10.107.74.133   <pending>     8080:32311/TCP   6s
kubernetes   ClusterIP      10.96.0.1       <none>        443/TCP          45m

--type=LoadBalancerflagはサービスをclusterの外に公開することを示す。 LoadBalancerをサポートしているcloud providersであれば、Serviceにアクセスするためのexternal IP addressが用意される。

Minikubeでは、LoadBalancerタイプのサービスには、minikube service ${service_name} コマンドでアクセスすることが出来る。 このコマンドでブラウザが開かれて、サービスがアクセス可能になる。

podsの情報やlogの内容に関しては下記のコマンドで獲得可能である。

➜  k8s git:(master) ✗ kubectl describe pods
Name:           hello-node-57c6b66f9c-7d26q
Namespace:      default
Node:           minikube/192.168.64.2
Start Time:     Fri, 20 Jul 2018 16:54:31 +0900
Labels:         pod-template-hash=1372622957
                run=hello-node
Annotations:    <none>
Status:         Running
IP:             172.17.0.4
Controlled By:  ReplicaSet/hello-node-57c6b66f9c
Containers:
  hello-node:
    Container ID:   docker://5333602c10e2b6ef2677125996cf7ccd51db23946a7b085b85354fc0c30516f8
    Image:          hello-node:v1
    Image ID:       docker://sha256:80bf931ffb07668a2ef31dd3e5c08350ed5d64477ba424a847bb29b5b1eef0a7
    Port:           8080/TCP
    Host Port:      0/TCP
    State:          Running
      Started:      Fri, 20 Jul 2018 16:54:32 +0900
    Ready:          True
    Restart Count:  0
    Environment:    <none>
    Mounts:
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-shf7x (ro)
Conditions:
  Type           Status
  Initialized    True
  Ready          True
  PodScheduled   True
Volumes:
  default-token-shf7x:
    Type:        Secret (a volume populated by a Secret)
    SecretName:  default-token-shf7x
    Optional:    false
QoS Class:       BestEffort
Node-Selectors:  <none>
Tolerations:     node.kubernetes.io/not-ready:NoExecute for 300s
                 node.kubernetes.io/unreachable:NoExecute for 300s
Events:
  Type    Reason                 Age   From               Message
  ----    ------                 ----  ----               -------
  Normal  Scheduled              14m   default-scheduler  Successfully assigned hello-node-57c6b66f9c-7d26q to minikube
  Normal  SuccessfulMountVolume  14m   kubelet, minikube  MountVolume.SetUp succeeded for volume "default-token-shf7x"
  Normal  Pulled                 14m   kubelet, minikube  Container image "hello-node:v1" already present on machine
  Normal  Created                14m   kubelet, minikube  Created container
  Normal  Started                14m   kubelet, minikube  Started container
➜  k8s git:(master) ✗ kubectl logs hello-node-57c6b66f9c-7d26q
Received request for URL: /
Received request for URL: /favicon.ico

Clean up

➜ kubectl delete service hello-node
service "hello-node" deleted

➜ kubectl delete deployment hello-node
deployment.extensions "hello-node" deleted

➜ docker rmi hello-node:v1 hello-node:v2 -f
Untagged: hello-node:v1
Deleted: sha256:80bf931ffb07668a2ef31dd3e5c08350ed5d64477ba424a847bb29b5b1eef0a7
Deleted: sha256:05f6355afc692766f99575564dd9d8e32917779c91285e8ddbadd615eb528bab
Deleted: sha256:137c95a151503aaa351d3430fa2ca089e28487516a7cbe61af318b2717cce6af
Deleted: sha256:1725ca28b86411d20d508a8275129fe68e68e4a6d32fd5a0c7d453a0de544f07
Error: No such image: hello-node:v2
➜ minikube stop
eval $(minikube docker-env -u)
Stopping local Kubernetes cluster...
Machine stopped.