Aprovisiona y usa el almacenamiento en bloque sin procesar respaldado por SSD local


En esta página, se explica cómo aprovisionar almacenamiento SSD local en los clústeres de Google Kubernetes Engine (GKE) y cómo configurar las cargas de trabajo para que consuman datos del almacenamiento en bloque sin procesar respaldado por SSD local conectado a los nodos de tu clúster.

El uso de esta opción de SSD local te brinda más control sobre el almacenamiento subyacente y te permite compilar tu propia caché a nivel de nodo para que los Pods entreguen un mejor rendimiento de tus aplicaciones. También puedes personalizar esta opción si instalas un sistema de archivos en discos SSD locales si ejecutas un DaemonSet para configurar RAID y formatear los discos según sea necesario.

Para obtener más información sobre la compatibilidad con SSD locales para el acceso a bloques sin procesar en GKE, consulta la página acerca de SSD locales.

Antes de comenzar

Antes de comenzar, asegúrate de haber realizado las siguientes tareas:

  • Habilita la API de Kubernetes Engine.
  • Habilitar la API de Google Kubernetes Engine
  • Si deseas usar Google Cloud CLI para esta tarea, instala y, luego, inicializa gcloud CLI. Si ya instalaste gcloud CLI, ejecuta gcloud components update para obtener la versión más reciente.

Crea un clúster o un grupo de nodos con almacenamiento en bloque sin procesar respaldado por SSD local

Usa la CLI de gcloud con la opción --local-nvme-ssd-block para crear un clúster con almacenamiento en bloque sin procesar respaldado por SSD local.

El comando de la CLI de gcloud que ejecutas para crear el clúster o grupo de nodos depende de la generación de series de máquinas a la que pertenece el tipo de máquina que usas. Por ejemplo, los tipos de máquinas N1 y N2 pertenecen a una serie de máquinas de primera y segunda generación, respectivamente, mientras que los tipos de máquinas C3 pertenecen a una serie de máquinas de tercera generación.

Crea un clúster con SSD local

Primera o segunda generación

Si usas un tipo de máquina de una serie de máquinas de primera o segunda generación, especifica tu opción --local-nvme-ssd-block count=NUMBER_OF_DISKS para crear el clúster. La opción especifica la cantidad de discos SSD locales que se conectarán a cada nodo. La cantidad máxima varía según el tipo de máquina y la región.

Para crear un clúster, sigue estos pasos:

gcloud container clusters create CLUSTER_NAME \
    --local-nvme-ssd-block count=NUMBER_OF_DISKS \
    --machine-type=MACHINE_TYPE \
    --release-channel CHANNEL_NAME

Reemplaza lo siguiente:

  • CLUSTER_NAME: el nombre del clúster
  • NUMBER_OF_DISKS: es la cantidad de discos SSD locales que se aprovisionarán en cada nodo. La cantidad máxima de discos varía según el tipo de máquina y la región.
  • MACHINE_TYPE: Es el tipo de máquina de primera o segunda generación que se usará. Debes especificar este campo, ya que no puedes usar SSD locales con el tipo e2-medium predeterminado.
  • CHANNEL_NAME: Un canal de versiones que incluye versiones de GKE posteriores a la 1.25.3-gke.1800.

Tercera generación

Si usas un tipo de máquina de una serie de máquinas de tercera generación, usa la opción --local-nvme-ssd-block, sin un campo de recuento, para crear un clúster. GKE aprovisiona de forma automática la capacidad de SSD local para tu clúster según la forma de VM. La cantidad máxima varía según el tipo de máquina y la región.

gcloud container clusters create CLUSTER_NAME \
    --machine-type=MACHINE_TYPE \
    --cluster-version CLUSTER_VERSION \
    --local-nvme-ssd-block

Reemplaza lo siguiente:

  • CLUSTER_NAME: el nombre del clúster
  • MACHINE_TYPE: el tipo de máquina que se usará de una serie de máquinas de tercera generación.
  • CLUSTER_VERSION: una versión de clúster de GKE que admite SSD locales en tipos de máquinas de una serie de máquinas de tercera generación.

Crea un grupo de nodos con SSD locales

Primera o segunda generación

Para crear un grupo de nodos que use discos SSD locales para el acceso sin procesar del bloque, ejecuta el siguiente comando:

gcloud container node-pools create POOL_NAME \
    --cluster=CLUSTER_NAME \
    --machine-type=MACHINE_TYPE \
    --local-nvme-ssd-block count=NUMBER_OF_DISKS

Reemplaza lo siguiente:

  • POOL_NAME: el nombre de tu grupo de nodos nuevo.
  • CLUSTER_NAME: el nombre del clúster
  • MACHINE_TYPE: Es el tipo de máquina de primera o segunda generación que se usará. Debes especificar este campo, ya que la SSD local no se puede usar con el tipo predeterminado e2-medium.
  • NUMBER_OF_DISKS: es la cantidad de discos SSD locales que se aprovisionarán en cada nodo. La cantidad máxima de discos varía según el tipo de máquina y la región.

Tercera generación

Si usas un tipo de máquina de una serie de máquinas de tercera generación, usa la opción --local-nvme-ssd-block, sin un campo de recuento, para crear un clúster:

gcloud container node-pools create POOL_NAME \
    --cluster=CLUSTER_NAME \
    --machine-type=MACHINE_TYPE \
    --node-version NODE_VERSION \
    --local-nvme-ssd-block

Reemplaza lo siguiente:

  • POOL_NAME: el nombre del grupo de nodos nuevo
  • CLUSTER_NAME: el nombre del clúster
  • MACHINE_TYPE: el tipo de máquina que se usará desde un tipo de máquina de tercera generación.
  • NODE_VERSION: Es una versión de grupo de nodos de GKE que admite SSD locales en tipos de máquinas de una serie de máquinas de tercera generación.

Los nodos en el grupo de nodos se crean con una etiqueta cloud.google.com/gke-local-nvme-ssd=true. Para verificar las etiquetas, ejecuta el siguiente comando:

kubectl describe node NODE_NAME

Para cada SSD local conectado al grupo de nodos, el SO host crea un vínculo simbólico (symlink) para acceder al disco en una carpeta ordinal y un symlink con un identificador único universal (UUID). Por ejemplo, si creas un grupo de nodos con tres SSD locales mediante la opción --local-nvme-ssd-block, el SO host crea los siguientes symlinks para los discos:

  • /dev/disk/by-id/google-local-ssd-block0
  • /dev/disk/by-id/google-local-ssd-block1
  • /dev/disk/by-id/google-local-ssd-block2

Del mismo modo, el SO host también crea los siguientes symlinks con UUID para los discos:

  • /dev/disk/by-uuid/google-local-ssds-nvme-block/local-ssd-GENERATED_UUID1
  • /dev/disk/by-uuid/google-local-ssds-nvme-block/local-ssd-GENERATED_UUID2
  • /dev/disk/by-uuid/google-local-ssds-nvme-block/local-ssd-GENERATED_UUID3

Esto garantiza que se pueda acceder a los discos mediante un identificador único.

Accede a los volúmenes SSD locales

En el siguiente ejemplo, se muestra cómo acceder al almacenamiento en bloque sin procesar respaldado por SSD local.

PersistentVolumes locales

Los volúmenes de SSD locales se pueden activar como Pods mediante PersistentVolumes.

Puedes crear PersistentVolumes desde SSD locales si creas un PersistentVolume de forma manual o si ejecutas el aprovisionador estático de volumen local.

Limitaciones de PersistentVolumes locales

  • Los objetos PersistentVolume locales no se limpian de forma automática cuando se borra, actualiza, repara o reduce la escala de un nodo. Te recomendamos analizar y borrar de forma periódica los objetos PersistentVolumes locales obsoletos asociados con los nodos borrados.

Crea el PersistentVolume de forma manual

Puedes crear un PersistentVolume de forma manual para todas las SSD locales de cada nodo del clúster.

Usa el campo nodeAffinity en un objeto PersistentVolume para hacer referencia a una SSD local en un nodo específico. En el siguiente ejemplo, se muestra la especificación de PersistentVolume para SSD local en nodos que ejecutan Linux:

apiVersion: v1
kind: PersistentVolume
metadata:
  name: "example-local-pv"
spec:
  capacity:
    storage: 375Gi
  accessModes:
  - "ReadWriteOnce"
  persistentVolumeReclaimPolicy: "Retain"
  storageClassName: "local-storage"
  local:
    path: "/mnt/disks/ssd0"
  nodeAffinity:
    required:
      nodeSelectorTerms:
      - matchExpressions:
        - key: "kubernetes.io/hostname"
          operator: "In"
          values:
          - "gke-test-cluster-default-pool-926ddf80-f166"

En este ejemplo, los discos SSD locales se configuran manualmente para RAID y se les da formato y, luego, se activan en /mnt/disks/ssd0 en el nodo gke-test-cluster-default-pool-926ddf80-f166. El campo nodeAffinity se usa para ayudar a asignar cargas de trabajo a los nodos con SSD locales que se configuran de forma manual para RAID. Si solo tienes un nodo en tu clúster o si configuraste RAID para todos los nodos, no es necesario el campo nodeAffinity.

La especificación de PersistenVolumeClaim correspondiente se ve de la siguiente manera:

  kind: PersistentVolumeClaim
  apiVersion: v1
  metadata:
    name: ssd-local-claim
  spec:
    accessModes:
    - ReadWriteOnce
    storageClassName: local-storage
    resources:
      requests:
        storage: 37Gi

Si borras el PersistentVolume, deberás borrar de forma manual los datos del disco.

Ejecuta el aprovisionador estático de volumen local

Puedes crear PersistentVolumes para SSD locales de forma automática con el aprovisionador estático de volumen local. El aprovisionador es un DaemonSet que administra los discos SSD locales en cada nodo, crea y borra PersistentVolumes para estos y limpia los datos en la SSD local cuando se libera el PersistentVolume.

Para ejecutar el aprovisionador estático de volumen local, haz lo siguiente:

  1. Usa un DaemonSet para configurar RAID y formatear los discos:

    1. Descarga la especificación gke-daemonset-raid-disks.yaml.
    2. Implementa los discos de raid DaemonSet. El DaemonSet establece un array RAID 0 en todos los discos SSD locales y formatea el dispositivo a un sistema de archivos ext4.

      kubectl create -f gke-daemonset-raid-disks.yaml
      
  2. Descarga la especificación gke-nvme-ssd-block-raid.yaml y modifica los campos de espacio de nombres de la especificación según sea necesario.

    La especificación incluye estos recursos:

    • ServiceAccount para el aprovisionador
    • ClusterRole y ClusterRoleBindings con permiso para realizar lo siguiente:
      • Crear y borrar los objetos PersistentVolume
      • Obtener objetos del nodo
    • ConfigMap con la configuración del aprovisionador para GKE
    • DaemonSet para ejecutar el aprovisionador
  3. Implementa el aprovisionador:

    kubectl create -f gke-nvme-ssd-block-raid.yaml
    

    Una vez que el aprovisionador se ejecuta de manera correcta, crea un objeto PersistentVolume para el dispositivo SSD local RAID en el clúster.

  4. Guarda el siguiente manifiesto de PersistentVolumeClaim como provisioner-pvc-example.yaml:

    kind: PersistentVolumeClaim
    apiVersion: v1
    metadata:
      name: PVC_NAME
    spec:
      accessModes:
      - ReadWriteOnce
      resources:
        requests:
          storage: 50Gi
      storageClassName: nvme-ssd-block
    

    Reemplaza PVC_NAME por el nombre de la PersistentVolumeClaim.

  5. Crea la PersistentVolumeClaim:

    kubectl create -f provisioner-pvc-example.yaml
    
  6. Guarda el siguiente manifiesto del Pod como provisioner-pod-example.yaml:

    apiVersion: v1
    kind: Pod
    metadata:
      name: POD_NAME
    spec:
      containers:
      - name: "shell"
        image: "ubuntu:14.04"
        command: ["/bin/sh", "-c"]
        args: ["echo 'hello world' > /cache/test.txt && sleep 1 && cat /cache/test.txt && sleep 3600"]
        volumeMounts:
        - mountPath: /cache
          name: local-ssd-storage
      volumes:
      - name: local-ssd-storage
        persistentVolumeClaim:
          claimName: PVC_NAME
    

    Reemplaza POD_NAME por el nombre del Pod.

  7. Crea el Pod:

    kubectl create -f provisioner-pod-example.yaml
    

Habilita la vinculación de volumen demorada

Para mejorar la programación, te recomendamos que crees una StorageClass con volumeBindingMode: WaitForFirstConsumer. Esto demora la vinculación de PersistentVolumeClaim hasta la programación del pod, de modo que se elige una SSD local de un nodo apropiado que pueda ejecutar el Pod. Este comportamiento de programación mejorado considera las solicitudes de CPU y memoria de Pods, la afinidad de nodos, la afinidad y la antiafinidad de Pods, y las solicitudes de varias PersistentVolumeClaim, junto con los nodos que tienen SSD locales disponibles, cuando seleccionas un nodo para un pod ejecutable.

En este ejemplo, se usa el modo de vinculación de volumen demorado:

apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
  name: "local-nvme"
provisioner: "kubernetes.io/no-provisioner"
volumeBindingMode: "WaitForFirstConsumer"

Para crear una StorageClass con vinculación demorada, guarda el manifiesto YAML en un archivo local y aplícalo al clúster mediante el siguiente comando:

kubectl apply -f filename

Soluciona problemas

Si deseas obtener instrucciones para solucionar problemas, consulta Soluciona problemas de almacenamiento en GKE.

¿Qué sigue?