Tutorial Kubernetes - 1ere partie
 
                    
                    Ce tutorial illustre comment démarrer avec Kubernetes (au minimum version 1.2) en mode pas à pas. Il est basé sur l'utilisation de Google Container Engine, mais peut facilement être suivi sur un autre environnement.
Initial configuration
create new project in Cloud Console (optional)
start Cloud Shell
configure Project environment variable
$ export PROJ="xtrav42kubnormal"
create work folder
$ mkdir mykubeapp
$ cd mykubeapp
Application creation
create source file
$ vi app.go
package main
import (
    "fmt"
    "net/http"
    "os"
    "time"
)
func helloHandler(w http.ResponseWriter, r *http.Request) {
    currenttime:=time.Now().Local()
    name,err:=os.Hostname()
    if err !=nil {
        panic(err)
    }
    fmt.Printf("server: %s received request from: %s\n",name,r.RemoteAddr)
    fmt.Fprintf(w, "server: %s\n\n",name)
    fmt.Fprintf(w, "request: %s %s\n",r.Host,r.URL.Path)
    fmt.Fprintf(w, "Hello World from Go!  current local time: %s\n", currenttime.Format("20060102 15:04:05"))
    res:=dowork(30000)
    fmt.Fprintf(w, "result: %d  duration: %s\n",res,time.Since(currenttime))
}
func dowork(max int) int{
    var k int
    for i:=0; i<max; i++ {
        for j:=0; j<max; j++ {
            k=k+i*j;
        }
    }
    return k
}
func main() {
    http.HandleFunc("/", helloHandler)
    fmt.Println("serving on port 8080")
    err := http.ListenAndServe(":8080", nil)
    if err != nil {
        panic("ListenAndServe: " + err.Error())
    }
}
build application
$ go build
run application and test it from Cloud Shell with Web Preview (ctrl-c to stop the app)
$ ./mykubeapp
Docker image preparation
recompile app to be statically linked
$ CGO_ENABLED=0 go build -ldflags '-extldflags "-static"'
check the binary doesn't have any dynamic dependencies
$ ldd mykubeapp 
not a dynamic executable
create simple Dockerfile
$ vi Dockerfile
FROM alpine
RUN apk add --no-cache bash
ADD mykubeapp /mykubeapp
CMD  ["/mykubeapp"]
build Docker image
$ sudo docker build -t areg/mykubeapp:1 .
Sending build context to Docker daemon 7.596 MBStep 1 : FROM alpinelatest: Pulling from library/alpine31b45a1205be: Pull complete Digest: sha256:023c4a98e02ff523c38e830299bbe64f3a0c1cdde7dbd4ecacaf46986e264c94Status: Downloaded newer image for alpine:latest ---> 31b45a1205beStep 2 : RUN apk add --no-cache bash ---> Running in 7c510d0b6a7ffetch http://dl-cdn.alpinelinux.org/alpine/v3.4/main/x86_64/APKINDEX.tar.gzfetch http://dl-cdn.alpinelinux.org/alpine/v3.4/community/x86_64/APKINDEX.tar.gz(1/5) Installing ncurses-terminfo-base (6.0-r7)(2/5) Installing ncurses-terminfo (6.0-r7)(3/5) Installing ncurses-libs (6.0-r7)(4/5) Installing readline (6.3.008-r4)(5/5) Installing bash (4.3.42-r3)Executing bash-4.3.42-r3.post-installExecuting busybox-1.24.2-r9.triggerOK: 13 MiB in 16 packages ---> 45680305244fRemoving intermediate container 7c510d0b6a7fStep 3 : ADD mykubeapp /mykubeapp ---> 44ea11cc5564Removing intermediate container bca9116980afStep 4 : CMD /mykubeapp ---> Running in 113da1f22c2f ---> 59dacfcbd8f8Removing intermediate container 113da1f22c2fSuccessfully built 59dacfcbd8f8
check image was successfully built
$ sudo docker images
REPOSITORY          TAG                 IMAGE ID            CREATED              VIRTUAL SIZEareg/mykubeapp      1                   59dacfcbd8f8        About a minute ago   15.83 MBalpine              latest              31b45a1205be        10 weeks ago         4.799 MB
test docker image locally using Web Preview
$ sudo docker run -p 8080:8080 areg/mykubeapp:1
serving on port 8080server: 419c0565b1a0 received request from: 172.18.0.1:39734^C
 tag image to prepare it for Google Container Registry
$ sudo docker tag areg/mykubeapp:1 gcr.io/$PROJ/mykubeapp:1
check docker images
$ sudo docker images
REPOSITORY                          TAG       IMAGE ID         CREATED            VIRTUAL SIZEareg/mykubeapp                      1         59dacfcbd8f8     25 minutes ago     15.83 MBgcr.io/xtrav42kubnormal/mykubeapp   1         59dacfcbd8f8     25 minutes ago     15.83 MBalpine                              latest    31b45a1205be     10 weeks ago       4.799 MB
push image to Google Container Registry
$ gcloud docker push gcr.io/$PROJ/mykubeapp:1
The push refers to a repository [gcr.io/xtrav42kubnormal/mykubeapp] (len: 1)59dacfcbd8f8: Pushed 44ea11cc5564: Pushed 45680305244f: Pushed 31b45a1205be: Image already exists 1: digest: sha256:10b59055e6c9e0f94f6576c4904bff00f76476baa960d1693a6ccdc3bc6ce326 size: 6088
tag image to prepare it for Google Container Registry
$ sudo docker tag areg/mykubeapp:1 gcr.io/$PROJ/mykubeapp:1
check docker images
$ sudo docker images
REPOSITORY                          TAG       IMAGE ID         CREATED            VIRTUAL SIZEareg/mykubeapp                      1         59dacfcbd8f8     25 minutes ago     15.83 MBgcr.io/xtrav42kubnormal/mykubeapp   1         59dacfcbd8f8     25 minutes ago     15.83 MBalpine                              latest    31b45a1205be     10 weeks ago       4.799 MB
push image to Google Container Registry
$ gcloud docker push gcr.io/$PROJ/mykubeapp:1
The push refers to a repository [gcr.io/xtrav42kubnormal/mykubeapp] (len: 1)59dacfcbd8f8: Pushed 44ea11cc5564: Pushed 45680305244f: Pushed 31b45a1205be: Image already exists 1: digest: sha256:10b59055e6c9e0f94f6576c4904bff00f76476baa960d1693a6ccdc3bc6ce326 size: 6088
 
Cluster creation on GKE
configure zone
$ gcloud config set compute/zone us-central1-a
create cluster with 3 machines of type n1-standard-1 (may take several minutes to complete)
$ gcloud container clusters create knormal --num-nodes 3 --machine-type n1-standard-1
Creating cluster knormal...done.Created [https://container.googleapis.com/v1/projects/xtrav42kubnormal/zones/us-central1-a/clusters/knormal].kubeconfig entry generated for knormal.NAME     ZONE           MASTER_VERSION  MASTER_IP       MACHINE_TYPE   NODE_VERSION  NUM_NODES  STATUSknormal  us-central1-a  1.3.6           23.251.157.118  n1-standard-1  1.3.6         3          RUNNING
 check created nodes
$ kubectl get nodes
NAME                                     STATUS    AGEgke-knormal-default-pool-3edb1986-gh00   Ready     12mgke-knormal-default-pool-3edb1986-xljo   Ready     12mgke-knormal-default-pool-3edb1986-y90h   Ready     12m
get credentials
$ gcloud container clusters get-credentials knormal
check created nodes
$ kubectl get nodes
NAME                                     STATUS    AGEgke-knormal-default-pool-3edb1986-gh00   Ready     12mgke-knormal-default-pool-3edb1986-xljo   Ready     12mgke-knormal-default-pool-3edb1986-y90h   Ready     12m
get credentials
$ gcloud container clusters get-credentials knormal
Application deployment as pods
create a simple 1 pod deployment with default settings
$ kubectl run mydeploy --image=gcr.io/$PROJ/mykubeapp:1 --port=8080
check created deployment
$ kubectl get deployment
NAME       DESIRED   CURRENT   UP-TO-DATE   AVAILABLE   AGEmydeploy   1         1         1            1           10s
check created pods
$ kubectl get pods -o wide
NAME                        READY  STATUS    RESTARTS   AGE  IP         NODEmydeploy-2057093778-ns1mu   1/1    Running   0          6m   10.0.2.3   gke-knormal-default-pool-3edb1986-y90h
check pod logs
$ kubectl logs mydeploy-2057093778-ns1mu
serving on port 8080
create service to allow external traffic
$ kubectl expose deployment mydeploy --type="LoadBalancer"
service "mydeploy" exposed
check created service (external ip may take a while to show up)
$ kubectl get services
NAME         CLUSTER-IP     EXTERNAL-IP   PORT(S)    AGEkubernetes   10.3.240.1     <none>        443/TCP    43mmydeploy     10.3.249.220   <pending>     8080/TCP   22s$ kubectl get services
NAME         CLUSTER-IP     EXTERNAL-IP      PORT(S)    AGEkubernetes   10.3.240.1     <none>           443/TCP    43mmydeploy     10.3.249.220   104.154.32.162   8080/TCP   1m
test access from external web browser using the service external IP http://104.154.32.162:8080
 check pod logs
$ kubectl logs mydeploy-2057093778-ns1mu
serving on port 8080server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558
check pod logs
$ kubectl logs mydeploy-2057093778-ns1mu
serving on port 8080server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558server: mydeploy-2057093778-ns1mu received request from: 10.128.0.2:64558