1. <strong id="7actg"></strong>
    2. <table id="7actg"></table>

    3. <address id="7actg"></address>
      <address id="7actg"></address>
      1. <object id="7actg"><tt id="7actg"></tt></object>

        在 Traefik 中使用 Kubernetes Gateway API

        共 9613字,需瀏覽 20分鐘

         ·

        2022-01-10 22:16

        Gateway API(之前叫 Service API)是由 SIG-NETWORK 社區(qū)管理的開(kāi)源項(xiàng)目,項(xiàng)目地址:https://gateway-api.sigs.k8s.io/。主要原因是 Ingress 資源對(duì)象不能很好的滿(mǎn)足網(wǎng)絡(luò)需求,很多場(chǎng)景下 Ingress 控制器都需要通過(guò)定義 annotations 或者 crd 來(lái)進(jìn)行功能擴(kuò)展,這對(duì)于使用標(biāo)準(zhǔn)和支持是非常不利的,新推出的 Gateway API 旨在通過(guò)可擴(kuò)展的面向角色的接口來(lái)增強(qiáng)服務(wù)網(wǎng)絡(luò)。

        Gateway API 是 Kubernetes 中的一個(gè) API 資源集合,包括 GatewayClass、Gateway、HTTPRoute、TCPRoute、Service 等,這些資源共同為各種網(wǎng)絡(luò)用例構(gòu)建模型。

        Gateway API 的改進(jìn)比當(dāng)前的 Ingress 資源對(duì)象有很多更好的設(shè)計(jì):

        • 面向角色 - Gateway 由各種 API 資源組成,這些資源根據(jù)使用和配置 Kubernetes 服務(wù)網(wǎng)絡(luò)的角色進(jìn)行建模。
        • 通用性 - 和 Ingress 一樣是一個(gè)具有眾多實(shí)現(xiàn)的通用規(guī)范,Gateway API 是一個(gè)被設(shè)計(jì)成由許多實(shí)現(xiàn)支持的規(guī)范標(biāo)準(zhǔn)。
        • 更具表現(xiàn)力 - Gateway API 資源支持基于 Header 頭的匹配、流量權(quán)重等核心功能,這些功能在 Ingress 中只能通過(guò)自定義注解才能實(shí)現(xiàn)。
        • 可擴(kuò)展性 - Gateway API 允許自定義資源鏈接到 API 的各個(gè)層,這就允許在 API 結(jié)構(gòu)的適當(dāng)位置進(jìn)行更精細(xì)的定制。

        還有一些其他值得關(guān)注的功能:

        • GatewayClasses - GatewayClasses 將負(fù)載均衡實(shí)現(xiàn)的類(lèi)型形式化,這些類(lèi)使用戶(hù)可以很容易了解到通過(guò) Kubernetes 資源可以獲得什么樣的能力。
        • 共享網(wǎng)關(guān)和跨命名空間支持 - 它們?cè)试S共享負(fù)載均衡器和 VIP,允許獨(dú)立的路由資源綁定到同一個(gè)網(wǎng)關(guān),這使得團(tuán)隊(duì)可以安全地共享(包括跨命名空間)基礎(chǔ)設(shè)施,而不需要直接協(xié)調(diào)。
        • 規(guī)范化路由和后端 - Gateway API 支持類(lèi)型化的路由資源和不同類(lèi)型的后端,這使得 API 可以靈活地支持各種協(xié)議(如 HTTP 和 gRPC)和各種后端服務(wù)(如 Kubernetes Service、存儲(chǔ)桶或函數(shù))。

        面向角色設(shè)計(jì)

        無(wú)論是道路、電力、數(shù)據(jù)中心還是 Kubernetes 集群,基礎(chǔ)設(shè)施都是為了共享而建的,然而共享基礎(chǔ)設(shè)施提供了一個(gè)共同的挑戰(zhàn),那就是如何為基礎(chǔ)設(shè)施用戶(hù)提供靈活性的同時(shí)還能被所有者控制。

        Gateway API 通過(guò)對(duì) Kubernetes 服務(wù)網(wǎng)絡(luò)進(jìn)行面向角色的設(shè)計(jì)來(lái)實(shí)現(xiàn)這一目標(biāo),平衡了靈活性和集中控制。它允許共享的網(wǎng)絡(luò)基礎(chǔ)設(shè)施(硬件負(fù)載均衡器、云網(wǎng)絡(luò)、集群托管的代理等)被許多不同的團(tuán)隊(duì)使用,所有這些都受到集群運(yùn)維設(shè)置的各種策略和約束。下面的例子顯示了是如何在實(shí)踐中運(yùn)行的。

        一個(gè)集群運(yùn)維人員創(chuàng)建了一個(gè)基于 GatewayClass 的 Gateway 資源,這個(gè) Gateway 部署或配置了它所代表的基礎(chǔ)網(wǎng)絡(luò)資源,集群運(yùn)維和特定的團(tuán)隊(duì)必須溝通什么可以附加到這個(gè) Gateway 上來(lái)暴露他們的應(yīng)用。集中的策略,如 TLS,可以由集群運(yùn)維在 Gateway 上強(qiáng)制執(zhí)行,同時(shí),Store 和 Site 應(yīng)用在他們自己的命名空間中運(yùn)行,但將他們的路由附加到相同的共享網(wǎng)關(guān)上,允許他們獨(dú)立控制他們的路由邏輯。

        這種關(guān)注點(diǎn)分離的設(shè)計(jì)可以使不同的團(tuán)隊(duì)能夠管理他們自己的流量,同時(shí)將集中的策略和控制留給集群運(yùn)維。

        概念

        在整個(gè) Gateway API 中涉及到3個(gè)角色:基礎(chǔ)設(shè)施提供商、集群管理員、應(yīng)用開(kāi)發(fā)人員,在某些場(chǎng)景下可能還會(huì)涉及到應(yīng)用管理員等角色。Gateway API 中定義了3種主要的資源模型:GatewayClass、GatewayRoute。

        GatewayClass

        GatewayClass 定義了一組共享相同配置和動(dòng)作的網(wǎng)關(guān)。每個(gè)GatewayClass 由一個(gè)控制器處理,是一個(gè)集群范圍的資源,必須至少有一個(gè) GatewayClass 被定義。

        這與 Ingress 的 IngressClass 類(lèi)似,在 Ingress v1beta1 版本中,與 GatewayClass 類(lèi)似的是 ingress-class 注解,而在Ingress V1 版本中,最接近的就是 IngressClass 資源對(duì)象。

        Gateway

        Gateway 網(wǎng)關(guān)描述了如何將流量轉(zhuǎn)化為集群內(nèi)的服務(wù),也就是說(shuō),它定義了一個(gè)請(qǐng)求,要求將流量從不了解 Kubernetes 的地方轉(zhuǎn)換到集群內(nèi)的服務(wù)。例如,由云端負(fù)載均衡器、集群內(nèi)代理或外部硬件負(fù)載均衡器發(fā)送到 Kubernetes 服務(wù)的流量。

        它定義了對(duì)特定負(fù)載均衡器配置的請(qǐng)求,該配置實(shí)現(xiàn)了 GatewayClass 的配置和行為規(guī)范,該資源可以由管理員直接創(chuàng)建,也可以由處理 GatewayClass 的控制器創(chuàng)建。

        Gateway 可以附加到一個(gè)或多個(gè)路由引用上,這些路由引用的作用是將流量的一個(gè)子集導(dǎo)向特定的服務(wù)。

        Route 資源

        路由資源定義了特定的規(guī)則,用于將請(qǐng)求從網(wǎng)關(guān)映射到 Kubernetes 服務(wù)。

        v1alpha2 版本開(kāi)始,API 中包含四種 Route 路由資源類(lèi)型,對(duì)于其他未定義的協(xié)議,鼓勵(lì)采用特定實(shí)現(xiàn)的自定義路由類(lèi)型,當(dāng)然未來(lái)也可能會(huì)添加新的路由類(lèi)型。

        HTTPRoute

        HTTPRoute?適用于 HTTP 或 HTTPS 連接,適用于我們想要檢查 HTTP 請(qǐng)求并使用 HTTP 請(qǐng)求進(jìn)行路由或修改的場(chǎng)景,比如使用 HTTP Headers 頭進(jìn)行路由,或在請(qǐng)求過(guò)程中對(duì)它們進(jìn)行修改。

        TLSRoute

        TLSRoute 用于 TLS 連接,通過(guò) SNI 進(jìn)行區(qū)分,它適用于希望使用 SNI 作為主要路由方法的地方,并且對(duì) HTTP 等更高級(jí)別協(xié)議的屬性不感興趣,連接的字節(jié)流不經(jīng)任何檢查就被代理到后端。

        TCPRoute 和 UDPRoute

        TCPRoute(和UDPRoute)旨在用于將一個(gè)或多個(gè)端口映射到單個(gè)后端。在這種情況下,沒(méi)有可以用來(lái)選擇同一端口的不同后端的判別器,所以每個(gè) TCPRoute 在監(jiān)聽(tīng)器上需要一個(gè)不同的端口。你可以使用 TLS,在這種情況下,未加密的字節(jié)流會(huì)被傳遞到后端,當(dāng)然也可以不使用 TLS,這樣加密的字節(jié)流將傳遞到后端。

        組合

        GatewayClass、Gateway、xRouteService 的組合定義了一個(gè)可實(shí)施的負(fù)載均衡器。下圖說(shuō)明了不同資源之間的關(guān)系:

        使用反向代理實(shí)現(xiàn)的網(wǎng)關(guān)的典型客戶(hù)端/網(wǎng)關(guān) API 請(qǐng)求流程如下所示:

        • 1. 客戶(hù)端向 http://foo.example.com 發(fā)出請(qǐng)求
        • 2. DNS 將域名解析為 Gateway 網(wǎng)關(guān)地址
        • 3. 反向代理在監(jiān)聽(tīng)器上接收請(qǐng)求,并使用 Host Header 來(lái)匹配HTTPRoute
        • 4. (可選)反向代理可以根據(jù) HTTPRoute 的匹配規(guī)則進(jìn)行路由
        • 5. (可選)反向代理可以根據(jù) HTTPRoute 的過(guò)濾規(guī)則修改請(qǐng)求,即添加或刪除 headers
        • 6. 最后,反向代理根據(jù) HTTPRoute 的 forwardTo 規(guī)則,將請(qǐng)求轉(zhuǎn)發(fā)給集群中的一個(gè)或多個(gè)對(duì)象,即服務(wù)。

        實(shí)現(xiàn)

        目前已經(jīng)有很多 Gateway API 的控制器實(shí)現(xiàn)方案了,比如 Contour、Google Kubernetes Engine、Istio、Traefik 等等。接下來(lái)我們以 Traefik 為例來(lái)進(jìn)行測(cè)試。不過(guò)需要注意的是 Traefik 目前是基于 v1alpha1 規(guī)范實(shí)現(xiàn)的,可能和上面提到的一些概念略有不同。

        要在 Traefik 中使用 Gateway API,首先我們需要先手動(dòng)安裝 Gateway API 的 CRDs,使用如下命令即可安裝,這將安裝包括 GatewayClass、Gateway、HTTPRoute、TCPRoute 等 CRDs:

        ??kubectl?kustomize?"github.com/kubernetes-sigs/gateway-api/config/crd?ref=v0.3.0"?\
        |?kubectl?apply?-f?-

        然后我們需要在 Traefik 中開(kāi)啟 kubernetesgateway 這個(gè) Provider,同樣基于前面 Traefik 章節(jié)中的 Helm Chart 包進(jìn)行定義,設(shè)置 experimental.kubernetesGateway.enabled=true,完整的 Values 文件如下所示:

        #?ci/deployment-prod.yaml

        #?Enable?experimental?features
        experimental:
        ??kubernetesGateway:??#?開(kāi)啟?gateway?api?支持
        ????enabled:?true

        providers:
        ??kubernetesCRD:
        ????enabled:?true
        ????allowCrossNamespace:?true??#?是否允許跨命名空間
        ????allowExternalNameServices:?true??#?是否允許使用?ExternalName?的服務(wù)

        ??kubernetesIngress:
        ????enabled:?true
        ????allowExternalNameServices:?true

        #?......
        #?其他忽略

        然后使用下面的命令更新 Traefik 即可:

        ??helm?upgrade?--install?traefik?./traefik?-f?./traefik/ci/deployment-prod.yaml?--namespace?kube-system

        更新完成后可以前往 Traefik 的 Dashboard 查看是否已經(jīng)啟用 KubernetesGateway 這個(gè) Provider:

        正常情況下啟用成功后 Traefik 也會(huì)創(chuàng)建一個(gè)默認(rèn)的 GatewayClass 資源對(duì)象和 Gateway 實(shí)例:

        ??kubectl?get?gatewayclass
        NAME??????CONTROLLER??????????????????????AGE
        traefik???traefik.io/gateway-controller???4m13s
        ??kubectl?get?gatewayclass?traefik?-o?yaml
        apiVersion:?networking.x-k8s.io/v1alpha1
        kind:?GatewayClass
        metadata:
        ??name:?traefik
        spec:
        ??controller:?traefik.io/gateway-controller
        ......
        ??kubectl?get?gateway?-n?kube-system
        NAME??????????????CLASS?????AGE
        traefik-gateway???traefik???5m55s
        ??kubectl?get?gateway?-n?kube-system?traefik-gateway?-o?yaml
        apiVersion:?networking.x-k8s.io/v1alpha1
        kind:?Gateway
        metadata:
        ??name:?traefik-gateway
        ??namespace:?kube-system
        spec:
        ??gatewayClassName:?traefik
        ??listeners:
        ??-?port:?8000
        ????protocol:?HTTP
        ????routes:
        ??????group:?networking.x-k8s.io
        ??????kind:?HTTPRoute
        ??????namespaces:
        ????????from:?Same
        ??????selector:
        ????????matchLabels:
        ??????????app:?traefik
        ......

        可以看到默認(rèn)創(chuàng)建的 Gateway 實(shí)例引用了 traefik 這個(gè) GatewayClass,其中 listeners 部分定義了該網(wǎng)關(guān)關(guān)聯(lián)的監(jiān)聽(tīng)器入口,監(jiān)聽(tīng)器定義邏輯端點(diǎn)綁定在該網(wǎng)關(guān)地址上,至少需要指定一個(gè)監(jiān)聽(tīng)器,下面的 HTTPRoute 定義了路由規(guī)則,namespaces 表示應(yīng)該在哪些命名空間中為該網(wǎng)關(guān)選擇路由,默認(rèn)情況下,這被限制在該網(wǎng)關(guān)的命名空間中,Selector 則指定一組路由標(biāo)簽,如果定義了這個(gè) Selector,則只路由匹配選擇器與網(wǎng)關(guān)相關(guān)聯(lián)的對(duì)象,一個(gè)空的選擇器匹配所有對(duì)象,這里會(huì)去匹配具有 app: traefik 標(biāo)簽的對(duì)象。

        為了能夠處理其他命名空間中的路由規(guī)則,我們可以將這里的 namespaces.from 修改為 All,但是經(jīng)測(cè)試未生效?

        下面我們安裝一個(gè)簡(jiǎn)單的 whoami 服務(wù)來(lái)進(jìn)行測(cè)試,直接使用下面的資源清單部署對(duì)應(yīng)的服務(wù)即可:

        #?01-whoami.yaml
        ---
        kind:?Deployment
        apiVersion:?apps/v1
        metadata:
        ??name:?whoami
        ??namespace:?kube-system
        spec:
        ??replicas:?2
        ??selector:
        ????matchLabels:
        ??????app:?whoami
        ??template:
        ????metadata:
        ??????labels:
        ????????app:?whoami
        ????spec:
        ??????containers:
        ????????-?name:?whoami
        ??????????image:?containous/whoami
        ??????????ports:
        ????????????-?containerPort:?80
        ??????????????name:?http
        ---
        apiVersion:?v1
        kind:?Service
        metadata:
        ??name:?whoami
        ??namespace:?kube-system
        spec:
        ??ports:
        ????-?protocol:?TCP
        ??????port:?80
        ??????targetPort:?http
        ??selector:
        ????app:?whoami

        測(cè)試服務(wù)部署完成后,我們就可以使用 Gateway API 的方式來(lái)進(jìn)行流量配置了。

        部署一個(gè)簡(jiǎn)單的 Host 主機(jī)

        在以前的方式中我們會(huì)創(chuàng)建一個(gè) Ingress 或 IngressRoute 資源對(duì)象,這里我們將部署一個(gè)簡(jiǎn)單的 HTTPRoute 對(duì)象。

        #?02-whoami-httproute.yaml
        apiVersion:?networking.x-k8s.io/v1alpha1
        kind:?HTTPRoute
        metadata:
        ??name:?http-app-1
        ??namespace:?kube-system
        ??labels:
        ????app:?traefik
        spec:
        ??hostnames:
        ????-?"whoami"
        ??rules:
        ????-?matches:
        ????????-?path:
        ????????????type:?Exact
        ????????????value:?/
        ??????forwardTo:
        ????????-?serviceName:?whoami
        ??????????port:?80
        ??????????weight:?1

        上面的 HTTPRoute 資源會(huì)捕捉到向 whoami 主機(jī)名發(fā)出的請(qǐng)求,并將其轉(zhuǎn)發(fā)到上面部署的 whoami 服務(wù),如果你現(xiàn)在對(duì)這個(gè)主機(jī)名進(jìn)行請(qǐng)求,你會(huì)看到典型的 whoami 輸出:

        ??kubectl?apply?-f?02-whoami-httproute.yaml
        ??kubectl?get?httproute?-n?kube-system
        NAME?????????HOSTNAMES????AGE
        http-app-1???["whoami"]???25s
        #?使用?whoami?這個(gè)主機(jī)名進(jìn)行訪(fǎng)問(wèn)測(cè)試
        ??curl?-H?"Host:?whoami"?http://192.168.31.108
        Hostname:?whoami-6b465b89d6-lcg4k
        IP:?127.0.0.1
        IP:?::1
        IP:?10.244.1.87
        IP:?fe80::cccc:6aff:fef8:eca9
        RemoteAddr:?10.244.1.85:60384
        GET?/?HTTP/1.1
        Host:?whoami
        User-Agent:?curl/7.64.1
        Accept:?*/*
        Accept-Encoding:?gzip
        X-Forwarded-For:?192.168.31.9
        X-Forwarded-Host:?whoami
        X-Forwarded-Port:?80
        X-Forwarded-Proto:?http
        X-Forwarded-Server:?traefik-84d4cccf9c-2pl5r
        X-Real-Ip:?192.168.31.9

        另外需要注意上面 HTTPRoute 對(duì)象中需要定義 app:traefik 標(biāo)簽,否則創(chuàng)建的 Gateway 實(shí)例不能關(guān)聯(lián)上。

        帶路徑的 Host 主機(jī)

        上面的例子可以很容易地限制流量只在一個(gè)給定的子路徑上進(jìn)行路由。

        #?03-whoami-httproute-paths.yaml
        ---
        apiVersion:?networking.x-k8s.io/v1alpha1
        kind:?HTTPRoute
        metadata:
        ??name:?http-app-1
        ??namespace:?kube-system
        ??labels:
        ????app:?traefik
        spec:
        ??hostnames:
        ????-?whoami
        ??rules:
        ????-?forwardTo:
        ????????-?port:?80
        ??????????serviceName:?whoami
        ??????????weight:?1
        ??????matches:
        ????????-?path:
        ????????????type:?Exact??#?匹配?/foo?的路徑
        ????????????value:?/foo

        創(chuàng)建上面修改后的 HTTPRoute,你會(huì)發(fā)現(xiàn)之前的請(qǐng)求現(xiàn)在返回404錯(cuò)誤,而請(qǐng)求 /foo 路徑后綴則返回成功。

        ??curl?-H?"Host:?whoami"?http://192.168.31.108
        404?page?not?found
        ??curl?-H?"Host:?whoami"?http://192.168.31.108/foo
        Hostname:?whoami-6b465b89d6-p5vwz
        IP:?127.0.0.1
        IP:?::1
        IP:?10.244.2.154
        IP:?fe80::7045:53ff:fef9:fadc
        RemoteAddr:?10.244.1.85:51686
        GET?/foo?HTTP/1.1
        Host:?whoami
        User-Agent:?curl/7.64.1
        Accept:?*/*
        Accept-Encoding:?gzip
        X-Forwarded-For:?192.168.31.9
        X-Forwarded-Host:?whoami
        X-Forwarded-Port:?80
        X-Forwarded-Proto:?http
        X-Forwarded-Server:?traefik-84d4cccf9c-2pl5r
        X-Real-Ip:?192.168.31.9

        關(guān)于請(qǐng)求的哪些部分可以被匹配的更多信息可以在官方 Gateway APIs 文檔(https://gateway-api.sigs.k8s.io/v1alpha1/api-types/httproute/#rules)中找到。

        金絲雀發(fā)布

        Gateway APIs 規(guī)范可以支持的另一個(gè)功能是金絲雀發(fā)布,假設(shè)你想在一個(gè)端點(diǎn)上運(yùn)行兩個(gè)不同的服務(wù)(或同一服務(wù)的兩個(gè)版本),并將一部分請(qǐng)求路由到每個(gè)端點(diǎn),則可以通過(guò)修改你的 HTTPRoute 來(lái)實(shí)現(xiàn)。

        首先,我們需要運(yùn)行第二個(gè)服務(wù),這里我們快速生成一個(gè) Nginx 的實(shí)例來(lái)進(jìn)行測(cè)試。

        #?03-nginx.yaml
        kind:?Deployment
        apiVersion:?apps/v1
        metadata:
        ??name:?nginx
        ??namespace:?kube-system
        spec:
        ??replicas:?2
        ??selector:
        ????matchLabels:
        ??????app:?nginx
        ??template:
        ????metadata:
        ??????labels:
        ????????app:?nginx
        ????spec:
        ??????containers:
        ????????-?name:?nginx
        ??????????image:?nginx
        ??????????ports:
        ????????????-?containerPort:?80
        ??????????????name:?http
        ---
        apiVersion:?v1
        kind:?Service
        metadata:
        ??name:?nginx
        ??namespace:?kube-system
        spec:
        ??ports:
        ????-?protocol:?TCP
        ??????port:?80
        ??????targetPort:?http
        ??selector:
        ????app:?nginx

        接著我們修改前面的 HTTPRoute 資源對(duì)象,其中有一個(gè) weight 選項(xiàng),可以為兩個(gè)服務(wù)分別分配不同的權(quán)重,如下所示:

        #?04-whoami-nginx-canary.yaml
        ---
        apiVersion:?networking.x-k8s.io/v1alpha1
        kind:?HTTPRoute
        metadata:
        ??labels:
        ????app:?traefik
        ??name:?http-app-1
        ??namespace:?kube-system
        spec:
        ??hostnames:
        ????-?whoami
        ??rules:
        ????-?forwardTo:
        ????????-?port:?80
        ??????????serviceName:?whoami
        ??????????weight:?3??#?3/4?的請(qǐng)求到whoami
        ????????-?port:?80
        ??????????serviceName:?nginx
        ??????????weight:?1??#?1/4?的請(qǐng)求到whoami

        創(chuàng)建上面的 HTTPRoute 后,現(xiàn)在我們可以再次訪(fǎng)問(wèn) whoami 服務(wù),正常我們可以看到有大約 25% 的請(qǐng)求會(huì)看到 Nginx 的響應(yīng),而不是 whoami 的響應(yīng)。

        到這里我們就使用 Traefik 來(lái)測(cè)試了 Kubernetes Gateway APIs 的使用。目前,Traefik 對(duì) Gateway APIs 的實(shí)現(xiàn)是基于 v1alpha1 版本的規(guī)范,目前最新的規(guī)范是 v1alpha2,所以和最新的規(guī)范可能有一些出入的地方。

        瀏覽 98
        點(diǎn)贊
        評(píng)論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        評(píng)論
        圖片
        表情
        推薦
        點(diǎn)贊
        評(píng)論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        1. <strong id="7actg"></strong>
        2. <table id="7actg"></table>

        3. <address id="7actg"></address>
          <address id="7actg"></address>
          1. <object id="7actg"><tt id="7actg"></tt></object>
            国产精品久久久久77777按摩 | 古代闺秀被强吃奶高h视频 | 久久久久女人 | 香蕉精品在线视频 | 我和老女人吃奶作爱 | 久久精品国产99 | 国产地址 | 国内外成人免费视频 | 国产精品爽爽v在线观看无码 | 亚洲综合成人在线 |