Skip to main content
Se proporciona el idioma español mediante traducción automática para su comodidad. En caso de alguna inconsistencia, el inglés precede al español.

Utilizar la topología CSI

Colaboradores netapp-aruldeepa

Trident puede crear y adjuntar volúmenes de forma selectiva a los nodos presentes en un clúster de Kubernetes mediante el uso de "Función de topología CSI" .

Descripción general

Al utilizar la función de topología CSI, el acceso a los volúmenes se puede limitar a un subconjunto de nodos, según las regiones y las zonas de disponibilidad. Actualmente, los proveedores de servicios en la nube permiten a los administradores de Kubernetes crear nodos basados en zonas. Los nodos pueden ubicarse en diferentes zonas de disponibilidad dentro de una región o en varias regiones. Para facilitar el aprovisionamiento de volúmenes para cargas de trabajo en una arquitectura multizona, Trident utiliza la topología CSI.

Consejo Obtenga más información sobre la función de topología CSI. "aquí" .

Kubernetes proporciona dos modos únicos de enlace de volúmenes:

  • Con VolumeBindingMode empezar a Immediate Trident crea el volumen sin tener en cuenta la topología. La vinculación de volúmenes y el aprovisionamiento dinámico se gestionan cuando se crea el PVC. Este es el valor predeterminado VolumeBindingMode y es adecuado para clústeres que no imponen restricciones de topología. Los volúmenes persistentes se crean sin depender de los requisitos de programación del pod solicitante.

  • Con VolumeBindingMode empezar a WaitForFirstConsumer La creación y el enlace de un volumen persistente para un PVC se retrasan hasta que se programa y se crea un pod que utiliza el PVC. De esta manera, se crean volúmenes para cumplir con las restricciones de programación impuestas por los requisitos de topología.

Nota El WaitForFirstConsumer El modo de enlace no requiere etiquetas de topología. Esto se puede utilizar independientemente de la función de topología CSI.
Lo que necesitarás

Para utilizar la topología CSI, necesita lo siguiente:

  • Un clúster de Kubernetes que ejecuta un"Versión de Kubernetes compatible"

    kubectl version
    Client Version: version.Info{Major:"1", Minor:"19", GitVersion:"v1.19.3", GitCommit:"1e11e4a2108024935ecfcb2912226cedeafd99df", GitTreeState:"clean", BuildDate:"2020-10-14T12:50:19Z", GoVersion:"go1.15.2", Compiler:"gc", Platform:"linux/amd64"}
    Server Version: version.Info{Major:"1", Minor:"19", GitVersion:"v1.19.3", GitCommit:"1e11e4a2108024935ecfcb2912226cedeafd99df", GitTreeState:"clean", BuildDate:"2020-10-14T12:41:49Z", GoVersion:"go1.15.2", Compiler:"gc", Platform:"linux/amd64"}
  • Los nodos del clúster deben tener etiquetas que indiquen la topología.(topology.kubernetes.io/region y topology.kubernetes.io/zone ). Estas etiquetas deben estar presentes en los nodos del clúster antes de instalar Trident para que Trident tenga en cuenta la topología.

    kubectl get nodes -o=jsonpath='{range .items[*]}[{.metadata.name}, {.metadata.labels}]{"\n"}{end}' | grep --color "topology.kubernetes.io"
    [node1, {"beta.kubernetes.io/arch":"amd64","beta.kubernetes.io/os":"linux","kubernetes.io/arch":"amd64","kubernetes.io/hostname":"node1","kubernetes.io/os":"linux","node-role.kubernetes.io/master":"","topology.kubernetes.io/region":"us-east1","topology.kubernetes.io/zone":"us-east1-a"}]
    [node2, {"beta.kubernetes.io/arch":"amd64","beta.kubernetes.io/os":"linux","kubernetes.io/arch":"amd64","kubernetes.io/hostname":"node2","kubernetes.io/os":"linux","node-role.kubernetes.io/worker":"","topology.kubernetes.io/region":"us-east1","topology.kubernetes.io/zone":"us-east1-b"}]
    [node3, {"beta.kubernetes.io/arch":"amd64","beta.kubernetes.io/os":"linux","kubernetes.io/arch":"amd64","kubernetes.io/hostname":"node3","kubernetes.io/os":"linux","node-role.kubernetes.io/worker":"","topology.kubernetes.io/region":"us-east1","topology.kubernetes.io/zone":"us-east1-c"}]

Paso 1: Crear un backend que tenga en cuenta la topología

Los sistemas de almacenamiento Trident pueden diseñarse para aprovisionar volúmenes de forma selectiva en función de las zonas de disponibilidad. Cada backend puede incluir una opción. supportedTopologies bloque que representa una lista de zonas y regiones admitidas. Para las StorageClasses que utilizan dicho backend, solo se creará un volumen si lo solicita una aplicación programada en una zona o región compatible.

Aquí tenéis un ejemplo de definición de backend:

YAML
---
version: 1
storageDriverName: ontap-san
backendName: san-backend-us-east1
managementLIF: 192.168.27.5
svm: iscsi_svm
username: admin
password: password
supportedTopologies:
  - topology.kubernetes.io/region: us-east1
    topology.kubernetes.io/zone: us-east1-a
  - topology.kubernetes.io/region: us-east1
    topology.kubernetes.io/zone: us-east1-b
JSON
{
  "version": 1,
  "storageDriverName": "ontap-san",
  "backendName": "san-backend-us-east1",
  "managementLIF": "192.168.27.5",
  "svm": "iscsi_svm",
  "username": "admin",
  "password": "password",
  "supportedTopologies": [
    {
      "topology.kubernetes.io/region": "us-east1",
      "topology.kubernetes.io/zone": "us-east1-a"
    },
    {
      "topology.kubernetes.io/region": "us-east1",
      "topology.kubernetes.io/zone": "us-east1-b"
    }
  ]
}
Nota `supportedTopologies`Se utiliza para proporcionar una lista de regiones y zonas por backend. Estas regiones y zonas representan la lista de valores permitidos que se pueden proporcionar en una StorageClass. Para las StorageClasses que contienen un subconjunto de las regiones y zonas proporcionadas en un backend, Trident crea un volumen en el backend.

Puedes definir supportedTopologies por cada grupo de almacenamiento también. Vea el siguiente ejemplo:

---
version: 1
storageDriverName: ontap-nas
backendName: nas-backend-us-central1
managementLIF: 172.16.238.5
svm: nfs_svm
username: admin
password: password
supportedTopologies:
  - topology.kubernetes.io/region: us-central1
    topology.kubernetes.io/zone: us-central1-a
  - topology.kubernetes.io/region: us-central1
    topology.kubernetes.io/zone: us-central1-b
storage:
  - labels:
      workload: production
    supportedTopologies:
      - topology.kubernetes.io/region: us-central1
        topology.kubernetes.io/zone: us-central1-a
  - labels:
      workload: dev
    supportedTopologies:
      - topology.kubernetes.io/region: us-central1
        topology.kubernetes.io/zone: us-central1-b

En este ejemplo, el region y zone Las etiquetas indican la ubicación del depósito de almacenamiento. topology.kubernetes.io/region y topology.kubernetes.io/zone dictar desde dónde se pueden consumir los grupos de almacenamiento.

Paso 2: Defina las StorageClasses que tengan en cuenta la topología.

En función de las etiquetas de topología que se proporcionan a los nodos del clúster, se pueden definir StorageClasses para que contengan información de topología. Esto determinará los grupos de almacenamiento que sirven como candidatos para las solicitudes de PVC realizadas, y el subconjunto de nodos que pueden utilizar los volúmenes aprovisionados por Trident.

Vea el siguiente ejemplo:

apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata: null
name: netapp-san-us-east1
provisioner: csi.trident.netapp.io
volumeBindingMode: WaitForFirstConsumer
allowedTopologies:
  - matchLabelExpressions: null
  - key: topology.kubernetes.io/zone
    values:
      - us-east1-a
      - us-east1-b
  - key: topology.kubernetes.io/region
    values:
      - us-east1
parameters:
  fsType: ext4

En la definición de StorageClass proporcionada anteriormente, volumeBindingMode está configurado para WaitForFirstConsumer . Los PVC que se soliciten con esta StorageClass no se procesarán hasta que se haga referencia a ellos en un pod. Y, allowedTopologies proporciona las zonas y la región que se utilizarán. El netapp-san-us-east1 StorageClass crea PVC en el san-backend-us-east1 Backend definido anteriormente.

Paso 3: Crear y usar un PVC

Una vez creada la StorageClass y asignada a un backend, ya puede crear PVC.

Vea el ejemplo spec abajo:

---
kind: PersistentVolumeClaim
apiVersion: v1
metadata: null
name: pvc-san
spec: null
accessModes:
  - ReadWriteOnce
resources:
  requests:
    storage: 300Mi
storageClassName: netapp-san-us-east1

La creación de un PVC utilizando este manifiesto daría como resultado lo siguiente:

kubectl create -f pvc.yaml
persistentvolumeclaim/pvc-san created
kubectl get pvc
NAME      STATUS    VOLUME   CAPACITY   ACCESS MODES   STORAGECLASS          AGE
pvc-san   Pending                                      netapp-san-us-east1   2s
kubectl describe pvc
Name:          pvc-san
Namespace:     default
StorageClass:  netapp-san-us-east1
Status:        Pending
Volume:
Labels:        <none>
Annotations:   <none>
Finalizers:    [kubernetes.io/pvc-protection]
Capacity:
Access Modes:
VolumeMode:    Filesystem
Mounted By:    <none>
Events:
  Type    Reason                Age   From                         Message
  ----    ------                ----  ----                         -------
  Normal  WaitForFirstConsumer  6s    persistentvolume-controller  waiting for first consumer to be created before binding

Para que Trident cree un volumen y lo una al PVC, utilice el PVC en una cápsula. Vea el siguiente ejemplo:

apiVersion: v1
kind: Pod
metadata:
  name: app-pod-1
spec:
  affinity:
    nodeAffinity:
      requiredDuringSchedulingIgnoredDuringExecution:
        nodeSelectorTerms:
        - matchExpressions:
          - key: topology.kubernetes.io/region
            operator: In
            values:
            - us-east1
      preferredDuringSchedulingIgnoredDuringExecution:
      - weight: 1
        preference:
          matchExpressions:
          - key: topology.kubernetes.io/zone
            operator: In
            values:
            - us-east1-a
            - us-east1-b
  securityContext:
    runAsUser: 1000
    runAsGroup: 3000
    fsGroup: 2000
  volumes:
  - name: vol1
    persistentVolumeClaim:
      claimName: pvc-san
  containers:
  - name: sec-ctx-demo
    image: busybox
    command: [ "sh", "-c", "sleep 1h" ]
    volumeMounts:
    - name: vol1
      mountPath: /data/demo
    securityContext:
      allowPrivilegeEscalation: false

Esta especificación de pod indica a Kubernetes que programe el pod en los nodos que están presentes en el us-east1 región, y elige cualquier nodo que esté presente en la us-east1-a o us-east1-b zonas.

Vea el siguiente resultado:

kubectl get pods -o wide
NAME        READY   STATUS    RESTARTS   AGE   IP               NODE              NOMINATED NODE   READINESS GATES
app-pod-1   1/1     Running   0          19s   192.168.25.131   node2             <none>           <none>
kubectl get pvc -o wide
NAME      STATUS   VOLUME                                     CAPACITY   ACCESS MODES   STORAGECLASS          AGE   VOLUMEMODE
pvc-san   Bound    pvc-ecb1e1a0-840c-463b-8b65-b3d033e2e62b   300Mi      RWO            netapp-san-us-east1   48s   Filesystem

Actualizar los backends para incluir supportedTopologies

Los sistemas backend preexistentes se pueden actualizar para incluir una lista de supportedTopologies usando tridentctl backend update . Esto no afectará a los volúmenes que ya se hayan aprovisionado y solo se utilizará para los PVC posteriores.