Month: May 2017

  • วิธีการติดตั้ง Kubernetes Add-on DNS และ DashBoard

    Kubernetes มี DNS กับ GUI ให้ใช้งานบ้างไหม

                หลังจากติดตั้ง Kubernetes แล้วการสร้าง containner โดยในที่นี้เรียกว่า pod (ใช้เรียก 1 containner หรือกลุ่มของ containner ก็ได้) ซึ่งสามารถสร้างด้วยคำสั่ง Kubectl ได้เลย (สร้างจากที่ไหนก็ได้) สำหรับผู้ที่ยังไม่ได้ติดตั้ง ต้องติดตั้งก่อนตามวิธีติดตั้ง Kubernetes บน CoreOS ตอนที่ 1[1] และ ตอนที่ 2[2] 

    สำหรับ Add-on ที่แนะนำจะเป็น DNS และ Dashboard ซึ่งเรียกได้ว่าจำเป็นต้องมี ไม่งั้นชีวิตจะยุ่งยากขึ้นเยอะครับ คงไม่มีใครอยากดูรายการ pod เยอะ ๆ ด้วย command line กันนะครับ

     วิธีการติดตั้ง DNS-Addon[3]

    • เข้าไปยังเครื่องที่ติดตั้ง Kubectl ไว้แล้ว ทำการสร้าง yaml file ดังนี้ (ถ้า vim วางแล้วเพี้ยนให้ใช้ nano แทน)
      nano dns-addon.yaml

      เนื้อหาในไฟล์ดังนี้ (อย่าลืมเปลี่ยน > เป็น > เวลา Copy & Paste ด้วยครับ)

      apiVersion: v1
      kind: Service
      metadata:
        name: kube-dns
        namespace: kube-system
        labels:
          k8s-app: kube-dns
          kubernetes.io/cluster-service: "true"
          kubernetes.io/name: "KubeDNS"
      spec:
        selector:
          k8s-app: kube-dns
        clusterIP: <DNS Cluster-IP>
        ports:
        - name: dns
          port: 53
          protocol: UDP
        - name: dns-tcp
          port: 53
          protocol: TCP
      
      
      ---
      
      
      apiVersion: v1
      kind: ReplicationController
      metadata:
        name: kube-dns-v20
        namespace: kube-system
        labels:
          k8s-app: kube-dns
          version: v20
          kubernetes.io/cluster-service: "true"
      spec:
        replicas: 1
        selector:
          k8s-app: kube-dns
          version: v20
        template:
          metadata:
            labels:
              k8s-app: kube-dns
              version: v20
            annotations:
              scheduler.alpha.kubernetes.io/critical-pod: ''
              scheduler.alpha.kubernetes.io/tolerations: '[{"key":"CriticalAddonsOnly", "operator":"Exists"}]'
          spec:
            containers:
            - name: kubedns
              image: gcr.io/google_containers/kubedns-amd64:1.9
              resources:
                limits:
                  memory: 170Mi
                requests:
                  cpu: 100m
                  memory: 70Mi
              livenessProbe:
                httpGet:
                  path: /healthz-kubedns
                  port: 8080
                  scheme: HTTP
                initialDelaySeconds: 60
                timeoutSeconds: 5
                successThreshold: 1
                failureThreshold: 5
              readinessProbe:
                httpGet:
                  path: /readiness
                  port: 8081
                  scheme: HTTP
                initialDelaySeconds: 3
                timeoutSeconds: 5
              args:
              - --domain=cluster.local.
              - --dns-port=10053
              ports:
              - containerPort: 10053
                name: dns-local
                protocol: UDP
              - containerPort: 10053
                name: dns-tcp-local
                protocol: TCP
            - name: dnsmasq
              image: gcr.io/google_containers/kube-dnsmasq-amd64:1.4
              livenessProbe:
                httpGet:
                  path: /healthz-dnsmasq
                  port: 8080
                  scheme: HTTP
                initialDelaySeconds: 60
                timeoutSeconds: 5
                successThreshold: 1
                failureThreshold: 5
              args:
              - --cache-size=1000
              - --no-resolv
              - --server=127.0.0.1#10053
              - --log-facility=-
              ports:
              - containerPort: 53
                name: dns
                protocol: UDP
              - containerPort: 53
                name: dns-tcp
                protocol: TCP
            - name: healthz
              image: gcr.io/google_containers/exechealthz-amd64:1.2
              resources:
                limits:
                  memory: 50Mi
                requests:
                  cpu: 10m
                  memory: 50Mi
              args:
              - --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1 > /dev/null
              - --url=/healthz-dnsmasq
              - --cmd=nslookup kubernetes.default.svc.cluster.local 127.0.0.1:10053 > /dev/null
              - --url=/healthz-kubedns
              - --port=8080
              - --quiet
              ports:
              - containerPort: 8080
                protocol: TCP
            dnsPolicy: Default
    • จากนั้นทำการสร้าง pod ดังนี้
      kubectl create -f dns-addon.yaml
    • สามารถตรวจสอบสถานะการสร้าง pod และ log ได้ดังนี้
      kubectl get pods --namespace=kube-system
      kubectl logs kube-dns-v20-xxxxx -n=kube-system dnsmasq
    • โดยอันที่จริงมีอีกหลายแบบครับ มีแบบ auto scale ก็มีครับ ลองศึกษาดูใน Internet ครับ

      วิธีการติดตั้ง Dashboard-Addon[3]

    • เข้าไปยังเครื่องที่ติดตั้ง Kubectl ไว้แล้ว ทำการสร้าง yaml file ดังนี้ (ถ้า vim วางแล้วเพี้ยนให้ใช้ nano แทน)
      nano kube-dashboard-rc.yaml

      เนื้อหาในไฟล์ดังนี้

      apiVersion: v1
      kind: ReplicationController
      metadata:
        name: kubernetes-dashboard-v1.6.1
        namespace: kube-system
        labels:
          k8s-app: kubernetes-dashboard
          version: v1.6.1
          kubernetes.io/cluster-service: "true"
      spec:
        replicas: 1
        selector:
          k8s-app: kubernetes-dashboard
        template:
          metadata:
            labels:
              k8s-app: kubernetes-dashboard
              version: v1.6.1
              kubernetes.io/cluster-service: "true"
            annotations:
              scheduler.alpha.kubernetes.io/critical-pod: ''
              scheduler.alpha.kubernetes.io/tolerations: '[{"key":"CriticalAddonsOnly", "operator":"Exists"}]'
          spec:
            containers:
            - name: kubernetes-dashboard
              image: gcr.io/google_containers/kubernetes-dashboard-amd64:v1.6.1
              resources:
                limits:
                  cpu: 100m
                  memory: 50Mi
                requests:
                  cpu: 100m
                  memory: 50Mi
              ports:
              - containerPort: 9090
              livenessProbe:
                httpGet:
                  path: /
                  port: 9090
                initialDelaySeconds: 30
                timeoutSeconds: 30
    • จากนั้นสร้างอีกไฟล์ดังนี้
      nano kube-dashboard-svc.yaml

      เนื้อหาในไฟล์ดังนี้

      apiVersion: v1
      kind: Service
      metadata:
        name: kubernetes-dashboard
        namespace: kube-system
        labels:
          k8s-app: kubernetes-dashboard
          kubernetes.io/cluster-service: "true"
      spec:
        selector:
          k8s-app: kubernetes-dashboard
        ports:
        - port: 80
          targetPort: 9090
    • จากนั้นทำการสร้าง pod ดังนี้
      kubectl create -f kube-dashboard-rc.yaml
      kubectl create -f kube-dashboard-svc.yaml
    • สามารถตรวจสอบสถานะการสร้าง pod และทำการ forward port ได้ดังนี้
      kubectl get pods --namespace=kube-system
      kubectl port-forward kubernetes-dashboard-v1.6.1-XXXX 9090 --namespace=kube-system

       

    • หลังจากนั้นสามารถทดสอบเปิด Browser บนเครื่องที่รัน kubectl เพื่อทดสอบได้เลย (สามารถเปิดใช้งานได้ 2 วิธีคือผ่านช่องทางปกติ หรือใช้ kubectl ดึงมาจาก pod โดยตรงแล้วทำการ forward port ก็ได้)

                      จะเห็นว่าถ้าเป็น web จะดูอะไรก็ง่ายขึ้นเยอะครับ แต่เนื่องจากไม่มีระบบ login ก็ต้องระวังดี ๆ ถ้าจะเปิดให้ใครก็ได้ใช้งาน อาจต้องสร้าง proxy ดักให้ใส่รหัสผ่านก่อนชั้นหนึ่ง หรือจะเน้นใช้ command line อย่างเดียวก็ได้ครับ….

    ==================================

    Reference :

    [1] รู้จักกับ Kubernetes และวิธีติดตั้ง Kubernetes ด้วย CoreOS (ตอนที่ 1 Master Node) : https://sysadmin.psu.ac.th/2017/05/17/setup-kubernetes-coreos-section-1/

    [2] วิธีติดตั้ง Kubernetes ด้วย CoreOS (ตอนที่ 2 Worker Node) : https://sysadmin.psu.ac.th/2017/05/27/setup-kubernetes-coreos-section-2/

    [3] CoreOS -> Deploy Add-ons : https://coreos.com/kubernetes/docs/latest/deploy-addons.html

     

  • เตรียม Linux Lite ไว้ใช้เมื่อฉุกเฉิน

    Linux มีหลายค่าย เช่น Ubuntu หรือ CentOS เป็นต้น เมื่อนำมาเพิ่มเติม Graphic User Interface (GUI) ให้ใช้งานได้ง่ายเช่นเดียวกับ Microsoft Windows ก็จะทำให้ Linux น่าใช้งานมาก สามารถใช้งานประจำวันได้เช่นเดียวกับ Microsoft Windows เลยนะครับ ผมจะข้ามเรื่องราวความเป็นมาของคำว่า Linux ไปนะครับ เอาเป็นว่าใครไม่รู้จักจริง ๆ ก็ Google Search เอานะครับ

    Linux ค่าย Ubuntu ถูกนำมาใส่ GUI โดยผู้พัฒนาหลายทีม ปัจจุบันจึงมีตัวเลือกให้ใช้งานอยู่เยอะมาก อันนี้บางคนก็ว่าเป็นข้อด้อยที่ทำให้มือใหม่ “งง” ไม่รู้จะเลือกตัวไหน ตัวที่ผมคิดว่าน่าใช้งานก็จะมี Linux Mint ซึ่งผมก็ใช้งานมาหลายปีทีเดียว วันนี้ผมพบว่ามี Trend ใหม่ที่ค่อนข้างน่าสนใจ คือ Linux Lite ครับ เป็นลิสต์ 1 ใน 5 ชื่อที่มีการโพสต์ไว้ในบล็อก “5 Lightweight Linux For Old Computers”  เป็น Linux ที่มีขนาดเล็กที่ทดสอบดูแล้วว่าใช้งานได้ดีกว่าอีก 4 ชื่อที่กล่าวถึงในบล็อกนั้น ยิ่งเล็กมากเป็นเบอร์ 1 นี่ จะไม่เหมาะสมที่จะนำมาใช้งานประจำวันได้เลย มันจะเหมาะกับงานแอดมินมากกว่า

    Linux Lite มีหน้าเว็บเพจที่มี Road Map ในการพัฒนาที่ชัดเจนทีเดียว ลองเข้าไปอ่านดูได้ที่ https://www.linuxliteos.com/ ครับ ทำให้ผมคิดว่าจะลองใช้งานตัวนี้แทน Linux Mint เพราะว่า Linux Lite มีขนาดที่เล็กกว่า และรู้สึกว่าใช้งานได้ง่าย ๆ เมนูก็คล้ายกับ Windows 7 ที่เราคุ้นเคย

    ผมตั้งชื่อบล็อกที่ผมเขียนในวันนี้ว่า “เตรียม Linux Lite ไว้ใช้เมื่อฉุกเฉิน” ผมคิดว่าพวกเราส่วนใหญ่จะใช้ Microsoft Windows กันทุกวัน แต่หากว่าวันใดที่เครื่องของเรา หรือ เพื่อนเรายกเครื่องมาให้เราช่วยดูเมื่อเกิดปัญหา หลาย ๆ ครั้งเรื่องราวมันจะจบลงที่ระบบปฏิบัติการเสียหาย ต้องล้างเครื่อง (Format) ใหม่ หรือไม่ก็อาจเกี่ยวกับ USB Flash Drive ที่ใช้เก็บไฟล์ข้อมูลที่ไปติดไวรัสคอมพิวเตอร์มาจากเครื่องคอมฯที่อื่น

    หากเราเรียนรู้วิธีการในวันนี้จะช่วยให้เราพร้อมที่จะจัดการปัญหาได้ทั้งแก่ตัวเองและช่วยเหลือเพื่อนของเราครับ

    ที่ผมจะทำก็คือผมจะติดตั้ง Linux Lite ลงไปใน USB Flash Drive เมื่อติดตั้งเสร็จแล้ว เราก็นำไปเสียบเข้าที่เครื่องคอมฯที่ BIOS สามารถตั้งค่าให้ boot USB Hard Disk ได้

    เราจะต้องทำดังนี้
    1. ให้แน่ใจว่า USB Flash Drive มีขนาดไม่น้อยกว่า 8 GB และพร้อมให้ฟอร์แมตได้
    2. ในเครื่อง Windows ของเรามีโปรแกรมที่ใช้สำหรับเขียนไฟล์ .iso ลงไปใน USB Flash Drive ได้ ผมเลือกใช้โปรแกรมชื่อว่า Rufus ล่าสุดคือรุ่น 2.14
    3. ไปยังเว็บไซต์ https://www.linuxliteos.com/ เพื่อดาวน์โหลดไฟล์ .iso ล่าสุดคือรุ่น 3.4 เลือกว่าจะเอา 32 Bit หรือ 64 Bit ไม่ต่างกันครับ (32 Bit จะนำไปใช้กับเครื่องที่มี RAM มากกว่า 4 GB ไม่ได้ครับ และ 64 Bit ก็จะนำไปใช้กับเครื่องเก่า ๆ ที่เมนบอร์ดเป็น 32 Bit ไม่ได้)
    4. ขั้นตอนติดตั้งคือ เสียบ USB Flash Drive จากนั้น เปิดโปรแกรม Rufus เลือกตำแหน่งที่วางไฟล์ .iso แล้วเลือกชื่อ USB Flash Drive แล้วกดปุ่มเพื่อติดตั้ง แล้วรอจนเสร็จ ถอด USB Flash Drive (ดูวิธีและภาพประกอบจากบล็อกที่เขียนไว้ เรื่อง “วิธีนำไฟล์ iso Linux Mint ลง USB Flash Drive ด้วยโปรแกรม Rufus for Windows“)

    ในตอนนี้ เราก็มี USB Flash Drive ที่พร้อมใช้เมื่อฉุกเฉินแล้ว แล้วใช้มันอย่างไรหละ

    ต่อไปก็เป็นขั้นตอนในการใช้งานเพื่อเข้าไป copy ไฟล์จากฮาร์ดดิสก์
    ขั้นตอนมีดังนี้ครับ
    1. บูตเครื่องด้วย USB Flash Drive Linux Lite ที่ทำเสร็จนั้น


    2. คลิกที่ไอคอน Home Folder เพื่อเปิดหน้าต่างโปรแกรม File Manager


    3. เสียบ USB Flash Drive Data ที่จะนำมาเก็บไฟล์จากฮาร์ดดิสก์ (ในรูปภาพคือไอคอนชื่อ MY_USB)


    4. คลิกเลือกไอคอนที่เป็นฮาร์ดดิสก์ของวินโดวส์


    5. ค้นหาไฟล์แล้ว เจอแล้วใช้วิธีการคลิกลากไปยังหน้าต่างของ USB Flash Drive Data (ตรงจุดนี้ไม่ทำรูปภาพให้ดูนะครับ ง่ายเหมือนใช้งาน Windows นะครับ)
    6. เมื่อเสร็จ ให้คลิกขวาที่ไอคอน USB Flash Drive Data และเลือกคำสั่ง Unmount

     

    และขั้นตอนในการใช้งานเพื่อจัดการลบไฟล์ใน USB Flash Drive ที่ติดไวรัส ก็คล้าย ๆ กัน
    ขั้นตอนมีดังนี้ครับ
    1. บูตเครื่องด้วย USB Flash Drive Linux Lite ที่ทำเสร็จนั้น
    2. เสียบ USB Flash Drive อันที่ติดไวรัสนั้น
    3. ค้นหาดูจะพบว่ามีโฟลเดอร์ที่มีชื่อแปลก ๆ เช่น ไม่มีชื่อแต่เป็นไอคอนรูปโฟลเดอร์ เป็นต้น
    4. ให้เปลี่ยนชื่อโฟลเดอร์จาก ไม่มีชื่อ เป็น ชื่ออะไรก็ได้ แค่นี้เอง

  • วิธีติดตั้ง Kubernetes ด้วย CoreOS (ตอนที่ 2 Worker Node)

    ถ้าต้องการระบบจัดการ docker container สักตัวต้องทำอย่างไร (ตอนที่ 2)

                จากตอนก่อนหน้านี้ รู้จักกับ Kubernetes และวิธีติดตั้ง Kubernetes ด้วย CoreOS (ตอนที่ 1 Master Node)[1] ก็มาต่อด้วยการติดตั้งบนเครื่อง Worker ต่อครับ

     วิธีการติดตั้ง Kubernetes Worker Node[2]

    • ทำการติดตั้ง CoreOS บน Worker Node
    • สร้าง directory ดังนี้
      sudo mkdir -p /etc/kubernetes/ssl
    • ทำการ copy ที่สร้างไว้ก่อนหน้านี้มาไว้ใน folder ดังนี้
      File: /etc/kubernetes/ssl/ca.pem
      File: /etc/kubernetes/ssl/${WORKER_FQDN}-worker.pem
      File: /etc/kubernetes/ssl/${WORKER_FQDN}-worker-key.pem
    • เปลี่ยน permission และ owner file เฉพาะไฟล์ -key* ดังนี้
      sudo chmod 600 /etc/kubernetes/ssl/*-key.pem
      sudo chown root:root /etc/kubernetes/ssl/*-key.pem
    • ทำการทำ link เผื่อให้ config แต่ละ worker เหมือน ๆ กัน
      cd /etc/kubernetes/ssl/
      sudo ln -s ${WORKER_FQDN}-worker.pem worker.pem
      sudo ln -s ${WORKER_FQDN}-worker-key.pem worker-key.pem
    • จากนั้นตั้งค่า flannel network เป็น network ที่เอาไว้เชื่อมแต่ละ pod ให้สามารถคุยกันได้ข้ามเครื่อง เพื่อสร้างวง virtual ip ให้กับ pod ดังนี้
      sudo mkdir /etc/flannel

      ทำการสร้างไฟล์ option.env

      sudo vim /etc/flannel/options.env

      เนื้อหาในไฟล์ดังนี้

      FLANNELD_IFACE=<Worker IP>
      FLANNELD_ETCD_ENDPOINTS=http://<Master IP>:2379,http://<Node1 IP>:2379,http://<Node2 IP>:2379
    • จากนั้นทำการสร้าง flannel service ดังนี้
      sudo mkdir -p /etc/systemd/system/flanneld.service.d/
      sudo vim /etc/systemd/system/flanneld.service.d/40-ExecStartPre-symlink.conf

      เนื้อหาในไฟล์ดังนี้

      [Service]
      ExecStartPre=/usr/bin/ln -sf /etc/flannel/options.env /run/flannel/options.env
    • จากนั้นทำการตั้งค่า docker เพื่อกำหนดให้ใช้งานผ่าน flannel โดยสร้างไฟล์ config ดังนี้
      sudo mkdir -p /etc/systemd/system/docker.service.d
      sudo vim /etc/systemd/system/docker.service.d/40-flannel.conf

      เนื้อหาในไฟล์ดังนี้

      [Unit]
      Requires=flanneld.service
      After=flanneld.service
      [Service]
      EnvironmentFile=/etc/kubernetes/cni/docker_opts_cni.env

      โดยที่ทำสร้างไฟล์ docker_opts_cni.env ขึ้นมาประกอบดังนี้

      sudo mkdir -p /etc/kubernetes/cni
      sudo vim /etc/kubernetes/cni/docker_opts_cni.env

      เนื้อหาในไฟล์ดังนี้

      DOCKER_OPT_BIP=""
      DOCKER_OPT_IPMASQ=""
    • จากนั้นทำการ restart docker service สักรอบดังนี้
      sudo systemctl restart docker
    • หนังจากนั้นทำการสร้าง config ไฟล์สุดท้ายสำหรับ flannel ดังนี้
      sudo mkdir -p /etc/kubernetes/cni/net.d
      sudo vim /etc/kubernetes/cni/net.d/10-flannel.conf

      เนื้อหาในไฟล์ดังนี้

      {
       "name": "podnet",
       "type": "flannel",
       "delegate": {
       "isDefaultGateway": true
       }
      }
    • ทำการ start flannel service และตรวจสถานะการทำงานดู
      sudo systemctl start flanneld
      sudo systemctl enable flanneld
      sudo systemctl status flanneld
    • จากนั้นทำการสร้าง kubelet service ดังนี้
      sudo vim /etc/systemd/system/kubelet.service

      เนื้อหาในไฟล์ดังนี้ (KUBELET_IMAGE_TAG version สามารถตรวจสอบล่าสุดได้ที่ https://quay.io/repository/coreos/hyperkube?tab=tags)

      [Service]
      Environment=KUBELET_IMAGE_TAG=v1.6.2_coreos.0
      Environment="RKT_RUN_ARGS=--uuid-file-save=/var/run/kubelet-pod.uuid \
        --volume var-log,kind=host,source=/var/log \
        --mount volume=var-log,target=/var/log \
        --volume dns,kind=host,source=/etc/resolv.conf \
        --mount volume=dns,target=/etc/resolv.conf"
      ExecStartPre=/usr/bin/mkdir -p /etc/kubernetes/manifests
      ExecStartPre=/usr/bin/mkdir -p /var/log/containers
      ExecStartPre=-/usr/bin/rkt rm --uuid-file=/var/run/kubelet-pod.uuid
      ExecStart=/usr/lib/coreos/kubelet-wrapper \
        --api-servers=https://<Master_IP> \
        --cni-conf-dir=/etc/kubernetes/cni/net.d \
        --network-plugin=cni \
        --container-runtime=docker \
        --register-node=true \
        --allow-privileged=true \
        --pod-manifest-path=/etc/kubernetes/manifests \
        --cluster_dns=<DNS_SERVICE_IP> \
        --cluster_domain=<CLUSTER_DNS_NAME> \
        --kubeconfig=/etc/kubernetes/worker-kubeconfig.yaml \
        --tls-cert-file=/etc/kubernetes/ssl/worker.pem \
        --tls-private-key-file=/etc/kubernetes/ssl/worker-key.pem
      ExecStop=-/usr/bin/rkt stop --uuid-file=/var/run/kubelet-pod.uuid
      Restart=always
      RestartSec=10
      
      [Install]
      WantedBy=multi-user.target
    • ทำการ start kubelet service และตรวจสถานะการทำงานดู (ต้องรอสักพักเพราะ service จะต้องโหลด image มาติดตั้งให้ในการ start ครั้งแรก สามารถใช้คำสั่ง journalctl -xe เพื่อตรวจสอบสถานะการทำงาน) ซึ่งจะพบว่ายัง error เพราะยังไม่ได้ลง kube-apiserver (แนะนำลงตัวอื่นให้เสร็จให้หมดแล้วค่อยมา start kubelet service ก็ได้)
      sudo systemctl start kubelet
      sudo systemctl enable kubelet
      sudo systemctl status kubelet
    • หลังจากนั้นทำการติดตั้ง kube-proxy ดังนี้
      sudo vim /etc/kubernetes/manifests/kube-proxy.yaml

      มีเนื้อหาในไฟล์ดังนี้

      apiVersion: v1
      kind: Pod
      metadata:
        name: kube-proxy
        namespace: kube-system
      spec:
        hostNetwork: true
        containers:
        - name: kube-proxy
          image: quay.io/coreos/hyperkube:v1.6.2_coreos.0
          command:
          - /hyperkube
          - proxy
          - --master=https://${MASTER_IP}
          - --kubeconfig=/etc/kubernetes/worker-kubeconfig.yaml
          securityContext:
            privileged: true
          volumeMounts:
          - mountPath: /etc/ssl/certs
            name: "ssl-certs"
          - mountPath: /etc/kubernetes/worker-kubeconfig.yaml
            name: "kubeconfig"
            readOnly: true
          - mountPath: /etc/kubernetes/ssl
            name: "etc-kube-ssl"
            readOnly: true
        volumes:
        - name: "ssl-certs"
          hostPath:
            path: "/usr/share/ca-certificates"
        - name: "kubeconfig"
          hostPath:
            path: "/etc/kubernetes/worker-kubeconfig.yaml"
        - name: "etc-kube-ssl"
          hostPath:
            path: "/etc/kubernetes/ssl"
      
    • ต่อด้วยการตั้งค่า kubeconfig ดังนี้
      sudo vim /etc/kubernetes/worker-kubeconfig.yaml

      มีเนื้อหาในไฟล์ดังนี้

      apiVersion: v1
      kind: Config
      clusters:
      - name: local
        cluster:
          certificate-authority: /etc/kubernetes/ssl/ca.pem
      users:
      - name: kubelet
        user:
          client-certificate: /etc/kubernetes/ssl/worker.pem
          client-key: /etc/kubernetes/ssl/worker-key.pem
      contexts:
      - context:
          cluster: local
          user: kubelet
        name: kubelet-context
      current-context: kubelet-context
    • ในกรณีที่ต้องการแจ้ง systemd ว่าเรามีการเปลี่ยนข้อมูลใน config และต้องการ rescan ทุกอย่างอีกครั้งให้สั่งดังนี้
      sudo systemctl daemon-reload
    • จากนั้นทดสอบ restart kubelet service ใหม่อีกครั้งและตรวจสอบ status หรือ journalctl -xe เพื่อดูว่าการทำงานปกติหรือไม่ ถ้าไม่แก้ให้ถูกต้องแล้ว restart ใหม่อีกครั้งไปเรื่อย ๆ จนกว่าจะปกติ
      sudo systemctl restart kubelet

      จบไปแล้วครับสำหรับการติดตั้ง worker node ครับ ต่อด้วยการติดตั้ง Kubectl สำหรับตรวจสอบสถานะแต่ละ Node ครับ

    วิธีการติดตั้ง Kubectl[3]

    • ทำการ Download tool ในที่นี้จะติดตั้งลงบนเครื่องอื่นที่ไม่ใช่ coreos (อย่าลืม copy เอา ca.pem,admin.pem,admin-key.pem ไปด้วย) เพราะ coreos ไม่อนุญาติให้เขียนบนพื้นที่ ../bin (จริง ๆ ติดตั้งที่ใดก็ได้ OS ใดก็ได้ครับยกตัวอย่าง windows[4]) โดยเลือก Version ให้สอดคล้องกับที่ใช้งานอยู่ครับ
      curl -O https://storage.googleapis.com/kubernetes-release/release/v1.6.2/bin/linux/amd64/kubectl
    • จากนั้นทำการเปลี่ยน permission ให้ execute ได้ และ ทำการ copy ไป global command
      chmod +x kubectl
      sudo mv kubectl /usr/local/sbin/ 
    • จากนั้นทำการตั้งค่าโปรแกรม (ต้องรันทุกครั้งหลังจาก Restart เครื่อง)
      kubectl config set-cluster default-cluster --server=https://<MASTER_IP> --certificate-authority=<cer path>/ca.pem
      kubectl config set-credentials default-admin --certificate-authority=<cer path>/ca.pem, --client-key=<cer path>/admin-key.pem --client-certificate=<cer path>/admin.pem
      kubectl config set-context default-system --cluster=default-cluster --user=default-admin
      kubectl config use-context default-system
    • จากนั้นจะสามารถใช้คำสั่งตรวจสอบสถานะได้ดังนี้
      ./kubectl get nodes

    จบไปแล้วครับสำหรับวิธีติดตั้ง Worker Node และ Kubectl ถ้าทำไม่ได้ลองทำซ้ำ ๆ ดูครับ ลองดู docker logs <containner_id> ตรวจดูปัญหาใน docker และ journalctl -xe เพื่อตรวจสอบ service ดูครับ…..

    ==================================

    Reference :

    [1] รู้จักกับ Kubernetes และวิธีติดตั้ง Kubernetes ด้วย CoreOS (ตอนที่ 1 Master Node) : https://sysadmin.psu.ac.th/2017/05/17/setup-kubernetes-coreos-section-1/

    [2] CoreOS -> Deploy Kubernetes Worker Node(s) : https://coreos.com/kubernetes/docs/latest/deploy-workers.html

    [3] CoreOS -> Setting up kubectl : https://coreos.com/kubernetes/docs/latest/configure-kubectl.html

    [4] Running kubectl on Windows : https://github.com/eirslett/kubectl-windows

  • Regular Expression สำหรับเลือก field ที่ต้องการจาก CSV File

    ตัวอย่างเช่น มีข้อมูลแบบ

    a,b,c,d,e

    ต้องการเฉพาะ Column ที่ 3 นั่นคือต้องการ c

    ให้ Find

    ^([^,]*),([^,]*),([^,]*),([^,]*),([^,]*)

    แล้ว Replace ด้วย

    \3

     

  • Regular Expression สำหรับ Email Address Validation

    หา valid email address

    ^(?!\b[a-zA-Z0-9._-]+@ [a-zA-Z0-9_.-]+\.[a-zA-Z0-9]{2,}\b).*$

    หาก invalid email address

    ^(?=\b[a-zA-Z0-9._-]+@ [a-zA-Z0-9_.-]+\.[a-zA-Z0-9]{2,}\b).*$
  • รู้จักกับ Kubernetes และวิธีติดตั้ง Kubernetes ด้วย CoreOS (ตอนที่ 1 Master Node)

    ถ้าต้องการระบบจัดการ docker container สักตัวต้องทำอย่างไร

                เมื่อกล่าวถึงระบบจัดการ docker container สักตัวหนึ่ง มักจะกล่าวถึง opensource ตัวหนึ่งชื่อ kubernetes ซึ่งเป็นเครื่องมือที่พัฒนาขึ้นมาด้วย Google[1] ซึ่งสามารถรองรับทั้งในส่วนของ Google Container Engine และ CoreOS จริง ๆ ลงได้บนอีกหลาย platform แต่สำหรับ CoreOS ได้ออกแบบมาให้รองรับ Kubernetes ทำให้การติดตั้งง่ายและสมบูรณ์มากขึ้น (อ่านไปเรื่อย ๆ จะสงสัยนี่ง่ายแล้วเหรอ แต่หลังจากเขียนบทความนี้เสร็จก็มีตัวติดตั้งตัวใหม่ชื่อ Tectonic[6] น่าจะเป็นตัวที่ทำให้การติดตั้งง่ายขึ้นครับ)

                Kubernetes เป็นเครื่องมือที่ช่วย build, deploy และ scale ให้เป็นเรื่องง่าย ๆ และสามารถ replicate containner ได้ง่ายมาก การติดตั้ง Kubernetes บน Google Container Engine ง่ายมาก แต่การติดตั้งบน CoreOS จะยากกว่า ซึ่งสามารถติดตั้งแบบ Single Node และ Multi-Node ซึ่งถ้าจะทำ Multi-Node ต้องเชื่อมต่อไปยัง etcd service ที่ติดตั้งบน CoreOS Cluster ด้วยก็จะดีครับ (ไม่งั้นเป็น Cluster ที่ไม่สมบูรณ์) สามารถอ่านเพิ่มเติมได้ที่วิธีการติดตั้ง CoreOS Cluster[2] (ในบทความใช้ก่อนหน้านี้ CoreOS Cluster เขียนในส่วน ETCD Version 2 แต่การใช้งานกับ Kubernetes ต้องใช้ ETCD Version 3 ตอนนี้ยังไม่มีบทความเสริมในส่วนนี้ อาจจะต้องหาข้อมูลเองก่อนครับ จริง ๆ มีวิธีแต่ยังยากในการเขียนบทความ ไว้ค่อยเขียนเพิ่มให้อีกทีครับ) ซึ่งแน่นอนระหว่าง master node และ worker node มีการตรวจสอบเรื่อง certificate ระหว่าง service ด้วย

                ตัวอย่าง Diagram ของระบบทั้งหมด[3]

    เรียนรู้การค่าเบื้องต้นก่อนการติดตั้ง[4]

    • MASTER_HOST : คือ ชื่อ host ที่ node ลูกเอาไว้ติดต่อและให้เข้าถึงจาก external client  เช่นเวลาสั่งสร้างเครื่องก็จะสั่งผ่านตัวนี้ ในกรณที่ต้องการทำ HA MASTER_HOST จะถูกใช้เป็น load balance โดยใช้ร่วมกับ DNS name โดยการคุยกันระหว่าง MASTER_HOST และ worker (node ลูก) จะใช้ port 443 และมีการเข้ารหัสและยืนยันด้วย TLS Certificate
    • ETCD_ENDPOINT : คือ บริการของ etcd service ซึ่งมีใน CoreOS Cluster ที่ติดตั้งไว้ ให้ใส่ไปให้หมดว่ามีเครื่องอะไรบ้าง คั่นด้วย , (ในที่นี้ไม่ได้ใช้ fleet สร้างเครื่อง หลังจากลงเสร็จจะใช้ kubectl สร้างแทน)
    • POD_NETWORK : เช่น 10.2.0.0/16 ใช้สำหรับกำหนดวง IP ของ pod (pod คือ ชื่อเรียก container อาจจะแค่ 1 container เหรือเรียกเป็นกลุ่มของหลาย ๆ container ที่สร้างด้วย kubernetes)
    • SERVICE_IP_RANGE : เช่น 10.3.0.0/24 ใช้สำหรับ service cluster VIPs ซึ่งควรจะอยู่คนละวงกับ pod_network ซึ่งเป็น ip ที่ไว้ให้ข้างนอกวงเข้าถึง มักจะเป็น IP สำหรับให้บริการ Service ต่าง ๆ และไว้สำหรับใช้งานคู่กับ kube-proxy
    • K8S_SERVICE_IP : เช่น 10.3.0.1 เป็น IP หนึ่งในวง SERVICE_IP_RANGE เพื่อให้บริการ Kubernetes API Service
    • DNS_SERVICE_IP : เช่น 10.3.0.10 เป็น IP หนึ่งในวง SERVICE_IP_RANGE ใช้สำหรับเป็น VIP ของ DNS Service เพื่อให้บริการ DNS ให้กับ worker แต่ละตัว

    วิธีการตั้งค่า TLS สำหรับ Kubernetes[4]

    • ทำการสร้าง Cluster Root CA  (ทุกไฟล์ต่อจากนี้ทำเก็บไว้ที่ CoreOS สักเครื่องหนึ่ง ถึงเวลาติดตั้ง Master, Worker ค่อยมาโหลดมาใช้ครับ)
      sudo openssl genrsa -out ca-key.pem 2048
      sudo openssl req -x509 -new -nodes -key ca-key.pem -days 10000 -out ca.pem -subj "/CN=kube-ca"

    • ตั้งค่า openssl config สำหรับ api-server โดยการสร้างไฟล์ดังนี้
      vim openssl.cnf

      โดยมีเนื้อหาในไฟล์ดังนี้ (ให้ระบุ IP Service และ Master Host ลงไปด้วย)
      *หมายเหตุ : แทนที่เลข IP ใน <….>

      [req]
      req_extensions = v3_req
      distinguished_name = req_distinguished_name
      [req_distinguished_name]
      [ v3_req ]
      basicConstraints = CA:FALSE
      keyUsage = nonRepudiation, digitalSignature, keyEncipherment
      subjectAltName = @alt_names
      [alt_names]
      DNS.1 = kubernetes
      DNS.2 = kubernetes.default
      DNS.3 = kubernetes.default.svc
      DNS.4 = kubernetes.default.svc.cluster.local
      IP.1 = <K8S_SERVICE_IP>
      IP.2 = <MASTER_HOST>
    • จากนั้นทำการสร้าง API Server Keypair ดังนี้
      sudo openssl genrsa -out apiserver-key.pem 2048
      sudo openssl req -new -key apiserver-key.pem -out apiserver.csr -subj "/CN=kube-apiserver" -config openssl.cnf
      sudo openssl x509 -req -in apiserver.csr -CA ca.pem -CAkey ca-key.pem -CAcreateserial -out apiserver.pem -days 365 -extensions v3_req -extfile openssl.cnf

    • ต่อไปเป็นส่วนของสร้าง Cer ในเครื่องลูกทุกเครื่อง (สร้างทีละเครื่องนะครับ) ทำการสร้างไฟล์ดังนี้
      vim worker-openssl.cnf

      เนื้อหาในไฟล์ดังนี้ แทนที่ WORKER_IP ด้วยเครื่องที่ต้องการ

      [req]
      req_extensions = v3_req
      distinguished_name = req_distinguished_name
      [req_distinguished_name]
      [ v3_req ]
      basicConstraints = CA:FALSE
      keyUsage = nonRepudiation, digitalSignature, keyEncipherment
      subjectAltName = @alt_names
      [alt_names]
      IP.1 = <WORKER_IP>
    • จากนั้นทำการสร้าง Keypair ในแต่ละ Worker ดังนี้ (WORKER_FQDN คือชื่อที่จด domain ไว้ ไม่มีก็ใส่ /etc/hosts เอาก็ได้ครับ แต่ต้องใส่เองทุกเครื่อง)
      sudo openssl genrsa -out ${WORKER_FQDN}-worker-key.pem 2048
      sudo WORKER_IP=${WORKER_IP} openssl req -new -key ${WORKER_FQDN}-worker-key.pem -out ${WORKER_FQDN}-worker.csr -subj "/CN=${WORKER_FQDN}" -config worker-openssl.cnf
      sudo WORKER_IP=${WORKER_IP} openssl x509 -req -in ${WORKER_FQDN}-worker.csr -CA ca.pem -CAkey ca-key.pem -CAcreateserial -out ${WORKER_FQDN}-worker.pem -days 365 -extensions v3_req -extfile worker-openssl.cnf
    • สุดท้ายคือการสร้าง Keypair ของ Cluster Admin
       sudo openssl genrsa -out admin-key.pem 2048
       sudo openssl req -new -key admin-key.pem -out admin.csr -subj "/CN=kube-admin"
       sudo openssl x509 -req -in admin.csr -CA ca.pem -CAkey ca-key.pem -CAcreateserial -out admin.pem -days 365
    • ทำได้ครบแล้วก็จะได้ประมาณดังรูป (ยกตัวอย่างมี  4 worker ใช้วิธีเขียน gen-worker-keypair.sh เพื่อรันหลาย ๆ รอบ ลองหาวิธีเขียนดูเองนะครับ)

    วิธีการตั้งค่า Kubernetes บน CoreOS Cluster[5]

    เพื่อให้การติดตั้งง่ายขึ้น อย่าลืมกำหนดค่าต่าง ๆ จดไว้ก่อน ไม่งั้นจะงงได้ ประมาณนี้ครับ

    ETCD_ENDPOINT=http://a.b.c.d:2379,http://a.b.c.e:2379,http://a.b.c.f:2379
    SERVER_IP_NETWORK=?
    K8S_SERVICE_IP=?
    MASTER_HOST=?
    DNS_SERVICE_IP=?
    POD_NETWORK=?

    ทำการติดตั้ง Master Node

    • ทำการติดตั้ง CoreOS บน Master Node
    • สร้าง directory ดังนี้
      sudo mkdir -p /etc/kubernetes/ssl
    • ทำการ copy ที่สร้างไว้ก่อนหน้านี้มาไว้ใน folder ดังนี้
      File: /etc/kubernetes/ssl/ca.pem
      File: /etc/kubernetes/ssl/apiserver.pem
      File: /etc/kubernetes/ssl/apiserver-key.pem
    • เปลี่ยน permission และ owner file เฉพาะไฟล์ -key* ดังนี้
      sudo chmod 600 /etc/kubernetes/ssl/*-key.pem
      sudo chown root:root /etc/kubernetes/ssl/*-key.pem
    • จากนั้นตั้งค่า flannel network[3] เป็น network ที่เอาไว้เชื่อมแต่ละ pod ให้สามารถคุยกันได้ข้ามเครื่อง (ต้องทำทุก node รวม worker ด้วย) เพื่อสร้างวง virtual ip ให้กับ pod ดังนี้
      sudo mkdir /etc/flannel

      ทำการสร้างไฟล์ option.env

      sudo vim /etc/flannel/options.env

      เนื้อหาในไฟล์ดังนี้

      FLANNELD_IFACE=<Master IP>
      FLANNELD_ETCD_ENDPOINTS=http://<Master IP>:2379,http://<Node1 IP>:2379,http://<Node2 IP>:2379
    • จากนั้นทำการสร้าง flannel service ดังนี้
      sudo mkdir -p /etc/systemd/system/flanneld.service.d/
      sudo vim /etc/systemd/system/flanneld.service.d/40-ExecStartPre-symlink.conf

      เนื้อหาในไฟล์ดังนี้

      [Service]
      ExecStartPre=/usr/bin/ln -sf /etc/flannel/options.env /run/flannel/options.env
    • จากนั้นทำการตั้งค่า docker เพื่อกำหนดให้ใช้งานผ่าน flannel โดยสร้างไฟล์ config ดังนี้
      sudo mkdir -p /etc/systemd/system/docker.service.d
      sudo vim /etc/systemd/system/docker.service.d/40-flannel.conf

      เนื้อหาในไฟล์ดังนี้

      [Unit]
      Requires=flanneld.service
      After=flanneld.service
      [Service]
      EnvironmentFile=/etc/kubernetes/cni/docker_opts_cni.env

      โดยที่ทำสร้างไฟล์ docker_opts_cni.env ขึ้นมาประกอบดังนี้

      sudo mkdir -p /etc/kubernetes/cni
      sudo vim /etc/kubernetes/cni/docker_opts_cni.env

      เนื้อหาในไฟล์ดังนี้

      DOCKER_OPT_BIP=""
      DOCKER_OPT_IPMASQ=""
    • จากนั้นทำการ restart docker service สักรอบดังนี้
      sudo systemctl restart docker
    • หนังจากนั้นทำการสร้าง config ไฟล์สุดท้ายสำหรับ flannel ดังนี้
      sudo mkdir -p /etc/kubernetes/cni/net.d
      sudo vim /etc/kubernetes/cni/net.d/10-flannel.conf

      เนื้อหาในไฟล์ดังนี้

      {
       "name": "podnet",
       "type": "flannel",
       "delegate": {
       "isDefaultGateway": true
       }
      }
    • ทำการ start flannel service และตรวจสถานะการทำงานดู
      sudo systemctl start flanneld
      sudo systemctl enable flanneld
      sudo systemctl status flanneld
    • จากนั้นทำการสั่งให้ทำ vxlan ผ่าน etcdctl ให้กับทุก node ดังนี้ (เปลี่ยน IP เป็นวงที่ต้องการ)
      sudo etcdctl set /coreos.com/network/config "{\"Network\":\"10.2.0.0/16\",\"Backend\":{\"Type\":\"vxlan\"}}"
    • จากนั้นทำการสร้าง kubelet service ดังนี้
      sudo vim /etc/systemd/system/kubelet.service

      เนื้อหาในไฟล์ดังนี้ (KUBELET_IMAGE_TAG version สามารถตรวจสอบล่าสุดได้ที่ https://quay.io/repository/coreos/hyperkube?tab=tags)

      [Service]
      Environment=KUBELET_IMAGE_TAG=v1.6.2_coreos.0
      Environment="RKT_RUN_ARGS=--uuid-file-save=/var/run/kubelet-pod.uuid \
        --volume var-log,kind=host,source=/var/log \
        --mount volume=var-log,target=/var/log \
        --volume dns,kind=host,source=/etc/resolv.conf \
        --mount volume=dns,target=/etc/resolv.conf"
      ExecStartPre=/usr/bin/mkdir -p /etc/kubernetes/manifests
      ExecStartPre=/usr/bin/mkdir -p /var/log/containers
      ExecStartPre=-/usr/bin/rkt rm --uuid-file=/var/run/kubelet-pod.uuid
      ExecStart=/usr/lib/coreos/kubelet-wrapper \
        --api-servers=http://127.0.0.1:8080 \
        --container-runtime=docker \
        --allow-privileged=true \
        --pod-manifest-path=/etc/kubernetes/manifests \
        --cluster_dns=<DNS_SERVICE_IP> \
        --cluster_domain=<CLUSTER_DNS_NAME>
      ExecStop=-/usr/bin/rkt stop --uuid-file=/var/run/kubelet-pod.uuid
      Restart=always
      RestartSec=10
      
      [Install]
      WantedBy=multi-user.target
    • ทำการ start kubelet service และตรวจสถานะการทำงานดู (ต้องรอสักพักเพราะ service จะต้องโหลด image มาติดตั้งให้ในการ start ครั้งแรก สามารถใช้คำสั่ง journalctl -xe เพื่อตรวจสอบสถานะการทำงาน) ซึ่งจะพบว่ายัง error เพราะยังไม่ได้ลง kube-apiserver (แนะนำลงตัวอื่นให้เสร็จให้หมดแล้วค่อยมา start kubelet service ก็ได้)
      sudo systemctl start kubelet
      sudo systemctl enable kubelet
      sudo systemctl status kubelet
    • ขั้นตอนต่อไปเป็นการสร้าง Rest API สำหรับจัดการ kubernetes (รวมถึงสามารถติดตั้งหน้าจอ GUI เพื่อควบคุมผ่าน Web ได้) โดยสร้างไฟล์ดังนี้
      sudo vim /etc/kubernetes/manifests/kube-apiserver.yaml

      เนื้อหาในไฟล์มีดังนี้ (ระวังเรื่องวรรคด้วยนะครับ ถ้าจะพิมพ์เองไม่แนะนำ copy ไปแก้ดีกว่า)

      apiVersion: v1
      kind: Pod
      metadata:
        name: kube-apiserver
        namespace: kube-system
      spec:
        hostNetwork: true
        containers:
        - name: kube-apiserver
          image: quay.io/coreos/hyperkube:v1.6.2_coreos.0
          command:
          - /hyperkube
          - apiserver
          - --bind-address=0.0.0.0
          - --etcd-servers=${ETCD_ENDPOINTS1},${ETCD_ENDPOINTS2},${ETCD_ENDPOINTS3}
          - --allow-privileged=true
          - --service-cluster-ip-range=${SERVICE_IP_RANGE}
          - --secure-port=443
          - --advertise-address=${ADVERTISE_IP}
          - --admission-control=NamespaceLifecycle,LimitRanger,ServiceAccount,DefaultStorageClass,ResourceQuota
          - --tls-cert-file=/etc/kubernetes/ssl/apiserver.pem
          - --tls-private-key-file=/etc/kubernetes/ssl/apiserver-key.pem
          - --client-ca-file=/etc/kubernetes/ssl/ca.pem
          - --service-account-key-file=/etc/kubernetes/ssl/apiserver-key.pem
          - --runtime-config=extensions/v1beta1/networkpolicies=true
          - --anonymous-auth=false
          livenessProbe:
            httpGet:
              host: 127.0.0.1
              port: 8080
              path: /healthz
            initialDelaySeconds: 15
            timeoutSeconds: 15
          ports:
          - containerPort: 443
            hostPort: 443
            name: https
          - containerPort: 8080
            hostPort: 8080
            name: local
          volumeMounts:
          - mountPath: /etc/kubernetes/ssl
            name: ssl-certs-kubernetes
            readOnly: true
          - mountPath: /etc/ssl/certs
            name: ssl-certs-host
            readOnly: true
        volumes:
        - hostPath:
            path: /etc/kubernetes/ssl
          name: ssl-certs-kubernetes
        - hostPath:
            path: /usr/share/ca-certificates
          name: ssl-certs-host
      
    • เพื่อให้สมบูรณ์ไปในคราวเดียว ต่อด้วยติดตั้ง kube-proxy ดังนี้
      sudo vim /etc/kubernetes/manifests/kube-proxy.yaml

      มีเนื้อหาในไฟล์ดังนี้

      apiVersion: v1
      kind: Pod
      metadata:
        name: kube-proxy
        namespace: kube-system
      spec:
        hostNetwork: true
        containers:
        - name: kube-proxy
          image: quay.io/coreos/hyperkube:v1.6.2_coreos.0
          command:
          - /hyperkube
          - proxy
          - --master=http://127.0.0.1:8080
          securityContext:
            privileged: true
          volumeMounts:
          - mountPath: /etc/ssl/certs
            name: ssl-certs-host
            readOnly: true
        volumes:
        - hostPath:
            path: /usr/share/ca-certificates
          name: ssl-certs-host
      
    • ยังไม่หมดต่อด้วย kube-controller-manager ใช้ในการทำ scale, replica โดยเป็นตัวควบคุม API อีกชั้นหนึ่ง ทำการสร้างไฟล์ดังนี้
      sudo vim /etc/kubernetes/manifests/kube-controller-manager.yaml

      มีเนื้อหาในไฟล์ดังนี้

      apiVersion: v1
      kind: Pod
      metadata:
        name: kube-controller-manager
        namespace: kube-system
      spec:
        hostNetwork: true
        containers:
        - name: kube-controller-manager
          image: quay.io/coreos/hyperkube:v1.6.2_coreos.0
          command:
          - /hyperkube
          - controller-manager
          - --master=http://127.0.0.1:8080
          - --leader-elect=true
          - --service-account-private-key-file=/etc/kubernetes/ssl/apiserver-key.pem
          - --root-ca-file=/etc/kubernetes/ssl/ca.pem
          resources:
            requests:
              cpu: 200m
          livenessProbe:
            httpGet:
              host: 127.0.0.1
              path: /healthz
              port: 10252
            initialDelaySeconds: 15
            timeoutSeconds: 15
          volumeMounts:
          - mountPath: /etc/kubernetes/ssl
            name: ssl-certs-kubernetes
            readOnly: true
          - mountPath: /etc/ssl/certs
            name: ssl-certs-host
            readOnly: true
        volumes:
        - hostPath:
            path: /etc/kubernetes/ssl
          name: ssl-certs-kubernetes
        - hostPath:
            path: /usr/share/ca-certificates
          name: ssl-certs-host
    • สำหรับอันสุดท้ายก็จะเป็น kube-scheduler (สำหรับการใช้งานเนื่องจากยังไม่ได้ลองใช้งาน ยังไม่เข้าใจว่าทำงานอย่างไร ถ้าว่างจะมาแก้อีกทีครับ) ทำการสร้างไฟล์ดังนี้
      sudo vim /etc/kubernetes/manifests/kube-scheduler.yaml

      มีเนื้อหาในไฟล์ดังนี้

      apiVersion: v1
      kind: Pod
      metadata:
        name: kube-scheduler
        namespace: kube-system
      spec:
        hostNetwork: true
        containers:
        - name: kube-scheduler
          image: quay.io/coreos/hyperkube:v1.6.2_coreos.0
          command:
          - /hyperkube
          - scheduler
          - --master=http://127.0.0.1:8080
          - --leader-elect=true
          resources:
            requests:
              cpu: 100m
          livenessProbe:
            httpGet:
              host: 127.0.0.1
              path: /healthz
              port: 10251
            initialDelaySeconds: 15
            timeoutSeconds: 15
      
    • ในส่วนของ Calico จะใช้สำหรับทำ Network Policy เนื่องจากเป็น Optional จึงขอยังไม่ตั้งค่าสำหรับบริการนี้
    • ในกรณีที่ต้องการแจ้ง systemd ว่าเรามีการเปลี่ยนข้อมูลใน config และต้องการ rescan ทุกอย่างอีกครั้งให้สั่งดังนี้
      sudo systemctl daemon-reload
    • จากนั้นทดสอบ restart kubelet service ใหม่อีกครั้งและตรวจสอบ status หรือ journalctl -xe เพื่อดูว่าการทำงานปกติหรือไม่ ถ้าไม่แก้ให้ถูกต้องแล้ว restart ใหม่อีกครั้งไปเรื่อย ๆ จนกว่าจะปกติ
      sudo systemctl restart kubelet

      จบตอนแรกไปก่อนนะครับ ตอนต่อไปจะต่อด้วย worker node และ addon อื่น ๆ

    ==================================

    Reference :

    [1] [Kubernetes] Deploy Docker Container บน Google Container Engine : https://www.nomkhonwaan.com/2016/04/12/deploy-docker-container-on-google-container-engine

    [2] วิธีสร้าง CoreOS Cluster : https://sysadmin.psu.ac.th/2017/05/04/setup-coreos-cluster/

    [3] How to Deploy Kubernetes on CoreOS Cluster : https://www.upcloud.com/support/deploy-kubernetes-coreos/

    [4] CoreOS -> Cluster TLS using OpenSSL : https://coreos.com/kubernetes/docs/latest/openssl.html

    [5] CoreOS -> CoreOS + Kubernetes Step By Step : https://coreos.com/kubernetes/docs/latest/getting-started.html

    [6] CoreOS -> Tectonic, Kubernetes cluster orchestrator with enterprise integration  : https://coreos.com/tectonic/docs/latest/

     

  • อยากรู้ว่า Windows 10 Firewall Inbound Rules เปิดหรือปิด SMBv1, SMBv2 หรือไม่

    อยากรู้ว่า Windows 10 Firewall Inbound Rules เปิดหรือปิด SMBv1, SMBv2 หรือไม่

    ทดสอบจากเครื่อง Linux ที่ตั้งอยู่ใน network เดียวกัน ทำ nmap ค้นหา SMB (TCP Port 445) ไปที่เครื่อง Windows IP 192.168.x.yy

     

    ครั้งที่ 1
    รายการ File and Printer Sharing (SMB-In) ใน Firewall Inbound Rules เมื่อตั้งค่า Enabled = No
    ผลลัพธ์
    $ nmap -A -T4 -Pn -p445 192.168.x.yy
    Starting Nmap 7.01 ( https://nmap.org ) at 2017-05-15 13:52 ICT
    Nmap scan report for 192.168.x.yy
    Host is up.
    PORT STATE SERVICE VERSION
    445/tcp filtered microsoft-ds
    Nmap done: 1 IP address (1 host up) scanned in 2.39 seconds

    ครั้งที่ 2
    รายการ File and Printer Sharing (SMB-In) ใน Firewall Inbound Rules เมื่อตั้งค่า Enabled = Yes
    ผลลัพธ์
    $ nmap -A -T4 -Pn -p445 192.168.x.yy
    Starting Nmap 7.01 ( https://nmap.org ) at 2017-05-15 13:55 ICT
    Nmap scan report for 192.168.x.yy
    Host is up (0.00048s latency).
    PORT STATE SERVICE VERSION
    445/tcp open microsoft-ds Microsoft Windows 10 microsoft-ds
    Service Info: OS: Windows 10; CPE: cpe:/o:microsoft:windows_10
    Host script results:
    | smb-security-mode:
    | account_used: guest
    | authentication_level: user
    | challenge_response: supported
    |_ message_signing: disabled (dangerous, but default)
    |_smbv2-enabled: Server supports SMBv2 protocol
    Nmap done: 1 IP address (1 host up) scanned in 47.82 seconds

    ครั้งที่ 3
    รายการ File and Printer Sharing (SMB-In) ใน Firewall Inbound Rules เมื่อตั้งค่า Enabled = Yes
    และ
    ได้ปิด SMBv1 ตามคำแนะนำ เรื่อง “วิธีปิด SMBv1 เพื่อป้องกันตัวเองจากมัลแวร์เรียกค่าไถ่ WannaCry (ทำเถอะ ไม่ถึง 5 นาที)” https://www.blognone.com/node/92410
    ผลลัพธ์
    $ nmap -A -T4 -Pn -p445 192.168.x.yy
    Starting Nmap 7.01 ( https://nmap.org ) at 2017-05-15 13:55 ICT
    Nmap scan report for 192.168.x.yy
    Host is up (0.00051s latency).
    PORT STATE SERVICE VERSION
    445/tcp open microsoft-ds?
    Host script results:
    |_smbv2-enabled: Server supports SMBv2 protocol
    Nmap done: 1 IP address (1 host up) scanned in 47.87 seconds
    จากผลลัพธ์ในครั้งที่ 3 จะมีเพียง SMBv2

    สรุปว่า รายการ File and Printer Sharing (SMB-In) ใน Windows 10 Firewall Inbound Rules นั้นหากตรวจดูพบว่าคอลัมน์ Enabled มีค่า No ก็คือ ไม่ได้อนุญาตการเข้าถึง

    ในตัวอย่างนี้ก็คือไม่อนุญาตการเข้าถึง SMB (TCP Port 445) ซึ่งเป็นช่องทางเข้าโจมตีจาก Ransomware ที่ชื่อ WannaCrypt (บางทีเรียกย่อ ๆ ว่า WannaCry)

  • TODO: สำหรับผู้ใช้ Microsoft Windows เพื่อป้องกัน Wana Decrypt0r Ransomware

    สิ่งที่ต้องทำ สำหรับ ผู้ใช้ Microsoft Windows

    และ สำหรับผู้ดูแลระบบของหน่วยงาน

    1. Backup หรือ สำรองข้อมูลสำคัญ ไว้ใน External Harddisk, USB Drive, Cloud Drive
    2. กรณี Windows Vista, Windows XP, Windows 8
      ให้ไปที่ Website นี้ เพื่อ Download ตัว Update ที่ตรงกับ Windows ของตน มาติดตั้ง (MS17-101 หรือ KB4012598)
      http://www.catalog.update.microsoft.com/Search.aspx?q=KB4012598
    3. กรณี Windows 7
      http://www.catalog.update.microsoft.com/search.aspx?q=4012212
    4. กรณี Windows 8.1
      http://catalog.update.microsoft.com/v7/site/search.aspx?q=4012213
    5. กรณี Windows 10
      Start > พิมพ์ Windows Update

    สำหรับคนที่ยังใช้ Windows XP ควรพิจารณา Upgrade มาเป็น Windows 10

    โดยติดตั้ง Microsoft Windows รุ่นล่าสุดของมหาวิทยาลัยสงขลานครินทร์

    (ต้องมี PSU Passport)ได้ที่
    https://licensing.psu.ac.th/windows-10-education-version-1703-updated-march-2017-microsoft-imagine/

     

    ขอให้โชคดี

     

  • มีโปรแกรมไวรัส “เรียกค่าไถ่” ระบาดทั่วโลก (Wana Decrypt0r)

    หากท่านใช้ Windows และ ได้รับ Email ที่มีไฟล์แนบ โปรดระมัดระวังอย่างที่สุด

    สรุปความสั้นๆ:

    1. มีโปรแกรมเรียกค่าไถ่ระบาดทั่วโลก: หากติดไวรัส ไฟล์ในเครื่องเช่น Word, Excel หรือ งานวิจัยของท่านจะถูกเข้ารหัส ทำให้เปิดไม่ได้อีกเลย จนกว่าจะยอมจ่ายเงินค่าไถ่ให้กับ Hacker
    2. กระทบต่อผู้ใช้งาน Microsoft Windows โดยเฉพาะอย่างยิ่ง เครื่องที่ใช้ Windows File Sharing (Drive I อะไรทำนองนั้น) ใช้ Windows เถื่อน โดนแน่ๆ เพราะจะไม่ได้รับการ Update จาก Microsoft ถ้าใช้ Windows ลิขสิทธิ์แต่ไม่เคย Update ก็น่าจะโดนได้ง่ายๆ ใช้ Windows XP น่ะเสี่ยงสุดๆ
    3. หากได้รับ Email และมี ไฟล์แนบ ให้ระมัดระวัง: ไม่ว่าจะมาจากคนที่รู้จักหรือไม่ก็ตาม ก่อนเปิดไฟล์ให้ดูดีๆ หากเปิดมาแล้วมันถามโน่นนี่เป็นภาษาที่ไม่เข้าใจ ให้ปรึกษานักคอมพิวเตอร์ใกล้ตัวท่าน
    4. หากโดนแล้ว ทำใจอย่างเดียว: อยากได้ไฟล์คืน จ่ายเงินสกุล BitCoin ซึ่งตอนนี้ แพงกว่าทองคำ และจ่ายไปแล้ว ก็ไม่รับประกันว่าจะได้ไฟล์คืน ดิ้นรนหาโปรแกรมแก้ ??? ระวังเจอไวรัสแฝง !!!
    5. AntiVirus ไม่ช่วยอะไร: เพราะไฟล์แนบไม่ใช่ Virus แต่ ถ้าเปิดโปรแกรมมา มันจะไป Download Virus จริงๆมาอีกที
    6. ป้องกันได้อย่างเดียวโดยการ Update Windows: ดังนั้น Windows เถื่อน, Windows โบราณ (XP เป็นต้น), Windows ขี้เกียจ (ไม่ยอม Update) เสี่ยงจะติดไวรัสนี้มากที่สุด

    [UPDATE] สิ่งที่ต้องทำสำหรับ Windows แต่ละรุ่น https://sysadmin.psu.ac.th/2017/05/15/todo-update-windows/

     

    รายละเอียดเชิงลึก

    https://www.techtalkthai.com/wana-decrypt0r-2-0-technical-note/

    ที่มาและภาพประกอบ:

    https://www.bleepingcomputer.com/news/security/wana-decryptor-wanacrypt0r-technical-nose-dive/