1. 程式人生 > 實用技巧 >istio(4):istio-流量管理-基於請求內容的訪問規則控制

istio(4):istio-流量管理-基於請求內容的訪問規則控制

istio(4):istio-流量管理-基於請求內容的訪問規則控制

將建立的 VirtualService 物件刪除

[root@k8s-master istio-1.3.1]# kubectl get virtualservices.networking.istio.io
NAME       GATEWAYS             HOSTS       AGE
bookinfo   [bookinfo-gateway]   [*]         2d23h
reviews                         [reviews]   3s
[root@k8s-master istio-1.3.1]# istioctl delete virtualservice reviews
Command "delete" is deprecated, Use `kubectl delete` instead (see https://kubernetes.io/docs/tasks/tools/install-kubectl)
Deleted config: virtualservice reviews
[root@k8s-master istio-1.3.1]# kubectl get virtualservices.networking.istio.io
NAME       GATEWAYS             HOSTS   AGE
bookinfo   [bookinfo-gateway]   [*]     2d23h
[root@k8s-master istio-1.3.1]#

檢視檔案 samples/bookinfo/networking/virtual-service-reviews-jason-v2-v3.yaml 的定義:

# cat  samples/bookinfo/networking/virtual-service-reviews-jason-v2-v3.yaml
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
  name: reviews
spec:
  hosts:
  - reviews
  http:
  - match:
    - headers:
        end-user:
          exact: jason
    route:
    - destination:
        host: reviews
        subset: v2
  - route:
    - destination:
        host: reviews
        subset: v3

這個 VirtualService 物件定義了對 reviews 服務訪問的 match 規則。意思是如果當前請求的 header 中包含 jason 這個使用者資訊,則只會訪問到 v2 的 reviews 這個服務版本,即都帶星的樣式,如果不包含該使用者資訊,則都直接將流量轉發給 v3 這個 reviews 的服務。

我們先不啟用這個 VirtualService,現在我們去訪問下 Bookinfo 這個應用:

右上角有登入按鈕,在沒有登入的情況下重新整理頁面,reviews 服務是被隨機訪問的,可以看到有帶星不帶星的樣式,點選登入,在彈窗中 User Name 輸入 jason,Password為空,登入:

再重新整理頁面,可以看到跟未登入前的訪問規則一樣,也是隨機的。

現在我們來建立上面的 VirtualService 這個物件:

[root@k8s-master istio-1.3.1]# kubectl create -f samples/bookinfo/networking/virtual-service-reviews-jason-v2-v3.yaml
The VirtualService "reviews" is invalid: []: Invalid value: map[string]interface {}{"apiVersion":"networking.istio.io/v1alpha3", "kind":"VirtualService", "metadata":map[string]interface {}{"creationTimestamp":"2019-11-11T03:13:57Z", "generation":1, "name":"reviews", "namespace":"default", "uid":"a221c753-d9b3-481c-8dff-a8810d0f2d45"}, "spec":map[string]interface {}{"hosts":[]interface {}{"reviews"}, "http":[]interface {}{map[string]interface {}{"match":[]interface {}{map[string]interface {}{"headers":map[string]interface {}{"end-user":map[string]interface {}{"exact":"jason"}}}}, "route":[]interface {}{map[string]interface {}{"destination":map[string]interface {}{"host":"reviews", "subset":"v2"}}}}, map[string]interface {}{"route":[]interface {}{map[string]interface {}{"destination":map[string]interface {}{"host":"reviews", "subset":"v3"}}}}}}}: validation failure list:
spec.http.route.weight in body is required
[root@k8s-master istio-1.3.1]# vim samples/bookinfo/networking/virtual-service-reviews-jason-v2-v3.yaml
[root@k8s-master istio-1.3.1]# vim samples/bookinfo/networking/virtual-service-reviews-jason-v2-v3.yaml
[root@k8s-master istio-1.3.1]# kubectl create -f samples/bookinfo/networking/virtual-service-reviews-jason-v2-v3.yaml
virtualservice.networking.istio.io/reviews created

修改一下

[root@k8s-master istio-1.3.1]# cat  samples/bookinfo/networking/virtual-service-reviews-jason-v2-v3.yaml
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
  name: reviews
spec:
  hosts:
  - reviews
  http:
  - match:
    - headers:
        end-user:
          exact: jason
    route:
    - destination:
        host: reviews
        subset: v2
      weight: 1
  - route:
    - destination:
        host: reviews
        subset: v3
      weight: 1

# istioctl get virtualservice
Command "get" is deprecated, Use `kubectl get` instead (see https://kubernetes.io/docs/tasks/tools/install-kubectl)
VIRTUAL-SERVICE NAME   GATEWAYS           HOSTS     #HTTP     #TCP      NAMESPACE   AGE
bookinfo               bookinfo-gateway   *             1        0      default     2d
reviews                                   reviews       2        0      default     42s

此時再回去重新整理頁面,發現一直都是黑星的 Reviews 版本(v2)被訪問到了。 登出退出後再訪問,此時又一直是紅色星的版本(v3)被訪問了。

說明我們基於 headers->end-user->exact:jason 的控制規則生效了。在 productpage 服務呼叫 reviews 服務時,登入的情況下會在 header 中帶上使用者資訊,通過 exact 規則匹配到相關資訊後,流量被引向了上面配置的v2版本中。

這裡要說明一下match的匹配規則:

1 All conditions inside a single match block have AND semantics,whilethe list of match blocks have OR semantics. The rule is matchedifany one of the match blocks succeed.

- match:
    - uri:
        prefix: "/wpcatalog"
      port: 444

多個 match 塊之間是隻要有一個 match 匹配成功了,就會走向它指定的服務版本去,而忽略其他的。我們的示例中在登入的條件下,滿足第一個 match,所以服務一直會訪問到 v2 版本。退出登入後,沒有 match 規則滿足匹配,會走向最後一個 route 規則,即 v3 版本。