Nginx Ingress Controller是部署于集群內部的Ingress控制器,可以為您提供性能更好且定制性更高的使用方式。在社區版本的基礎上,ACK集群提供的Nginx Ingress Controller整合了阿里云產品的一系列功能,提供更加便捷的使用體驗。由于Nginx Ingress Controller部署在集群內部,因此它的穩定性與使用時的配置、當前集群狀態密切相關。本文介紹Nginx Ingress Controller的使用建議,您可以參考以下使用建議,對集群內的Ingress Controller進行配置,獲得最佳的使用效果。
索引
提升Nginx Ingress Controller的性能和穩定性
使用合適的副本數和資源限制
默認情況下,通過集群創建或從組件中心安裝的Nginx Ingress Controller的副本數為2,您可以根據業務的實際需要進行調整。
在部署Nginx Ingress Controller時,請確保Nginx Ingress Controller分布在不同的節點上,避免不同Nginx Ingress Controller之間資源的搶占和單點故障。您也可以為其使用獨占節點來保證性能與穩定性,具體操作,請參見使用獨占節點保證Nginx Ingress性能與穩定性。同時建議您不要為Nginx Ingress Controller設定資源限制,避免OOM所帶來的流量中斷。如果確實有限制的需要,建議資源限制CPU不低于1000 Milicore(YAML配置里格式為1000m
)和內存不低于2 GiB。
使用獨占節點來提升Nginx Ingress性能與穩定性
如果您對Ingress Controller有較高穩定性要求,可以為其分配獨占節點以避免資源的搶占。具體操作,請參見部署高可靠Ingress Controller。
對于高負載場景,您也可以通過設置Ingress Controller來支撐高負載應用。具體操作,請參見部署高負載場景的Nginx Ingress Controller。
優化Nginx Ingress性能
Nginx Ingress Controller性能調優主要分為系統參數調優和Nginx參數調優:
系統參數調優:阿里云上的操作系統已經默認優化了一些常見參數,其他還需要調優的系統參數主要包括系統最大Backlog數和可用端口的最大范圍。系統參數調優后可以保證Nginx處理高并發請求的能力,以及在連接后端時不會因為端口耗盡而失敗。
Nginx參數調優:
調整單個Worker的最大連接數:Nginx參數主要可以調整單個Worker的最大連接數來保證Nginx Ingress Controller處理高并發請求的能力。
增加連接超時時間:Nginx Ingress Controller與Nginx默認表現不同,會使用長連接對后端業務Pod發起請求,因此Nginx參數還需要增加連接超時時間來讓單條連接能夠處理更多的請求,減少連接創建時的開銷。
設置長連接超時時間:請您確保后端的業務長連接的超時時間不低于Nginx Ingress Controller的連接超時時間( ACK集群中默認為900s)。
Nginx Ingress組件默認已經置入了相關的調優項,在一般場景中能夠達到較優的表現。如果您有特殊需要,可以通過ConfigMap中的相關字段進一步優化系統參數和Nginx參數。關于ConfigMap的更多信息,請參見ConfigMaps。
對Nginx Ingress Controller配置HPA進行自動擴容
一般情況下,Nginx Ingress Controller已經有足夠的能力應對業務的突發流量。如果在高負載情況下仍不滿足您的要求,也可以配置HPA對Nginx Ingress Controller進行擴容。具體操作,請參見容器水平伸縮(HPA)。
在Pod擴縮容時可能會導致部分業務連接的中斷情況,請謹慎配置。
配置的YAML示例如下所示:
apiVersion: autoscaling/v2beta1
kind: HorizontalPodAutoscaler
metadata:
name: nginx-ingress-controller-hpa
namespace: kube-system
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: nginx-ingress-controller
minReplicas: 2
maxReplicas: 5
metrics:
- type: Resource
resource:
name: cpu
targetAverageUtilization: 50
為后端服務配置合理的preStop Hook
在后端服務滾動更新時,Nginx ingress Controller會將正在終止的Pod的端點摘除,同時保持還在處理的請求的連接。如果后端服務Pod在收到結束信號后立即退出,就可能會導致正在處理的請求失敗,或者由于時序問題,部分流量仍被轉發到已經退出的Pod中,導致部分流量產生損失。
為了解決滾動更新時流量產生損失的情況,推薦在后端服務的Pod中配置preStop Hook,在端點被摘除后仍繼續工作一段時間,解決流量中斷的情況。
在Pod模板的容器配置中加入:
apiVersion: apps/v1
kind: Deployment
spec:
template:
spec:
containers:
- name: app
lifecycle:
# 配置preStop Hook,等待30秒后退出。
# 需要容器中存在sleep命令。
preStop:
exec:
command:
- sleep
- 30
提升Nginx Ingress Controller的可觀測性
使用SLS和阿里云Prometheus服務提升可觀測性
Nginx Ingress Controller提供了基于SLS日志以及Prometheus的監控大盤,幫助您更好地了解業務的流量情況。
SLS日志:
創建集群時,如果您已經選中了啟用日志組件及Ingress Dashboard,您就可以直接通過容器服務管理控制臺 頁面的Ingress概覽中查看到基于SLS日志服務提供的大盤服務;您也可以直接在 查看到Nginx Ingress Controller產生的相關日志。具體操作,請參見Nginx Ingress訪問日志分析與監控。
如果您在創建時沒有選中日志以及Ingress的相關選項,也可以手動配置日志收集組件和規則。具體操作,請參見Nginx Ingress訪問日志分析與監控。關于監控的更多信息,請參見Ingress Dashboard監控。
阿里云Prometheus監控:阿里云Prometheus監控可以在創建集群時選擇安裝,或者在創建集群后通過 安裝或查看。具體操作,請參見阿里云Prometheus監控。
說明使用阿里云Prometheus監控時,請為集群中的Ingress資源添加
host
字段,否則在默認情況下,該Ingress的部分metrics將會缺失。您也可以通過在Nginx Ingress Controller的Deployment中修改controller
啟動參數,加入--metrics-per-host=false
來解決該問題。
Nginx Ingress Controller進階功能
使用多套Nginx Ingress Controller
在應用中,您可能會因為內外網隔離等需要,在集群中部署多套Nginx Ingress Controller。具體操作,請參見部署多個Ingress Controller。
在集群內部訪問Nginx Ingress Controller
在集群中,LoadBalancer Service的外部地址(Nginx Ingress Controller的公網 IP)通常會被Iptables或IPVS攔截并轉發。當externalTrafficPolicy
為Local
,且節點上沒有對應Nginx Ingress Pod時,會發生網絡不通的問題。ACK集群中的Nginx Ingress Controller默認使用了Local模式的LoadBalancer Service,因此在集群內訪問Nginx Ingress Controller綁定的CLB地址時,可能會出現網絡不通的情況。
建議您在集群內部有訪問Nginx Ingress Controller(通過公網IP或綁定公網IP的域名)的需要時,使用Service ClusterIP或內部域名(nginx-ingress-lb.kube-system
)訪問。同時請避免在Nginx Ingress Controller中對自身進行訪問,也可能會因為Hairpin問題導致網絡不通。關于該問題的解決方案,請參見Kubernetes集群中訪問LoadBalancer暴露出去的SLB地址不通。
使用WAF或透明WAF
為了阻擋惡意請求,您可以在Web應用防火墻控制臺或應用型負載均衡ALB控制臺為集群Nginx Ingress Controller所使用的CLB開啟WAF或透明WAF功能。在開啟HTTPS端口上的WAF或透明WAF功能時,需要在控制臺上配置所使用的證書。這種情況下,可能會出現以下問題:
TLS請求會在WAF或透明WAF上進行截斷,因此集群內通過Secret配置的證書將不會被暴露在公網出口上。
在集群內通過CLB IP或Service ClusterIP訪問443端口可能不會經過WAF或透明WAF,導致證書返回錯誤。
在開啟WAF或透明WAF的情況下,Nginx Ingress Controller將默認無法獲得真實的客戶端IP。您可以通過在ConfigMap中 ( 通過組件管理安裝的Nginx Ingress Controller默認為kube-system命名空間下的nginx-configuration)添加以下內容,配置啟用Nginx的Realip模塊,使用
X-Forwarded-For
頭作為真實客戶端地址。use-forwarded-headers: "true" # 0.30.0及更舊版本使用該選項。 enable-real-ip: "true" # 0.44.0及更新版本使用該選項。 proxy-real-ip-cidr: <您從WAF獲取到的回源IP段>
通過Nginx Ingress Controller進行應用的藍綠或灰度發布
您可以通過容器服務管理控制臺的灰度發布或手動添加Annotation的方式來使用Nginx Ingress Controller提供的灰度功能,具體操作,請參見通過Nginx Ingress實現灰度發布和藍綠發布。
請確保需要灰度所使用的服務(包括原服務和灰度服務)沒有同時被灰度Ingress以外的Ingress資源引用。否則,可能會出現灰度規則的沖突,從而引發流量路由錯誤。
通過Nginx Ingress Controller代理非HTTP請求
Nginx Ingress Controller默認使用HTTP協議連接到后端服務,但同時提供了對多種后端協議的支持,其中比較常用的協議有WebSocket、HTTPS和gRPC。關于支持的后端協議具體類型,請參見Backend Protocol。
WebSocket:Nginx Ingress Controller提供了對WebSocket的原生支持,您不需要進行任何配置即可轉發WebSocket連接。如果您有持續較長的WebSocket連接,可以通過Annotation適當地調整后端連接的超時時間,防止業務因為超時而斷連。關于調整的具體操作,請參見Custom timeouts。
HTTPS:針對使用HTTPS的后端服務,您可以在Ingress中添加
nginx.ingress.kubernetes.io/backend-protocol:"HTTPS"
的Annotation切換為HTTPS連接。gRPC:gRPC僅支持通過TLS端口訪問。因此,請確保您的業務通過Nginx Ingress Controller訪問gRPC服務時,使用的是加密的TLS端口。關于配置gRPC的具體操作,請參見通過Ingress Controller實現gRPC服務訪問。