国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

Kubernetes Pod 獲取真實(shí) IP 地址

這篇具有很好參考價(jià)值的文章主要介紹了Kubernetes Pod 獲取真實(shí) IP 地址。希望對(duì)大家有所幫助。如果存在錯(cuò)誤或未考慮完全的地方,請(qǐng)大家不吝賜教,您也可以點(diǎn)擊"舉報(bào)違法"按鈕提交疑問(wèn)。

1. 準(zhǔn)備

1.1 鏈路介紹

7 層轉(zhuǎn)發(fā)鏈路

Client --> Nginx --> K8s Nginx Ingress

4 層轉(zhuǎn)發(fā)鏈路:

Client --> 公有云 SLB(或 F5、LVS、Haproxy 等)--> K8s Nginx Ingress

實(shí)際業(yè)務(wù)可能會(huì)串聯(lián)更多層級(jí)的轉(zhuǎn)發(fā)。例如 WAF、CDN、API Gateway 一般都是 7 層轉(zhuǎn)發(fā),LB、LVS 一般是 4 層 TCP 轉(zhuǎn)發(fā)。

1.2 準(zhǔn)備 Whoami 探針

whomai 是一個(gè) go 編寫的調(diào)試探針工具,回顯 http 頭信息。

apiVersion: apps/v1
kind: Deployment
metadata:
  name: whoami
  namespace: default
  labels:
    app: whoami
spec:
  replicas: 1
  selector:
    matchLabels:
      app: whoami
  template:
    metadata:
      labels:
        app: whoami
    spec:
      containers:
      - image: containous/whoami
        imagePullPolicy: Always
        name: whoami
        ports:
        - containerPort: 80
          name: 80tcp02
          protocol: TCP
      dnsPolicy: ClusterFirst
      restartPolicy: Always
---
kind: Service
apiVersion: v1
metadata:
  name: whoami
  namespace: default
  labels:
    app: whoami
spec:
  selector:
    app: whoami
  ports:
  - name: whoami
    port: 80
    targetPort: 80
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: whoami
  namespace: default
spec:
  rules:
    - host: whoami.oook.com
      http:
        paths:
          - backend:
              service:
                name: whoami
                port:
                  number: 80
            path: /
            pathType: ImplementationSpecific

客戶端訪問(wèn),回顯 HTTP 頭顯示:

Hostname: whoami-57cb797c4f-dxlxx
IP: 127.0.0.1
IP: 10.244.5.76
RemoteAddr: 10.244.0.9:42634
GET / HTTP/1.1
Host: whoami.test.com
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/81.0.4044.138 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
Accept-Encoding: gzip, deflate
Accept-Language: zh-CN,zh;q=0.9,en;q=0.8
Cache-Control: no-cache
Pragma: no-cache
Upgrade-Insecure-Requests: 1
X-Forwarded-For: 10.244.0.1
X-Forwarded-Host: whoami.test.com
X-Forwarded-Port: 80
X-Forwarded-Proto: http
X-Original-Uri: /
X-Real-Ip: 10.244.0.1
X-Request-Id: a367b1746e215adffe4da8a73f3452cf
X-Scheme: http

2. 解決方法

2.1 7 層 HTTP 頭 X-Forwarded-For 透?jìng)?/h4>

HTTP 工作在網(wǎng)絡(luò)第 7 層,頭中有個(gè) X-Forwarded-For 字段。

大部分 CDN、WAF、LB 用 X-Forwarded-For 字段來(lái)存客戶端 IP,也有用 X-Real-Ip 字段,cloudflare、百度云加速還擴(kuò)展了 CF-Connecting-IP 字段。

# 第一個(gè) ip 是客戶端 ip,后面的 proxy 為路過(guò)一層就加一層的 ip
# 這里的 proxy 可以是 WAF、CDN、LB、API Gateway 等
X-Forwareded-For:Client,proxy1,proxy2,proxy3......

2.2 4 層 Proxy Protocol 透?jìng)?/h4>

TCP 工作在網(wǎng)絡(luò)第 4 層,Proxy Protocol 就是在 TCP 中增加一個(gè)小的報(bào)頭,用來(lái)存儲(chǔ)額外的信息。

代理協(xié)議即 Proxy Protocol,是 haproxy 的作者 Willy Tarreau 于 2010 年開(kāi)發(fā)和設(shè)計(jì)的一個(gè) Internet 協(xié)議,通過(guò)為 TCP 添加一個(gè)很小的頭信息,來(lái)方便的傳遞客戶端信息(協(xié)議棧、源IP、目的IP、源端口、目的端口等),在網(wǎng)絡(luò)情況復(fù)雜又需要獲取客戶 IP 時(shí)非常有用。

其本質(zhì)是在三次握手結(jié)束后由代理在連接中插入了一個(gè)攜帶了原始連接四元組信息的數(shù)據(jù)包。

目前 Proxy Protocol 有兩個(gè)版本,v1 僅支持 human-readable 報(bào)頭格式(ASCIII 碼),v2 需同時(shí)支持 human-readable 和二進(jìn)制格式,即需要兼容 v1 格式。

Proxy Protocol 的接收端必須在接收到完整有效的 Proxy Protocol 頭部后才能開(kāi)始處理連接數(shù)據(jù)。因此對(duì)于服務(wù)器的同一個(gè)監(jiān)聽(tīng)端口,不存在兼容帶 Proxy Protocol 包的連接和不帶 Proxy Protocol 包的連接。如果服務(wù)器接收到的第一個(gè)數(shù)據(jù)包不符合 Proxy Protocol的格式,那么服務(wù)器會(huì)直接終止連接。

Proxy Protocol 是比較新的協(xié)議,但目前已經(jīng)有很多軟件支持,如 Haproxy、Nginx、Apache、Squid、MySQL 等等。

要使用 Proxy Protocol 需要兩個(gè)角色 Sender 和 Receiver,Sender 在與 Receiver 之間建立連接后,會(huì)先發(fā)送一個(gè)帶有客戶信息的 TCP Header,因?yàn)楦牧?TCP 協(xié)議頭,需 Receiver 也支持 Proxy Protocol,否則不能識(shí)別 TCP包頭,導(dǎo)致無(wú)法成功建立連接。

3. 7 層透?jìng)髦?Kubernetes 配置

3.1 Nginx?Ingress Controller X-Forwarded-For 配置

查看 NGINX Ingress Controller 的 ConfigMap 文檔中有以下配置:

use-forwarded-headers

如果為 true,Nginx 會(huì)將傳入的 X-Forwarded-* 頭傳遞給 upstreams。當(dāng) Nginx 位于另一個(gè)正在設(shè)置這些標(biāo)頭的 L7 proxy/load balancer 之后時(shí),請(qǐng)使用此選項(xiàng)。

如果為 false,Nginx 會(huì)忽略傳入的 X-Forwarded-* 頭,用它看到的請(qǐng)求信息填充它們。如果 Nginx 直接暴露在互聯(lián)網(wǎng)上,或者它在基于 L3/packet-based load balancer 后面,并且不改變數(shù)據(jù)包中的源 IP,請(qǐng)使用此選項(xiàng)。

Nginx Ingress Controller 直接暴露互聯(lián)網(wǎng)也就是 Edge 模式不能開(kāi)啟為 true,否則會(huì)有偽造 IP 的安全問(wèn)題。也就是 k8s 有公網(wǎng) IP,直接讓客戶端訪問(wèn),本配置不要設(shè)為 true。

forwarded-for-header

設(shè)置標(biāo)頭字段以標(biāo)識(shí)客戶端的原始IP地址。 默認(rèn)為 X-Forwarded-For。

如果 Nginx Ingress Controller 在 CDN、WAF、LB 等后面,設(shè)置從頭的哪個(gè)字段獲取 IP,默認(rèn)是 X-Forwarded-For。這個(gè)配置應(yīng)該和 use-forwarded-headers 配合使用。

compute-full-forwarded-for

將遠(yuǎn)程地址附加到 X-Forwarded-For 標(biāo)頭,而不是替換它。 啟用此選項(xiàng)后,upstreams 應(yīng)用程序?qū)⒏鶕?jù)其自己的受信任代理列表提取客戶端 IP。

實(shí)際配置如下:

# kubectl -n ingress-nginx  edit cm nginx-configuration
# 添加
data:
  compute-full-forwarded-for: "true"
  forwarded-for-header: "X-Forwarded-For"
  use-forwarded-headers: "true"

3.2 使用?externalTrafficPolicy: Local 保留報(bào)文的源地址

Kubernetes 將在 Pod 所在 Node 上針對(duì) nodePort 下發(fā) DNAT 規(guī)則:

          client
             \ ^
              \ \
               v \
   node 1 <--- node 2
    | ^   SNAT
    | |   --->
    v |
 endpoint
  • 客戶端發(fā)送數(shù)據(jù)包到 node2:nodePort;
  • node2 使用它自己的 IP 地址替換數(shù)據(jù)包的源 IP 地址(SNAT);
  • node2 使用 pod IP 地址替換數(shù)據(jù)包的目的 IP 地址;
  • 數(shù)據(jù)包被路由到 node 1,然后交給 endpoint;
  • Pod 的回復(fù)被路由回 node2;
  • Pod 的回復(fù)被發(fā)送回給客戶端。

這樣就無(wú)法返回正確的客戶端 IP,返回的 IP 為集群內(nèi)部的 IP 地址。

為了防止這種情況發(fā)生,Kubernetes 提供了一個(gè)特性來(lái)保留客戶端的源 IP 地址,設(shè)置 service.spec.externalTrafficPolicy 的值為 Local,請(qǐng)求就只會(huì)被代理到本地 endpoints 而不會(huì)被轉(zhuǎn)發(fā)到其它節(jié)點(diǎn)。這樣就保留了最初的源 IP 地址。如果沒(méi)有本地 endpoints,發(fā)送到這個(gè)節(jié)點(diǎn)的數(shù)據(jù)包將會(huì)被丟棄。這樣在應(yīng)用到數(shù)據(jù)包的任何包處理規(guī)則下,你都能依賴這個(gè)正確的 source-ip 使數(shù)據(jù)包通過(guò)并到達(dá) endpoint。

設(shè)置?service.spec.externalTrafficPolicy 字段如下:

kubectl patch svc nodeport -p '{"spec":{"externalTrafficPolicy":"Local"}}'

這樣就可以獲取到真實(shí)的 IP:

        client
       ^ /   \
      / /     \
     / v       X
   node 1     node 2
    ^ |
    | |
    | v
 endpoint
  • 客戶端發(fā)送數(shù)據(jù)包到 node2:nodePort,它沒(méi)有任何 endpoints;
  • 數(shù)據(jù)包被丟棄;
  • 客戶端發(fā)送數(shù)據(jù)包到 node1:nodePort,它有 endpoints;
  • node1 使用正確的源 IP 地址將數(shù)據(jù)包路由到 endpoint。

實(shí)際配置如下:

apiVersion: v1
kind: Service
metadata:
  labels:
    app.kubernetes.io/name: ingress-nginx
    app.kubernetes.io/part-of: ingress-nginx
  name: ingress-nginx
  namespace: ingress-nginx
spec:
  externalTrafficPolicy: Local
  ports:
  - name: http
    nodePort: 30080
    port: 80
    protocol: TCP
    targetPort: 80
  - name: https
    nodePort: 30443
    port: 443
    protocol: TCP
    targetPort: 443
  selector:
    app.kubernetes.io/name: ingress-nginx
    app.kubernetes.io/part-of: ingress-nginx
  type: NodePort

3.3 Nginx 作為邊緣節(jié)點(diǎn)配置

作為 Edge 需要重寫 remote_addr,保證客戶端 IP 不會(huì)被偽造。

  • 必須:X-Forwarded-For 重寫為 $remote_addr
  • 非必須擴(kuò)展:X-Real-IP 重寫為 $remote_addr
upstream k8s {
    server 10.10.115.21:443;
    server 10.10.115.22:443;
    server 10.10.115.23:443;
}

map $http_upgrade $connection_upgrade {
    default Upgrade;
    ''      close;
}
server {
    if ($http_x_forwarded_proto = '') {
        set $http_x_forwarded_proto  $scheme;
   }
location / {

        proxy_set_header Host              $http_host;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_set_header X-Forwarded-Port  $server_port;
        #proxy_set_header X-Forwarded-For   $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-For   $remote_addr;
        proxy_set_header X-Real-IP         $remote_addr;

        proxy_pass          https://k8s;
        proxy_http_version  1.1;
        proxy_set_header    Upgrade $http_upgrade;
        proxy_set_header    Connection $connection_upgrade;
        proxy_read_timeout 900s;
        proxy_buffering off;
    }
}

3.4 X-Forwarded-For 是否可以偽造

客戶端是否能偽造 IP,取決于邊緣節(jié)點(diǎn)(Edge)是如何處理 X-Forwarded-For 字段的。

客戶端直接連接的首個(gè) Proxy 節(jié)點(diǎn)都叫做邊緣節(jié)點(diǎn)(Edge),不管是網(wǎng)關(guān)、CDN、LB 等只要這一層是直接接入客戶端訪問(wèn)的,那么他就是一個(gè)邊緣節(jié)點(diǎn)。

不重寫-不安全的邊緣節(jié)點(diǎn)(Edge)

邊緣節(jié)點(diǎn)如果是透?jìng)?HTTP 頭中的 X-Forwarded-For 字段,那么這個(gè)就是不安全的,客戶端可以在 HTTP 中實(shí)現(xiàn)包含 X-Forwarded-For 字段值,這個(gè)值又被透?jìng)髁恕?/p>

# 不安全
X-Forwareded-For:Client(Edge不重寫,只透?jìng)?,proxy1,proxy2,proxy3……

# 不安全
X-Forwareded-For:Client(Edge不重寫,只透?jìng)?,proxy1,proxy2,proxy3……

#安全
X-Forwareded-For:Client(Edge獲取的remote_addr),proxy1,proxy2,proxy3……

4. 4 層透?jìng)?Kubernetes 配置

4.1 Nginx?Ingress Controller?Proxy Protocol 配置

查看 NGINX Ingress Controller 的 ConfigMap 文檔中有以下配置:

use-proxy-protocol

啟用或禁用 Proxy Protocol,以接收通過(guò)代理服務(wù)器和負(fù)載均衡器(例如 HAProxy 和Amazon Elastic Load Balancer(ELB))傳遞的客戶端連接(真實(shí)IP地址)信息。

Nginx??Ingress Controller 作為 receiver 角色 Proxy Protocol 配置:

data:
  use-proxy-protocol: "true"

實(shí)際配置如下:

# kubectl -n ingress-nginx edit cm nginx-configuration
# 添加
data:
  use-proxy-protocol: "true"

注意

需要上一層 LB 支持 Proxy Protocol,才能這么配置,否則會(huì)導(dǎo)致無(wú)法連接。

同樣需要將??service.spec.externalTrafficPolicy 的值設(shè)置為 Local。

4.2 Haproxy 支持 Proxy Protocol 配置

Haproxy 是 proxy protocol 的親爹,使用非常方便。配置 send-proxy 和 accept-proxy 兩個(gè)參數(shù)即可。

frontend nginx-ingress-http
  bind 0.0.0.0:80
  bind 127.0.0.1:80
  # bind *:80 # accept-proxy 作為 receiver
  mode tcp
  option tcplog
  tcp-request inspect-delay 5s
  default_backend nginx-ingress-http

backend nginx-ingress-http
  mode tcp
  option tcplog
  option tcp-check
  balance roundrobin
  default-server inter 10s downinter 5s rise 2 fall 2 slowstart 60s maxconn 40960 maxqueue 256 weight 100
  server nginx-ingress-1 10.10.115.21:30080 send-proxy check
  server nginx-ingress-2 10.10.115.22:30080 send-proxy check
  server nginx-ingress-3 10.10.115.23:30080 send-proxy check

frontend nginx-ingress-https
  bind 0.0.0.0:443
  bind 127.0.0.1:443
  # bind *:443 # accept-proxy 作為 receiver
  mode tcp
  option tcplog
  tcp-request inspect-delay 5s
  default_backend nginx-ingress-https

backend nginx-ingress-https
  mode tcp
  option tcplog
  option tcp-check
  balance roundrobin
  default-server inter 10s downinter 5s rise 2 fall 2 slowstart 60s maxconn 40960 maxqueue 256 weight 100
  server nginx-ingress-1 10.10.115.21:30443 send-proxy check
  server nginx-ingress-2 10.10.115.22:30443 send-proxy check
  server nginx-ingress-3 10.10.115.23:30443 send-proxy check

總結(jié)

上游如果是 7 層用 X-Forwarded-For,如果是 4 層用 Proxy Protocol。

如果鏈路的邊緣節(jié)點(diǎn)(Edge)X-Forwarded-For 字段是安全的,建議用 X-Forwarded-For。

如果鏈路 Proxy 全路徑都支持 Proxy Protocol,那么建議用 Proxy Protocol。

如果有 4 層 TCP 業(yè)務(wù)應(yīng)用,那么獲取客戶端 IP 就的用 Proxy Protocol。

參考

●How does Cloudflare handle HTTP Request headers?
●NGINX Ingress Controller ConfigMaps
●HTTP Headers X-Forwarded-For
●Nginx Module ngx_http_realip_module
●Haproxy Proxy Protocol
●Kubernetes Using Source IP文章來(lái)源地址http://www.zghlxwxcb.cn/news/detail-604447.html

到了這里,關(guān)于Kubernetes Pod 獲取真實(shí) IP 地址的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來(lái)自互聯(lián)網(wǎng)用戶投稿,該文觀點(diǎn)僅代表作者本人,不代表本站立場(chǎng)。本站僅提供信息存儲(chǔ)空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請(qǐng)注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實(shí)不符,請(qǐng)點(diǎn)擊違法舉報(bào)進(jìn)行投訴反饋,一經(jīng)查實(shí),立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • Django 獲取真實(shí)ip地址

    2024年02月12日
    瀏覽(20)
  • docker 容器獲取真實(shí)ip地址

    docker 容器獲取真實(shí)ip地址

    1、調(diào)用處 2、Iputils **特別注意:**如果使用到了nginx代理的話,需要在nginx.cofig內(nèi)加上下面配置 效果: 加油,奧利給

    2024年02月16日
    瀏覽(23)
  • Java-通過(guò)IP獲取真實(shí)地址

    Java-通過(guò)IP獲取真實(shí)地址

    最近寫了一個(gè)日志系統(tǒng),需要通過(guò)訪問(wèn)的 IP 地址來(lái)獲取真實(shí)的地址,并且存到數(shù)據(jù)庫(kù)中,我也是在網(wǎng)上看了一些文章,遂即整理了一下供大家參考。 這個(gè)是獲取正確 IP 地址的方法,可以直接使用的。 通過(guò)以上方法你可以獲取到訪問(wèn)者的 IP 地址,只有獲取到了 IP 地址,才能

    2024年02月15日
    瀏覽(27)
  • JavaWeb 獲取客戶端的真實(shí)IP地址

    通常我們?cè)贘avaWeb中獲取客戶端IP地址只需要使用 request.getRemoteAddr(); 方法即可 如果前端使用了Nginx等反向代理的話,我們使用 request.getRemoteAddr(); 方法獲取到的IP地址就是 127.0.0.1 因?yàn)榻?jīng)過(guò)代理以后,在客戶端和服務(wù)器之間增加了中間層,因此服務(wù)器無(wú)法直接拿到客戶端的 IP 但

    2024年02月15日
    瀏覽(25)
  • java獲取真實(shí)的請(qǐng)求接口ip地址

    在Java程序中獲取請(qǐng)求的真實(shí)IP地址可以使用以下方法: 使用javax.servlet.http.HttpServletRequest類中的getRemoteAddr()方法,這個(gè)方法可以獲取請(qǐng)求的IP地址。 可以檢查X-Forwarded-For,如果請(qǐng)求是通過(guò)代理服務(wù)器發(fā)送的,那么X-Forwarded-For將包含被代理客戶端的IP地址??梢允褂肏ttpServletReque

    2024年02月11日
    瀏覽(19)
  • nginx獲取不到真實(shí)ip地址,注意這個(gè)細(xì)節(jié)

    1 一定要把proxy_pass語(yǔ)句放在最后面 location / { ????????proxy_set_header Host $host; ????????proxy_set_header X-Real-IP $remote_addr; ????????proxy_set_header REMOTE-HOST $remote_addr; ????????proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; ????????client_max_body_size 1024m; ????????# 一

    2024年02月13日
    瀏覽(24)
  • 獲取客戶端真實(shí) IP 地址的最佳實(shí)踐

    1. 業(yè)務(wù)上云帶來(lái)性能收益 公司從去年全面推動(dòng)業(yè)務(wù)上云,而以往 IDC 架構(gòu)部署上,接入層采用典型的 4 層 LVS 多機(jī)房容災(zāi)架構(gòu),在業(yè)務(wù)高峰時(shí)期,擴(kuò)容困難(受限于物理機(jī)資源和 LVS 內(nèi)網(wǎng)網(wǎng)段的網(wǎng)絡(luò)規(guī)劃),且抵擋不住 HTTPS 卸載引發(fā)的高 CPU 占用。 而經(jīng)過(guò)壓力測(cè)試發(fā)現(xiàn),使用

    2024年02月05日
    瀏覽(30)
  • 【Java開(kāi)發(fā)】之獲取客戶端真實(shí) IP 地址

    在投票系統(tǒng)開(kāi)發(fā)中,為了防止刷票,我們需要限制每個(gè) IP 地址只能投票一次; 當(dāng)網(wǎng)站受到諸如 DDoS(Distributed Denial of Service,分布式拒絕服務(wù)攻擊)等攻擊時(shí),我們需要快速定位攻擊者 IP; 在滲透測(cè)試過(guò)程中,經(jīng)常會(huì)碰到網(wǎng)站有 CDN(Content Distribution Network,內(nèi)容交付網(wǎng)絡(luò)),

    2024年02月04日
    瀏覽(37)
  • Nginx代理后獲取客戶端真實(shí)IP地址

    Nginx代理后獲取客戶端真實(shí)IP地址

    在項(xiàng)目實(shí)際應(yīng)用中,我們可能會(huì)需要獲取到用戶也就是客戶端的真實(shí)IP地址,比如記錄系統(tǒng)操作日志等情況。 通常情況下我們可以使用以下方式來(lái)獲取IP地址 但是當(dāng)我們使用Nginx反向代理項(xiàng)目地址后,使用以上方法只能獲取到Nginx服務(wù)器的IP地址,并不是客戶端的IP地址。 解決

    2023年04月11日
    瀏覽(41)
  • Java中使用HttpRequest獲取用戶真實(shí)IP地址端口

    獲取請(qǐng)求來(lái)源ip代碼: 獲取請(qǐng)求來(lái)源端口代碼:

    2024年02月11日
    瀏覽(22)

覺(jué)得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請(qǐng)作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包