Blog

OpenShift Data Foundation (ODF) : stockage unifié avec Ceph sur OpenShift

OpenShift
ODF
Ceph
Stockage
S3

Déploiement et configuration d'OpenShift Data Foundation (ODF), basé sur Ceph, pour fournir du stockage bloc, fichier et objet natif sur OpenShift. Installation via l'Operator, StorageClasses, Noobaa S3 et monitoring.

5 mars 2025

OpenShift Data Foundation : le socle de stockage intégré d’OpenShift

OpenShift Data Foundation (ODF) est la solution de stockage software-defined de Red Hat, intégrée nativement à OpenShift. Basée sur Ceph (le projet de stockage distribué CNCF) et NooBaa (stockage objet multi-cloud), ODF fournit les trois modes de stockage en un seul déploiement :

  • Bloc (RBD)ReadWriteOnce, idéal pour les bases de données
  • Fichier (CephFS)ReadWriteMany, pour les workloads qui partagent des volumes
  • Objet (S3) — via NooBaa MultiCloud Gateway, compatible S3

ODF est la solution recommandée par Red Hat pour les déploiements OpenShift bare-metal et vSphere avec des besoins en stockage persistant à haute disponibilité.


Prérequis

  • Minimum 3 nœuds de stockage dédiés (ou workers) avec des disques raw non formatés
  • Au moins 3 disques de 500 Go minimum par nœud de stockage (SSD recommandé)
  • Les nœuds de stockage doivent être labellisés
# Labelliser les nœuds destinés au stockage ODF
oc label nodes worker-storage-1 worker-storage-2 worker-storage-3 \
  cluster.ocs.openshift.io/openshift-storage=''

# Vérifier
oc get nodes -l cluster.ocs.openshift.io/openshift-storage=

Installation via l’Operator ODF

# Créer le namespace
oc create namespace openshift-storage

# Installer l'Operator ODF
cat <<EOF | oc apply -f -
apiVersion: operators.coreos.com/v1alpha1
kind: Subscription
metadata:
  name: odf-operator
  namespace: openshift-storage
spec:
  channel: stable-4.16
  installPlanApproval: Automatic
  name: odf-operator
  source: redhat-operators
  sourceNamespace: openshift-marketplace
EOF

Attendre que l’Operator soit prêt :

oc wait csv -n openshift-storage \
  -l operators.coreos.com/odf-operator.openshift-storage \
  --for=condition=Succeeded \
  --timeout=300s

Créer le StorageSystem

Le StorageSystem instancie l’ensemble de la stack ODF (Ceph + NooBaa).

apiVersion: odf.openshift.io/v1alpha1
kind: StorageSystem
metadata:
  name: ocs-storagecluster-storagesystem
  namespace: openshift-storage
spec:
  kind: storagecluster.ocs.openshift.io/v1
  name: ocs-storagecluster
  namespace: openshift-storage
---
apiVersion: ocs.openshift.io/v1
kind: StorageCluster
metadata:
  name: ocs-storagecluster
  namespace: openshift-storage
spec:
  storageDeviceSets:
    - name: ocs-deviceset
      count: 1                          # 1 set par nœud de stockage
      replica: 3                        # Réplication triple
      resources:
        requests:
          cpu: "2"
          memory: 5Gi
        limits:
          cpu: "4"
          memory: 10Gi
      placement:
        nodeAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
            nodeSelectorTerms:
              - matchExpressions:
                  - key: cluster.ocs.openshift.io/openshift-storage
                    operator: In
                    values: ['']
      dataPVCTemplate:
        spec:
          accessModes: [ReadWriteOnce]
          resources:
            requests:
              storage: 500Gi            # Taille de chaque OSD
          storageClassName: ""          # Utiliser les disques locaux
          volumeMode: Block
  multiCloudGateway:
    reconcileStrategy: standalone       # NooBaa standalone
  monDataDirHostPath: /var/lib/rook

StorageClasses créées par ODF

Après installation, ODF crée automatiquement les StorageClasses suivantes :

oc get storageclass | grep ocs

# ocs-storagecluster-ceph-rbd         → Bloc (ReadWriteOnce)
# ocs-storagecluster-cephfs           → Fichier (ReadWriteMany)
# ocs-storagecluster-ceph-rgw         → Objet (S3 via RADOS Gateway)
# openshift-storage.noobaa.io         → Objet (S3 via NooBaa)

Définir ODF comme StorageClass par défaut

# Retirer le statut default de la StorageClass actuelle
oc patch storageclass standard \
  -p '{"metadata": {"annotations": {"storageclass.kubernetes.io/is-default-class": "false"}}}'

# Définir ODF RBD comme défaut
oc patch storageclass ocs-storagecluster-ceph-rbd \
  -p '{"metadata": {"annotations": {"storageclass.kubernetes.io/is-default-class": "true"}}}'

Utiliser les différents modes de stockage

Bloc (RBD) — base de données PostgreSQL

apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: postgres-data
  namespace: production
spec:
  accessModes:
    - ReadWriteOnce
  storageClassName: ocs-storagecluster-ceph-rbd
  resources:
    requests:
      storage: 100Gi
  volumeMode: Filesystem

Fichier (CephFS) — volume partagé multi-pods

apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: shared-assets
  namespace: production
spec:
  accessModes:
    - ReadWriteMany             # Plusieurs pods peuvent monter ce volume
  storageClassName: ocs-storagecluster-cephfs
  resources:
    requests:
      storage: 50Gi

Objet S3 via NooBaa — bucket applicatif

# Créer un ObjectBucketClaim (OBC)
apiVersion: objectbucket.io/v1alpha1
kind: ObjectBucketClaim
metadata:
  name: mon-bucket-app
  namespace: production
spec:
  generateBucketName: mon-bucket-app
  storageClassName: openshift-storage.noobaa.io
  additionalConfig:
    bucketclass: noobaa-default-bucket-class

L’OBC crée automatiquement un ConfigMap et un Secret avec les credentials S3 :

# Récupérer les credentials
oc get configmap mon-bucket-app -n production -o yaml
# Contient : BUCKET_NAME, BUCKET_PORT, BUCKET_REGION, BUCKET_HOST

oc get secret mon-bucket-app -n production -o yaml
# Contient : AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY

NooBaa MultiCloud Gateway : fédération S3

NooBaa permet de créer une façade S3 unifiée qui abstraite plusieurs backends de stockage (ODF, AWS S3, Azure Blob, GCS).

# BucketClass qui répartit les données entre ODF et AWS S3
apiVersion: noobaa.io/v1alpha1
kind: BucketClass
metadata:
  name: spread-bucketclass
  namespace: openshift-storage
spec:
  placementPolicy:
    tiers:
      - backingStores:
          - odf-backing-store        # Stockage local ODF
          - aws-s3-backing-store     # Backup AWS S3
        placement: Spread            # Répartition entre les deux
---
# BackingStore AWS S3
apiVersion: noobaa.io/v1alpha1
kind: BackingStore
metadata:
  name: aws-s3-backing-store
  namespace: openshift-storage
spec:
  type: aws-s3
  awsS3:
    bucketName: mon-bucket-aws-backup
    region: eu-west-1
    secret:
      name: aws-s3-credentials
      namespace: openshift-storage

Snapshots de volumes

ODF supporte les VolumeSnapshot Kubernetes natifs.

# Créer un VolumeSnapshotClass
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshotClass
metadata:
  name: ocs-storagecluster-rbdplugin-snapclass
driver: openshift-storage.rbd.csi.ceph.com
deletionPolicy: Delete
parameters:
  clusterID: openshift-storage
  csi.storage.k8s.io/snapshotter-secret-name: rook-csi-rbd-provisioner
  csi.storage.k8s.io/snapshotter-secret-namespace: openshift-storage
---
# Prendre un snapshot
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshot
metadata:
  name: snapshot-postgres-2025-03-05
  namespace: production
spec:
  volumeSnapshotClassName: ocs-storagecluster-rbdplugin-snapclass
  source:
    persistentVolumeClaimName: postgres-data

Dashboard et monitoring

ODF s’intègre nativement au dashboard OpenShift et expose des métriques Prometheus.

# Accéder au dashboard ODF
oc get route -n openshift-storage | grep console

# Métriques clés à surveiller
# ceph_cluster_total_used_bytes / ceph_cluster_total_bytes  → utilisation globale
# ceph_osd_stat_bytes_used                                  → utilisation par OSD
# ceph_health_status                                        → 0=OK, 1=WARN, 2=ERR
# noobaa_system_capacity_percent                            → capacité NooBaa

# Vérifier l'état du cluster Ceph
oc exec -n openshift-storage \
  $(oc get pod -n openshift-storage -l app=rook-ceph-tools -o name) \
  -- ceph status

Conclusion

OpenShift Data Foundation fournit une solution de stockage complète et intégrée pour les clusters OpenShift : bloc pour les bases de données, fichier pour les workloads partagés, et objet S3 via NooBaa. Son intégration native avec OpenShift (dashboard, Prometheus, RBAC) en fait l’option naturelle pour les équipes qui veulent éviter la complexité opérationnelle de solutions tierces tout en bénéficiant de la maturité de Ceph.