iT邦幫忙

2021 iThome 鐵人賽

DAY 8
0
DevOps

前端工程師學習 DevOps 之路系列 第 8

Day08-Kubernetes 那些事 -Service 篇

前言

在前面的文章講完了 Pod 後接下來就要講講如何正確的連接到 Pod ,其實連接到 Pod 有兩種方式,一種是建立 Service 另一種是用 port-forward ,接下來的文章就來好好談談這兩種方法吧!

port-forward

port-forward 簡單來說就是把 host 上的某個 port 連線至 Pod 的對外 port ,就好像我們在用 Docker 跑一個 container 的時候會下 -P 這個參數來連結機器與 container 的 port 一樣,只是這邊是連到 Pod 而已。

方法也很簡單只要在終端機下 kubectl port-forward helloworld NodePort:PodPort 即可。

這時候在瀏覽器就可以打上 http://localhost:8080 來看到內容了。

相信大家也知道這種做法有個缺點就是每次建立 Pod 還要自己手動打指令去連結 port 真的太搞剛了,而且久了也會忘記到底機器上哪個 port 有用到,因此這邊筆者要推薦另一個做法來取代 port-forward 也就是 Service。

什麼是 Service?

service 的存在就是建立一個網路連線通道讓應用程式可以正確地連結到正在運行的 Pods,而 Service 一共有 4 種表現形式,接下來就細談一下這 4 種形式的差異吧!

  • ClusterIP

    預設值,代表這個 Service 只能在相同的 Cluster 內使用,無法讓外部使用。

  • NodePort

    簡單來說就是外部可以連到內部使用了,假如機器上本身有其他服務,例如:Nginx 之類的服務,然後還架一個 K8s 的 cluster 出來,這時候 K8s cluster 內的 service 就可以利用 NodePort 讓機器上其他服務也可以使用。

  • ExternalName

    主要是為了讓不同 namespace 中的以 ClusterIP 形式生成的 Service 可以利用 ExternalName 設定的外部名稱,藉以連到指定的 namespace 中的 Service,由於筆者目前還沒有提到 namespace 所以讀者們稍微有一個印象就好,後續的文章會再加以闡述 namespace。

  • LoadBalancer

    這個屬性是強化版的 NodePort ,除了擁有 NodePort 可以讓外部連線的優點,同時也建立了負載平衡的機制來分散流量,但很可惜 LoadBalancer 目前只有雲端服務,如:GCP、AWS 等等有支援而已,minikube 目前暫不支援所以想在本地端試試看的讀者可能就沒辦法嘗試使用這個形式了。


加了 Service 後目前 K8s 的流程圖就會長這樣,雖然有點簡陋但應該不算難懂XD

Service 寫法

接下來就用一個簡單的範例來講一下 Service 的寫法吧!

apiVersion: v1
kind: Service
metadata:
  name: helloworld
  labels:
    app: frontend
    environment: develop
spec:
  type: NodePort
  ports:
    - protocol: TCP
      port: 8080
      targetPort: 8080
      nodePort: 32700
  selector:
    app: frontend

基本上寫法就跟 Pod 差不多,唯一不同的地方就在 spec 的細部設定,因此底下就來講講 spec 的相關設定吧!

  • type

    用來決定這個 Service 要以什麼形式建立, type 後面的值接的就是上面文章提到的 4 種形式。

  • ports

    用來決定該 Service 要連接哪些 port ,這邊有一些細部的設定分別來闡述一下。

    • protocol: 用來決定連線的網路協議,預設值為 TCP ,當然也可以使用 UDP。

    • port: 建立好的 Service 要以哪個 port 連接到 Pod 上。

    • targetPort: 指的是目標 Pod 的 port ,通常 port 跟 targetPort 會設定一樣。

    • nodePort: 指的是機器上的 Port 要對應到該 Service 上,這個設定要 nodePort 形式的 Service 才有效果,假如今天沒有設定 nodePort 的話,K8s 就會自動開一個機器上的 port 去對應到該 Service ,這邊有個小提醒,nodePort 的範圍在 30000–32767 之間,不在這範圍內的 port 都是不允許的。

  • selectors

    還記得上一篇文章提到的 Label 嗎?今天 Service 想要連接到正確的 Pod 就必須要利用 selectors 了,這邊只要原封不動的把 Pod 的 Label 複製上去即可。

建立 Service

跟 Pod 一樣都需要用 apply 這個參數來建立 Service 的描述檔。

剛剛上面的 port-forward 是利用跟本機端的 port 連動,所以可以用 localhost 的方式連接到 Pod ,由於這裡已經歸 K8s 管了,因此我們必須要用 minikube 的虛擬機器 IP 才可以連到,這邊可以下 minikube ip 來取得虛擬機器 IP。

接下來我們就可以透過剛剛設定好的 Service nodePort 來連接到 Pod 了,由於一開始有先在 Service 描述檔上寫上 nodePort: 32700 ,因此我們就可以利用機器上的 32700 port 來連接到 Service 的 8080 port。

看到這邊貌似很完美,但相信讀者們一定會發現一件事,這個 port 真的太醜了,有沒有辦法讓我們用 http 的預設 80 port 來連接呢?其實是可以的而這個方法會在下一篇文章告訴大家。

小結

今天介紹了 Service 這個用來連接 Pod 的網路連線通道,相信大家應該都更了解要如何跟 K8s 內的 Pod 進行溝通,但其實我們還差一步就可以讓使用者有更好的連線方式可以連接。

如果對於文章有任何問題歡迎留言給我,接下來筆者要介紹 Ingress ,那我們就下篇文章見嘍~


上一篇
Day07-Kubernetes 那些事 -Label 篇
下一篇
Day09-Kubernetes那些事 - Ingress 篇(一)
系列文
前端工程師學習 DevOps 之路30

尚未有邦友留言

立即登入留言