networkpolicy

网络策略基于ip端口控制流量(OSI 第 3 层或第 4 层)),NetworkPolicy 适用于一端或两端与 Pod 的连接,与其他连接无关。

需要依赖cni 网络插件,calico 通过自定义k8s 资源支持网络策略

配置文件

第一步:配置文件结构

字段 释义 举例
apiversion api群组 networking.k8s.io/v1
kind 资源类型 NetworkPolicy
metadata 元数据信息
spec

第二步:剖析spec

字段 释义 举例
podSelector 选中要实施网络策略的pod
poicyTypes 策略的类型,["Ingress","Egress"] 5中特殊情况接下来描述
ingress 入栈流量的过滤策略
egress 出栈流量的过滤策略

第三步:具体展开

  • podSelector

    1. 选择该资源所在名称空间下的所有pod

      spec:
        podSelector: {}
      
    2. 选择该资源所在名称空间下拥有指定标签的pod

      spec:
        podSelector:
          matchLables:
            app: db
      
      sepc:
        podSelector:
          matchExpressions:
          - key: app
            operator: In
            values:
            - db
      
  • policyTypes

    1. 不应用任何自定义策略,执行默认策略(允许任何的出栈和入栈流量)

      spec:
        policyTypes: []
      
    2. 禁止所有的出栈流量

      spec:
        policyTypes:
        - Egress
        ...
        spec下没有定义 egress
      
    3. 禁止所有的入栈流量

      spec:
        policyTypes:
        - Ingress
        ...
        spec 下没有定义 ingress
      
    4. 允许所有的出栈流量

      spec:
        policyTypes:
        - Egress
        egress: {}
      
    5. 允许所有的入栈流量

      spec:
        policyTypes:
        - Ingress
        ingress:{}
      
  • ingress

    1. 定义来源:例如允许哪个ip、名称空间、pod 访问

    2. 定义允许访问本地的端口、协议

    fromports两种是交际的关系,而from和ports中以列表展示的资源是并集关系

    spec:
      ingress:
      - from:
        - ipBlock:
          cidr: "10.4.7.1/24"
          expect:
          - "10.4.7.50/32"
          - "192.168.123.1/24"
        - namespaceSelector:
            matchLabels: {}
            matchExpressions: {}
          # 默认从networPolicy所定义的名称空间选择pod
        - podSelector:
            matchLabels: {}
            matchExpressions: {}
          #namespaceSelector:{}
      - ports:
        - protocol: TCP
          port: 8000
    
  • egress

    spec:
      ingress:
      - to:
        - ipBlock:
          cidr: "10.4.7.1/24"
          expect:
          - "10.4.7.50/32"
          - "192.168.123.1/24"
        - namespaceSelector:
            matchLabels: {}
            matchExpressions: {}
         # 默认从networPolicy所定义的名称空间选择pod
        - podSelector:
            matchLabels: {}
            matchExpressions: {}
          #namespaceSelector:{}
      - ports:
        - protocol: TCP
          port: 8000
    

案例测试

kubectl create ns ns01
kubectl create ns ns02

kubectl create deploy test-networkpolicy --image=python -n ns01 --image=python --replicas=2
kubectl create deploy test-networkpolicy --image=python -n ns02 --image=python --replicas=2
kubectl create ns web
kubectl create ns db
kubectl run web --image=python -n web --port=8000 -- python -m http.server 
kubectl run web2 --image=python -n web --port=8001 -- python -m http.server 8001
kubectl run db --image=python -n db --port=8000 -- python -m http.server 8000 
kubectl run db2 --image=python -n db --port=8001 -- python -m http.server 8001 

场景一:只允许同名称空间的pod通讯

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: only-communication-onenamespace
  namespace: web
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  - Egress
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          kubernetes.io/metadata.name: "web"
  egress:
  - to:
    - namespaceSelector:
        matchLabels:
          kubernetes.io/metadata.name: "web"

场景二:只允许该名称空间pod访问外部应用

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: out-to-anyone
  namespace: web
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  - Egress
  egress:
  - {}

场景三:只允许该名称空间的pod访问指定名称空间的指定端口

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: speci-namespace-port
  namespace: web
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  - Egress
  egress:
  - to:
    - namespaceSelector:
        matchLabels:
          kubernetes.io/metadata.name: db
    ports:
    - port: 8001

场景四:只允许该名称空间的pod访问指定名称空间下指定pod的指定端口

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: spec-namespace-pod-port
  namespace: web
spec:
  podSelector: {}
  policyTypes:
  - Egress
  egress:
  - to:
    - namespaceSelector:
        matchLabels:
          "kubernetes.io/metadata.name": "db"
      podSelector:
        matchLabels:
          run: "db2"
    ports:
    - port: 8001

场景五:只允许指定名称空间的pod访问本名称空间

场景六: 只允许指定名称空间的指定pod访问本名称空间

场景七:只允许指定名称空间的指定pod访问本名称空间指定端口

场景八:只允许指定名称空间的指定pod访问本名称空间指定pod的端口

场景九:只允许指定指定ip段访问本名称空间

场景十:本名称空间只允许访问指定指定ip段的pod

场景九:禁止该名称空间pod与任何pod 通讯

第一题:只允许ns01 名称空间内部通讯

# 隔离名称空间的通讯
# 名称空间ns01的pod只允许名称空间内pod通讯
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: isolation-namespace
  namespace: ns01
spec:
  podSelector: {}  #选择该名称空间下的所有pod
  policyTypes:
   - Ingress
   - egress
  ingress:
  - from:
    - namespaceSelector:
        matchExpressions:
        - key: kubernetes.io/metadata.name
          operator: In
          values:
          - ns01
  egress:
  - to:
    - namespaceSelector:
        matchExpressions:
        - key: kubernetes.io/metadata.name
          operator: In
          values:
          - ns0

第二题:只允许通过ns02中的pod访问ns01 监听8080的pod

# ns01 中创建一个 netpol allow-port-from-namespace
# 允许 ns02 中的pod 连接到 ns01 中的监听8080的pod
# 不允许访问ns01中未监听8080的pod访问
# 不允许名称空间ns02 外的访问
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-port-from-namespace
  namespace: ns01
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  ingress:
  - from:
    - namespaceSelector:
        matchExpressions:
        - key: kubernetes.io/metadata.name
          operator: In
          values:
          - ns02
  - ports:
    - protocol: TCP
      port: 8080
posted @ 2021-12-18 21:48  mingtian是吧  阅读(73)  评论(0编辑  收藏  举报