Contour 學習筆記(二):使用級聯功能實現藍綠部署和金絲雀發佈

上篇文章介紹了 Contour 分佈式架構的工做原理,順便簡單介紹了下 IngressRoute 的使用方式。本文將探討 IngressRoute 更高級的用法,其中級聯功能是重點。html

1. IngressRoute 大入門

上篇文章在 examples/example-workload 目錄下建立了一個示例應用,咱們來回顧一下它的 IngressRoute 配置:json

apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata: 
  labels:
    app: kuard
  name: kuard
  namespace: default
spec: 
  virtualhost:
    fqdn: kuard.local
  routes: 
    - match: /
      services: 
        - name: kuard
          port: 80
  • virtualhost : 該字段是 root IngressRoute,表示此域的頂級入口點。
  • fqdn : 該字段指定了完整的域名,能夠經過在 HTTP 請求頭中指定 Host: 字段來訪問該服務。

這是最簡單是使用方法,看起來沒什麼特別的,咱們來稍做修改一下:segmentfault

apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata: 
  labels:
    app: kuard
  name: kuard
  namespace: default
spec: 
  virtualhost:
    fqdn: kuard.local
  routes: 
    - match: /test
      services: 
        - name: kuard
          port: 80

match: / 改成 match: /test,而後從新應用新規則。這時若是你訪問 url kuard.local/test 是不通的,由於 kuard 服務自己並無 /test 這個路徑,咱們能夠強制將路徑重寫爲 /後端

apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata: 
  labels:
    app: kuard
  name: kuard
  namespace: default
spec: 
  virtualhost:
    fqdn: kuard.local
  routes: 
    - match: /test
      prefixRewrite: "/"
      services: 
        - name: kuard
          port: 80

從新 apply 以後,再次訪問 url kuard.local/test 就通了。api

這裏能夠和標準的 ingress 對象對比一下,IngressRoute 的優點在於它能夠分別對每一個路由設置 rewrite 規則,而 Nginx Ingress Controller 只能設置全局的 rewrite 規則,由於它用的是 annotations。雖然能夠經過其餘手段來實現,但相對來講會比較麻煩。bash

2. 級聯功能介紹

下面咱們來看看 IngressRoute 的級聯功能,這是個很是有特點的功能,你能夠經過級聯多個路由規則,上層 IngressRoute 的配置被下層繼承。例如,咱們能夠將 url 路徑 / 的路由規則級聯到其餘的 IngressRoute 中,其餘的 IngressRoute 能夠來自不一樣的 namespace。微信

舉個例子,咱們能夠先建立一個這樣的 IngressRoute:架構

$ cat > delegate-from-main.yaml <<EOF
apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata:
  name: delegate-from-main
spec:
  routes:
    - match: /
      services:
        - name: kuard
          port: 80
EOF
$ kubectl apply -f delegate-from-main.yaml

$ kubectl get ingressroute delegate-from-main -o jsonpath='{.status.currentStatus}'
orphaned

該 IngressRoute 的狀態爲 orphaned,由於它沒有包含一個合法的 fqdn。接下來須要建立一個 root IngressRoute 來和它進行級聯:app

apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata: 
  labels:
    app: kuard
  name: kuard
  namespace: default
spec: 
  virtualhost:
    fqdn: kuard.local
  routes: 
    - match: /
      delegate:
        name: delegate-from-main
        namespace: default

這時若是再檢查 IngressRoute delegate-from-main 的狀態,就會發現它從 orphaned 狀態變成了 valid 狀態,kuard.local 也可以順利訪問。分佈式

瞭解了級聯功能的用法以後,下面就來看看它的應用場景。

  • 場景一:可使用級聯功能來作藍綠部署和灰度發佈,只須要在上層 IngressRoute 中稍做修改,切換到另外一個下層 IngressRoute,就能夠切換流量的處理規則。
  • 場景二:管理員能夠利用級聯功能將部分 ingress 的權限放行到其餘的 namespace 中,在這些 namespace 中,用戶能夠自由更新與 root IngressRoute 級聯的相關的 IngressRoute。例如,若是管理員想防止其餘用戶配置非法的域名或路徑,能夠將該部分的配置權限放到 root IngressRoute 中,其餘 namespace 中的下層 IngressRoute 中只能配置各自的路徑相關信息。

接下來主要探討場景一。

3. 藍綠部署

藍綠部署簡單來說就是在生產環境中有兩套系統:一套是正在提供服務的系統,標記爲「綠色」;另外一套是準備發佈的系統,標記爲「藍色」。兩套系統都是功能完善的,而且正在運行的系統,只是系統版本和對外服務狀況不一樣。

最初,沒有任何系統,沒有藍綠之分。

而後,第一套系統開發完成,直接上線,這個過程只有一個系統,也沒有藍綠之分。

後來,開發了新版本,要用新版本替換線上的舊版本,在線上的系統以外,搭建了一個使用新版本代碼的全新系統。 這時候,一共有兩套系統在運行,正在對外提供服務的老系統是綠色系統,新部署的系統是藍色系統。

藍色系統不對外提供服務,用來作啥?

用來作發佈前測試,測試過程當中發現任何問題,能夠直接在藍色系統上修改,不干擾用戶正在使用的系統。(注意,兩套系統沒有耦合的時候才能百分百保證不干擾)

藍色系統通過反覆的測試、修改、驗證,肯定達到上線標準以後,直接將用戶切換到藍色系統:

切換後的一段時間內,依舊是藍綠兩套系統並存,可是用戶訪問的已是藍色系統。這段時間內觀察藍色系統(新系統)工做狀態,若是出現問題,直接切換回綠色系統。

當確信對外提供服務的藍色系統工做正常,不對外提供服務的綠色系統已經再也不須要的時候,藍色系統正式成爲對外提供服務系統,成爲新的綠色系統。 原先的綠色系統能夠銷燬,將資源釋放出來,用於部署下一個藍色系統。

經過 IngressRoute 的級聯功能能夠很方便地實現藍綠部署策略,首先建立一個上層的 root IngressRoute(假設名爲 root-blog),而後將域名 yangcs.net/blogs 的路由策略級聯到下層的 IngressRoute(名爲 blog)。咱們會同時部署」藍色「版本和」綠色「版本的應用,此時只有」綠色「版本接收流量。

---
apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata:
  name: root-blog
  namespace: root-ingressroute
spec:
  virtualhost:
    fqdn: yangcs.net
    tls:
      secretName: yangcs-net
  routes:
    - match: /blog
      delegate:
        name: blog
        namespace: marketing
---
apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata:
  name: blog
  namespace: marketing
spec:
  routes:
    - match: /blog
      services:
        - name: green
          port: 80

---
apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata:
  name: blog2
  namespace: marketing
spec:
  routes:
    - match: /blog
      services:
        - name: blue
          port: 80

在對藍色版本進行測試驗證以後,就能夠將用戶切換到藍色應用了:

apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata:
  name: root-blog
  namespace: root-ingressroute
spec:
  virtualhost:
    fqdn: yangcs.net
    tls:
      secretName: yangcs-net
  routes:
    - match: /blog
      delegate:
        name: blog2
        namespace: marketing

4. 金絲雀發佈

金絲雀發佈(Canary)也是一種發佈策略,和國內常說的灰度發佈是同一類策略。它和藍綠有點像,可是它更加規避風險。你能夠階段性的進行,而不用一次性從藍色版本切換到綠色版本。

採用金絲雀部署,你能夠在生產環境的基礎設施中小範圍的部署新的應用代碼。一旦應用簽署發佈,只有少數用戶被路由到它,能夠最大限度的下降影響。

若是沒有錯誤發生,把剩餘的 V1 版本所有升級爲 V2 版本。若是有錯誤發生,則直接回退到老版本,發佈失敗。下圖示範了金絲雀部署:

其實金絲雀發佈的名稱來源於一個典故。在 17 世紀,英國礦井工人發現,金絲雀對瓦斯這種氣體特別敏感,空氣中哪怕有極其微量的瓦斯,金絲雀也會中止唱歌。當瓦斯含量超過必定限度時,人類毫無察覺,但金絲雀卻會毒發身亡。當時在採礦設備相對簡陋的條件下,工人們每次下井都會帶上一隻金絲雀做爲」瓦斯檢測指標「,以便在危險狀況下緊急撤離。映射到這裏就是先發布一小部分來試探總體是否可以正常運行,若是能正常運行則進行徹底部署的發佈方式,目前仍然是很多成長型技術組織的主流發佈方式。

IngressRoute 能夠經過分配權重來實現金絲雀發佈,和藍綠部署同樣,首先建立一個上層的 root IngressRoute(名爲 root-blog),而後將域名 yangcs.net/blogs 的路由策略級聯到下層的 IngressRoute(名爲 blog)。在下層的 IngressRoute 中將流量按不一樣權重轉發到不一樣的後端服務。

apiVersion: contour.heptio.com/v1beta1
kind: IngressRoute
metadata:
  name: blog
  namespace: marketing
spec:
  routes:
    - match: /blog
      services:
        - name: green
          port: 5
        - name: blue
          port: 95

若是沒有錯誤發生,就將 green 的權重調整爲 100,blue 的權重調整爲 0。至此就完成了金絲雀發佈。

本文主要介紹了 IngressRoute 級聯功能的用法,探討了如何使用級聯功能來實現藍綠部署和金絲雀發佈,後面的文章將會陸續探討其餘的流量治理功能。

5. 參考資料

微信公衆號

掃一掃下面的二維碼關注微信公衆號,在公衆號中回覆◉加羣◉便可加入咱們的雲原生交流羣,和孫宏亮、張館長、陽明等大佬一塊兒探討雲原生技術

相關文章
相關標籤/搜索