Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Nota. transl.: L'autor de l'article - Reuven Harrison - té més de 20 anys d'experiència en desenvolupament de programari, i avui és el CTO i cofundador de Tufin, una empresa de solucions de gestió de polítiques de seguretat. Tot i que considera que les polítiques de xarxa de Kubernetes són prou potents per segmentar la xarxa en un clúster, també creu que no són tan fàcils d'implementar a la pràctica. Aquest material (més aviat voluminós) pretén millorar la consciència dels especialistes en aquesta matèria i ajudar-los a crear les configuracions necessàries.

Avui en dia, moltes empreses trien cada cop més Kubernetes per executar les seves aplicacions. L'interès per aquest programari és tan gran que alguns anomenen Kubernetes "el nou sistema operatiu per als centres de dades". A poc a poc, Kubernetes (o k8s) comença a ser percebut com una part crítica del negoci, que requereix l'organització de processos empresarials madurs, inclosa la seguretat de la xarxa.

Per als professionals de la seguretat que s'han vist desconcertats treballant amb Kubernetes, la política predeterminada d'aquesta plataforma pot ser un autèntic descobriment: permetre-ho tot.

Aquesta guia us ajudarà a entendre el funcionament intern de les polítiques de xarxa; entendre en què es diferencien de les regles dels tallafocs habituals. També parlarà d'alguns dels inconvenients i donarà recomanacions que ajudaran a protegir les aplicacions a Kubernetes.

Polítiques de xarxa de Kubernetes

El mecanisme de política de xarxa de Kubernetes us permet gestionar la interacció de les aplicacions desplegades a la plataforma a la capa de xarxa (la tercera en el model OSI). Les polítiques de xarxa no tenen algunes de les funcions avançades dels tallafocs moderns, com ara el control de la capa 7 OSI i la detecció d'amenaces, però proporcionen una capa bàsica de seguretat de xarxa que és un bon punt de partida.

Les polítiques de xarxa controlen les comunicacions entre pods

Les càrregues de treball a Kubernetes es distribueixen entre pods, que consisteixen en un o més contenidors desplegats junts. Kubernetes assigna a cada pod una adreça IP accessible des d'altres pods. Les polítiques de xarxa de Kubernetes estableixen permisos d'accés per a grups de pods de la mateixa manera que s'utilitzen els grups de seguretat al núvol per controlar l'accés a les instàncies de la màquina virtual.

Definició de polítiques de xarxa

Igual que altres recursos de Kubernetes, les polítiques de xarxa s'estableixen a YAML. A l'exemple següent, l'aplicació balance obre l'accés a postgres:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.postgres
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: postgres
  ingress:
  - from:
    - podSelector:
        matchLabels:
          app: balance
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

(Nota. transl.: aquesta captura de pantalla, com totes les captures de pantalla similars posteriors, no es va crear amb eines natives de Kubernetes, sinó amb l'eina Tufin Orca, que va ser desenvolupada per l'empresa de l'autor de l'article original i que s'esmenta al final del material.)

Es requereixen coneixements bàsics de YAML per definir la vostra pròpia política de xarxa. Aquest llenguatge es basa en el sagnat (especificat per espais, no per tabulacions). L'element sagnat pertany a l'element sagnat més proper a sobre. El nou element de la llista comença amb un guionet, tots els altres elements són de la forma valor-clau.

Després de descriure la política a YAML, utilitzeu kubectlper crear-lo al clúster:

kubectl create -f policy.yaml

Especificació de la política de xarxa

L'especificació de la política de xarxa de Kubernetes inclou quatre elements:

  1. podSelector: defineix els pods afectats per aquesta política (objectius) - obligatoris;
  2. policyTypes: indica quins tipus de polítiques s'inclouen en aquesta: entrada i/o sortida - opcional, però recomano especificar-ho explícitament en tots els casos;
  3. ingress: defineix permès entrant trànsit als pods de destinació: opcional;
  4. egress: defineix permès sortint el trànsit dels pods objectiu és opcional.

Un exemple manllevat del lloc de Kubernetes (he substituït role en app), mostra com s'utilitzen els quatre elements:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: test-network-policy
  namespace: default
spec:
  podSelector:    # <<<
    matchLabels:
      app: db
  policyTypes:    # <<<
  - Ingress
  - Egress
  ingress:        # <<<
  - from:
    - ipBlock:
        cidr: 172.17.0.0/16
        except:
        - 172.17.1.0/24
    - namespaceSelector:
        matchLabels:
          project: myproject
    - podSelector:
        matchLabels:
          role: frontend
    ports:
    - protocol: TCP
      port: 6379
  egress:         # <<<
  - to:
    - ipBlock:
        cidr: 10.0.0.0/24
    ports:
    - protocol: TCP
      port: 5978

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat
Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Tingueu en compte que no cal incloure els quatre elements. Només és necessari podSelector, la resta de paràmetres es poden utilitzar com es desitgi.

Si ometem policyTypes, la política s'interpretarà de la següent manera:

  • S'assumeix per defecte definir el costat d'entrada. Si la política no ho indica explícitament, el sistema assumirà que tot el trànsit està prohibit.
  • El comportament al costat de sortida estarà determinat per la presència o absència del paràmetre de sortida corresponent.

Per evitar errors, el recomano ser sempre explícit policyTypes.

Segons la lògica anterior, en cas que els paràmetres ingress i / o egress s'omet, la política denegarà tot el trànsit (vegeu "Regla d'escombrat" a continuació).

Política per defecte: permet

Si no es defineixen polítiques, Kubernetes permet tot el trànsit de manera predeterminada. Tots els pods poden intercanviar informació lliurement entre ells. Des del punt de vista de la seguretat, això pot semblar contrari a la intuïció, però recordeu que Kubernetes va ser creat originalment per desenvolupadors amb l'objectiu de fer que les aplicacions siguin interoperables. Les polítiques de xarxa es van afegir més tard.

Espais de noms

Els espais de noms són el mecanisme de col·laboració de Kubernetes. Estan dissenyats per aïllar entorns lògics entre si, alhora que permeten la comunicació entre espais per defecte.

Com la majoria dels components de Kubernetes, les polítiques de xarxa viuen en un espai de noms específic. Al bloc metadata podeu especificar a quin espai pertany la política:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: test-network-policy
  namespace: my-namespace  # <<<
spec:
...

Si l'espai de noms no s'especifica explícitament a les metadades, el sistema utilitzarà l'espai de noms especificat a kubectl (per defecte namespace=default):

kubectl apply -n my-namespace -f namespace.yaml

Recomano especificar l'espai de noms de manera explícita, tret que estigueu escrivint una política que s'orienti a diversos espais de noms alhora.

Primari l’element podSelector a la política seleccionarà pods de l'espai de noms al qual pertany la política (no té accés als pods des d'un altre espai de noms).

De la mateixa manera, podSelectors en blocs d'entrada i sortida només pot seleccionar pods del seu propi espai de noms, tret que, per descomptat, els combini amb namespaceSelector (Això s'explicarà a la secció "Filtrar per espais de noms i pods").

Normes de nomenclatura de polítiques

Els noms de les polítiques són únics dins del mateix espai de noms. No hi pot haver dues polítiques amb el mateix nom al mateix espai, però hi pot haver polítiques amb el mateix nom en espais diferents. Això és útil quan voleu tornar a aplicar la mateixa política en diversos espais.

M'agrada especialment un dels mètodes de denominació. Consisteix a concatenar el nom de l'espai de noms amb els pods de destinació. Per exemple:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.postgres  # <<<
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: postgres
  ingress:
  - from:
    - podSelector:
        matchLabels:
          app: admin
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Etiquetes

Les etiquetes personalitzades es poden adjuntar a objectes de Kubernetes, com ara pods i espais de noms. Etiquetes (etiquetes etiquetes) són l'equivalent a les etiquetes al núvol. Les polítiques de xarxa de Kubernetes utilitzen etiquetes per seleccionar beinesal que s'apliquen:

podSelector:
  matchLabels:
    role: db

… o espais de nomsals quals s'apliquen. Aquest exemple selecciona tots els pods dels espais de noms amb etiquetes coincidents:

namespaceSelector:
  matchLabels:
    project: myproject

Una advertència: quan s'utilitza namespaceSelector Assegureu-vos que els espais de noms que seleccioneu contenen l'etiqueta correcta. Tingueu en compte que els espais de noms integrats com ara default и kube-system, no contenen etiquetes per defecte.

Podeu afegir una etiqueta a un espai com aquest:

kubectl label namespace default namespace=default

En aquest cas, l'espai de noms de la secció metadata hauria de fer referència al nom real de l'espai, no a l'etiqueta:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: test-network-policy
  namespace: default   # <<<
spec:
...

Font i destinació

Les polítiques del tallafoc consisteixen en regles d'origen i de destinació. Les polítiques de xarxa de Kubernetes es defineixen per objectiu, el conjunt de pods als quals s'apliquen i, a continuació, estableixen regles per al trànsit d'entrada i/o sortida. En el nostre exemple, l'objectiu de la política seran tots els pods de l'espai de noms default amb etiqueta clau app i significat db:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: test-network-policy
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: db   # <<<
  policyTypes:
  - Ingress
  - Egress
  ingress:
  - from:
    - ipBlock:
        cidr: 172.17.0.0/16
        except:
        - 172.17.1.0/24
    - namespaceSelector:
        matchLabels:
          project: myproject
    - podSelector:
        matchLabels:
          role: frontend
    ports:
    - protocol: TCP
      port: 6379
  egress:
  - to:
    - ipBlock:
        cidr: 10.0.0.0/24
    ports:
    - protocol: TCP
      port: 5978

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat
Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Subsecció ingress en aquesta política obre el trànsit entrant als pods orientats. En altres paraules, l'entrada és l'origen i l'objectiu és la destinació corresponent. De la mateixa manera, la sortida és la destinació i l'objectiu és la seva font.

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Això equival a dues regles de tallafoc: Entrada → Destí; Destí → Sortida.

Sortida i DNS (important!)

Restringir el trànsit de sortida presteu especial atenció al DNS - Kubernetes utilitza aquest servei per assignar serveis a adreces IP. Per exemple, la política següent no funcionarà perquè no heu permès l'aplicació balance accedir al DNS:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.balance
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: balance
  egress:
  - to:
    - podSelector:
        matchLabels:
          app: postgres
  policyTypes:
  - Egress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Podeu solucionar-ho obrint l'accés al servei DNS:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.balance
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: balance
  egress:
  - to:
    - podSelector:
        matchLabels:
          app: postgres
  - to:               # <<<
    ports:            # <<<
    - protocol: UDP   # <<<
      port: 53        # <<<
  policyTypes:
  - Egress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Últim element to està buit, i per això tria indirectament tots els pods en tots els espais de noms, permetent balance Envieu consultes DNS al servei de Kubernetes adequat (normalment s'executa a l'espai kube-system).

Aquest enfocament funciona, però massa permissiu i insegur, perquè us permet dirigir consultes DNS fora del clúster.

Podeu millorar-lo en tres passos consecutius.

1. Permet només consultes DNS dins cluster afegint namespaceSelector:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.balance
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: balance
  egress:
  - to:
    - podSelector:
        matchLabels:
          app: postgres
  - to:
    - namespaceSelector: {} # <<<
    ports:
    - protocol: UDP
      port: 53
  policyTypes:
  - Egress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

2. Permet consultes DNS només a l'espai de noms kube-system.

Per fer-ho, heu d'afegir una etiqueta a l'espai de noms kube-system: kubectl label namespace kube-system namespace=kube-system - i registrar-lo a la política utilitzant namespaceSelector:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.balance
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: balance
  egress:
  - to:
    - podSelector:
        matchLabels:
          app: postgres
  - to:
    - namespaceSelector:         # <<<
        matchLabels:             # <<<
          namespace: kube-system # <<<
    ports:
    - protocol: UDP
      port: 53
  policyTypes:
  - Egress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

3. Les persones paranoiques poden anar més enllà i restringir les consultes DNS a un servei DNS específic kube-system. La secció "Filtra per espais de noms i pods" us mostrarà com aconseguir-ho.

Una altra opció és resoldre el DNS a nivell d'espai de noms. En aquest cas, no caldrà obrir-lo per a tots els serveis:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.dns
  namespace: default
spec:
  podSelector: {} # <<<
  egress:
  - to:
    - namespaceSelector: {}
    ports:
    - protocol: UDP
      port: 53
  policyTypes:
  - Egress

Buit podSelector selecciona tots els pods de l'espai de noms.

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Primer partit i ordre de regla

En els tallafocs convencionals, l'acció (Permetre o Denegar) en un paquet ve determinada per la primera regla que compleix. A Kubernetes, l'ordre de les polítiques no importa.

Per defecte, quan no s'estableixen polítiques, es permet la comunicació entre pods i poden intercanviar informació lliurement. Tan bon punt comenceu a formular polítiques, cada pod afectat per almenys una d'elles queda aïllada segons la disjunció (OR lògic) de totes les polítiques que l'han seleccionat. Les beines no afectades per cap política romanen obertes.

Podeu canviar aquest comportament amb una regla d'escombrat.

Regla de neteja ("Prohibeix")

Les polítiques del tallafoc solen negar qualsevol trànsit que no estigui permès explícitament.

Kubernetes no té una acció de "negació"., però, el mateix efecte es pot aconseguir amb una política normal (permissiva) seleccionant un grup buit de pods font (entrada):

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: deny-all
  namespace: default
spec:
  podSelector: {}
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Aquesta política selecciona tots els pods de l'espai de noms i deixa l'entrada sense definir, denegant tot el trànsit entrant.

De la mateixa manera, podeu restringir tot el trànsit sortint de l'espai de noms:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: deny-all-egress
  namespace: default
spec:
  podSelector: {}
  policyTypes:
  - Egress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Tingueu en compte que qualsevol política addicional que permeti el trànsit a pods a l'espai de noms tindrà prioritat sobre aquesta regla (semblant a afegir una regla d'autorització abans d'una regla de denegació a la configuració del tallafoc).

Permet tot (Qualsevol-Qualsevol-Qualsevol-Permet)

Per crear una política "Permetre-ho tot", heu de complementar la política de denegació anterior amb un element buit ingress:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-all
  namespace: default
spec:
  podSelector: {}
  ingress: # <<<
  - {}     # <<<
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Proporciona accés a tots els pods de tots els espais de noms (i totes les IP) a qualsevol pod de l'espai de noms default. Aquest comportament està habilitat per defecte, de manera que normalment no cal definir-lo més. Tanmateix, de vegades pot ser necessari desactivar temporalment determinats permisos específics per diagnosticar el problema.

La regla es pot reduir per permetre només l'accés un conjunt específic de beines (app:balance) a l'espai de noms default:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-all-to-balance
  namespace: default
spec:
  podSelector:
    matchLabels:
      app: balance
  ingress: 
  - {}
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

La política següent permet tot el trànsit d'entrada (entrada) I sortint (de sortida), inclòs l'accés a qualsevol IP fora del clúster:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-all
spec:
  podSelector: {}
  ingress:
  - {}
  egress:
  - {}
  policyTypes:
  - Ingress
  - Egress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat
Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Combinació de múltiples polítiques

Les polítiques estan lògicament OR a tres nivells; Els permisos de cada pod s'estableixen segons la disjunció de totes les polítiques que l'afecten:

1. Als camps from и to es poden definir tres tipus d'elements (tots combinats amb OR):

  • namespaceSelector - selecciona tot l'espai de noms;
  • podSelector - selecciona beines;
  • ipBlock - selecciona una subxarxa.

Al mateix temps, el nombre d'elements (fins i tot els mateixos) en subseccions from/to no limitat. Tots ells es combinaran amb un OR lògic.

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.postgres
  namespace: default
spec:
  ingress:
  - from:
    - podSelector:
        matchLabels:
          app: indexer
    - podSelector:
        matchLabels:
          app: admin
  podSelector:
    matchLabels:
      app: postgres
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

2. Secció de política interior ingress pot tenir molts elements from (combinat per OR lògic). De la mateixa manera, secció egress pot incloure molts elements to (també combinat per disjunció):

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.postgres
  namespace: default
spec:
  ingress:
  - from:
    - podSelector:
        matchLabels:
          app: indexer
  - from:
    - podSelector:
        matchLabels:
          app: admin
  podSelector:
    matchLabels:
      app: postgres
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

3. També es combinen diferents polítiques amb un OR lògic

Però quan es combinen, hi ha una restricció va assenyalar Chris Cooney: Kubernetes només pot combinar polítiques amb diferents policyTypes (Ingress o Egress). Les polítiques que defineixen l'entrada (o la sortida) es sobreescriuran mútuament.

Relació entre espais de noms

Per defecte, es permet l'intercanvi d'informació entre espais de noms. Això es pot canviar amb una política restrictiva que restringeix el trànsit sortint i/o entrant a l'espai de noms (vegeu "Regla d'escombrat" més amunt).

En bloquejar l'accés a un espai de noms (vegeu "Regla d'escombrat" anterior), podeu fer excepcions a la política de denegació si permeteu connexions des d'un espai de noms específic amb namespaceSelector:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: database.postgres
  namespace: database
spec:
  podSelector:
    matchLabels:
      app: postgres
  ingress:
  - from:
    - namespaceSelector: # <<<
        matchLabels:
          namespace: default
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Com a resultat, tots els pods de l'espai de noms default obtenir accés a les beines postgres a l'espai de noms database. Però què passa si voleu obrir l'accés postgres només pods específics a l'espai de noms default?

Filtra per espais de noms I pods

Kubernetes versió 1.11 i posterior us permet combinar operadors namespaceSelector и podSelector utilitzant AND lògic. Sembla això:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: database.postgres
  namespace: database
spec:
  podSelector:
    matchLabels:
      app: postgres
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          namespace: default
      podSelector: # <<<
        matchLabels:
          app: admin
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Per què s'interpreta com a AND en comptes de l'OR habitual?

Tingueu en compte que podSelector no comença amb un guionet. A YAML això vol dir que podSelector i dempeus davant seu namespaceSelector referir-se al mateix element de la llista. Per tant, es combinen amb un AND lògic.

Afegint un guió abans podSelector donarà lloc a un nou element de llista que es combinarà amb l'anterior namespaceSelector utilitzant l'OR lògic.

Per seleccionar beines amb una etiqueta específica en tots els espais de noms, introduïu buit namespaceSelector:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: database.postgres
  namespace: database
spec:
  podSelector:
    matchLabels:
      app: postgres
  ingress:
  - from:
    - namespaceSelector: {}
      podSelector:
        matchLabels:
          app: admin
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Múltiples etiquetes es combinen amb AND

Les regles del tallafoc amb múltiples entitats (amfitrions, xarxes, grups) es combinen mitjançant un OR lògic. La següent regla s'activarà si l'origen del paquet coincideix Host_1 O Host_2:

| Source | Destination | Service | Action |
| ----------------------------------------|
| Host_1 | Subnet_A    | HTTPS   | Allow  |
| Host_2 |             |         |        |
| ----------------------------------------|

Per contra, a Kubernetes hi ha diferents etiquetes podSelector o namespaceSelector es combinen amb un AND lògic. Per exemple, la regla següent seleccionarà pods que tinguin les dues etiquetes, role=db И version=v2:

podSelector:
  matchLabels:
    role: db
    version: v2

La mateixa lògica s'aplica a tots els tipus de declaracions: selectors d'objectius de política, selectors de pods i selectors d'espais de noms.

Subxarxes i adreces IP (IPBlocks)

Els tallafocs utilitzen VLAN, adreces IP i subxarxes per segmentar una xarxa.

A Kubernetes, les adreces IP s'assignen automàticament als pods i poden canviar amb freqüència, de manera que les etiquetes s'utilitzen per seleccionar pods i espais de noms a les polítiques de xarxa.

Subxarxes (ipBlocks) s'utilitzen per gestionar les connexions externes (nord-sud) d'entrada (entrada) o de sortida (sortida). Per exemple, aquesta política obre tots els pods de l'espai de noms default accés al servei DNS de Google:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: egress-dns
  namespace: default
spec:
  podSelector: {}
  policyTypes:
  - Egress
  egress:
  - to:
    - ipBlock:
        cidr: 8.8.8.8/32
    ports:
    - protocol: UDP
      port: 53

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

El selector de pods buit en aquest exemple significa "seleccioneu tots els pods de l'espai de noms".

Aquesta política només permet l'accés a 8.8.8.8; està prohibit l'accés a qualsevol altra IP. Per tant, en essència, heu bloquejat l'accés al servei DNS intern de Kubernetes. Si encara voleu obrir-lo, especifiqueu-lo explícitament.

En general ipBlocks и podSelectors s'exclouen mútuament, ja que les adreces IP internes dels pods no s'utilitzen ipBlocks. Assenyalant pods IP interns, en realitat permetreu connexions a/des de pods amb aquestes adreces. A la pràctica, no sabràs quina adreça IP utilitzar, i per això no hauries d'utilitzar-les per seleccionar pods.

Com a exemple contrari, la política següent inclou totes les IP i, per tant, permet l'accés a la resta de pods:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: egress-any
  namespace: default
spec:
  podSelector: {}
  policyTypes:
  - Egress
  egress:
  - to:
    - ipBlock:
        cidr: 0.0.0.0/0

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Només podeu obrir l'accés a les IP externes, excloses les adreces IP internes dels pods. Per exemple, si la subxarxa del vostre pod és 10.16.0.0/14:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: egress-any
  namespace: default
spec:
  podSelector: {}
  policyTypes:
  - Egress
  egress:
  - to:
    - ipBlock:
        cidr: 0.0.0.0/0
        except:
        - 10.16.0.0/14

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Ports i protocols

Normalment, els pods escolten en un port. Això vol dir que simplement podeu deixar de banda els números de port a les vostres polítiques i deixar-ho tot per defecte. Tanmateix, es recomana fer polítiques el més restrictives possible, de manera que en alguns casos encara podeu especificar ports:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.postgres
  namespace: default
spec:
  ingress:
  - from:
    - podSelector:
        matchLabels:
          app: indexer
    - podSelector:
        matchLabels:
          app: admin
    ports:             # <<<
      - port: 443      # <<<
        protocol: TCP  # <<<
      - port: 80       # <<<
        protocol: TCP  # <<<
  podSelector:
    matchLabels:
      app: postgres
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Tingueu en compte que el selector ports s'aplica a tots els elements del bloc to o from, que conté. Per especificar diferents ports per a diferents conjunts d'elements, trenca ingress o egress en diverses subseccions to o from i a cada un escriu els teus ports:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default.postgres
  namespace: default
spec:
  ingress:
  - from:
    - podSelector:
        matchLabels:
          app: indexer
    ports:             # <<<
     - port: 443       # <<<
       protocol: TCP   # <<<
  - from:
    - podSelector:
        matchLabels:
          app: admin
    ports:             # <<<
     - port: 80        # <<<
       protocol: TCP   # <<<
  podSelector:
    matchLabels:
      app: postgres
  policyTypes:
  - Ingress

Una introducció a les polítiques de xarxa de Kubernetes per a professionals de la seguretat

Els ports per defecte funcionen:

  • Si ometeu completament la definició de ports (ports), que vol dir tots els protocols i tots els ports;
  • Si ometeu la definició del protocol (protocol), que significa TCP;
  • Si ometeu la definició del port (port), que vol dir tots els ports.

Pràctica recomanada: no confieu en els valors predeterminats, especifiqueu el que necessiteu de manera explícita.

Tingueu en compte que heu d'utilitzar ports de pod, no serveis (més sobre això al paràgraf següent).

Polítiques definides per a pods o serveis?

Normalment, els pods de Kubernetes es comuniquen entre ells mitjançant un servei: un equilibrador de càrrega virtual que redirigeix ​​el trànsit als pods que implementen el servei. Podríeu pensar que les polítiques de xarxa controlen l'accés als serveis, però no és així. Les polítiques de xarxa de Kubernetes funcionen amb ports de pod, no amb serveis.

Per exemple, si un servei escolta al port 80, però redirigeix ​​el trànsit al port 8080 dels seus pods, heu d'especificar 8080 a la política de xarxa.

Aquest mecanisme s'ha de reconèixer com a subòptim: si el dispositiu intern del servei (els ports dels quals escolten pods) canvia, s'hauran d'actualitzar les polítiques de xarxa.

Nou enfocament arquitectònic mitjançant Service Mesh (per exemple, vegeu sobre Istio a continuació - traducció aprox.) permet fer front a aquest problema.

És necessari escriure tant Ingress com Egress?

La resposta breu és sí, perquè el pod A es comuniqui amb el pod B, heu de permetre que creï una connexió de sortida (per això cal configurar la política de sortida) i el pod B ha de poder acceptar una connexió entrant. (per a això, en conseqüència, necessiteu una política d'entrada).

Tanmateix, a la pràctica, podeu confiar en la política predeterminada per permetre connexions en una o ambdues direccions.

Si algun pod-font serà seleccionat per un o més sortida-polítics, les restriccions que se li imposaran vindran determinades per la seva disjunció. En aquest cas, haureu de permetre explícitament la connexió al poddestinatari. Si cap política no selecciona cap pod, el seu trànsit de sortida (de sortida) està permès de manera predeterminada.

De la mateixa manera, el destí dels pod'a-destinatariseleccionat per un o més ingrés-les polítiques es determinaran per la seva disjunció. En aquest cas, heu de permetre explícitament que rebi trànsit del pod d'origen. Si cap política no selecciona cap pod, tot el trànsit d'entrada es permet de manera predeterminada.

Vegeu "Stateful or Stateless" a continuació.

Registres

Les polítiques de xarxa de Kubernetes no saben com registrar el trànsit. Això fa que sigui difícil determinar si una política funciona com s'esperava i dificulta molt l'anàlisi de seguretat.

Control de trànsit a serveis externs

Les polítiques de xarxa de Kubernetes no us permeten especificar un nom de domini complet (DNS) a les seccions de sortida. Aquest fet comporta un inconvenient important quan s'intenta restringir el trànsit a destinacions externes que no tenen una adreça IP fixa (com ara aws.com).

Verificació de polítiques

Els tallafocs us advertiran o fins i tot es negaran a acceptar una política errònia. Kubernetes també fa algunes verificacions. Quan s'estableix una política de xarxa mitjançant kubectl, Kubernetes pot declarar que la política és incorrecta i negar-se a acceptar-la. En altres casos, Kubernetes agafarà la política i l'omplirà amb els detalls que falten. Els podeu veure amb l'ordre:

kubernetes get networkpolicy <policy-name> -o yaml

Tingueu en compte que el sistema de validació de Kubernetes no és infal·lible i pot perdre alguns tipus d'errors.

Execució

Kubernetes no fa complir les polítiques de xarxa per si mateix, sinó que és només una passarel·la d'API que posa la càrrega del control en un sistema subjacent anomenat Container Networking Interface (CNI). Establir polítiques en un clúster de Kubernetes sense assignar un CNI adequat és similar a establir polítiques en un servidor de gestió de tallafocs sense establir-les posteriorment als tallafocs. Depèn de tu assegurar-te de tenir un CNI digne o, en el cas de les plataformes Kubernetes, allotjat al núvol (Per obtenir una llista de proveïdors vegeu aquí -aprox. trans.), activeu les polítiques de xarxa que us configuraran el CNI.

Tingueu en compte que Kubernetes no us avisarà si configureu una política de xarxa sense el CNI auxiliar adequat.

Amb estat o sense estat?

Tots els CNI de Kubernetes que he trobat tenen estat (per exemple, Calico utilitza Linux conntrack). Això permet que el pod rebi respostes a la connexió TCP que va iniciar sense haver de restablir-la. Tanmateix, no conec un estàndard de Kubernetes que garanteixi l'estat.

Gestió avançada de polítiques de seguretat

A continuació es mostren algunes maneres de millorar l'eficiència de l'aplicació de polítiques de seguretat a Kubernetes:

  1. El patró arquitectònic de Service Mesh utilitza sidecars per proporcionar telemetria detallada i control de trànsit a nivell de servei. Com a exemple, es pot prendre Istio.
  2. Alguns dels proveïdors de CNI han ampliat les seves eines per anar més enllà de les polítiques de xarxa de Kubernetes.
  3. Tufin Orca proporciona transparència i automatització de les polítiques de xarxa de Kubernetes.

El paquet Tufin Orca gestiona les polítiques de xarxa de Kubernetes (i és la font de les captures de pantalla anteriors).

Дополнительная информация

Conclusió

Les polítiques de xarxa de Kubernetes ofereixen un bon conjunt d'eines per segmentar clústers, però no són intuïtives i tenen moltes subtileses. Crec que a causa d'aquesta complexitat, les polítiques de molts clústers existents tenen errors. Les possibles solucions a aquest problema són automatitzar les definicions de polítiques o utilitzar altres eines de segmentació.

Espero que aquesta guia us ajudi a aclarir algunes preguntes i a resoldre els problemes que us podeu trobar.

PS del traductor

Llegeix també al nostre blog:

Font: www.habr.com

Afegeix comentari