OpenShift Storage¶
Overview¶
OpenShift provides persistent storage for applications using Persistent Volumes (PV), Persistent Volume Claims (PVC), and Storage Classes.
Storage Types¶
Persistent Volume (PV)¶
Cluster-level storage resource provisioned by administrator.
Persistent Volume Claim (PVC)¶
Request for storage by a user/application.
Storage Class¶
Dynamic provisioning template for storage.
Storage Classes¶
List Storage Classes¶
Default Storage Class¶
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: standard
annotations:
storageclass.kubernetes.io/is-default-class: "true"
provisioner: kubernetes.io/aws-ebs
parameters:
type: gp2
fsType: ext4
Creating PVC¶
Basic PVC¶
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: myapp-pvc
namespace: myproject
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 10Gi
storageClassName: standard
Using CLI¶
Access Modes¶
| Mode | Abbreviation | Description |
|---|---|---|
| ReadWriteOnce | RWO | Single node read-write |
| ReadOnlyMany | ROX | Multiple nodes read-only |
| ReadWriteMany | RWX | Multiple nodes read-write |
Using Storage in Pods¶
Mount PVC in Deployment¶
apiVersion: apps/v1
kind: Deployment
metadata:
name: myapp
spec:
replicas: 1
selector:
matchLabels:
app: myapp
template:
metadata:
labels:
app: myapp
spec:
containers:
- name: myapp
image: myapp:latest
volumeMounts:
- name: data
mountPath: /data
volumes:
- name: data
persistentVolumeClaim:
claimName: myapp-pvc
Dynamic Provisioning¶
AWS EBS¶
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: aws-ebs
provisioner: kubernetes.io/aws-ebs
parameters:
type: gp3
iops: "3000"
throughput: "125"
encrypted: "true"
Azure Disk¶
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: azure-disk
provisioner: kubernetes.io/azure-disk
parameters:
storageaccounttype: Premium_LRS
kind: Managed
NFS¶
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: nfs
provisioner: example.com/nfs
parameters:
server: nfs-server.example.com
path: /exports
Static Provisioning¶
Create PV¶
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv-nfs
spec:
capacity:
storage: 100Gi
accessModes:
- ReadWriteMany
persistentVolumeReclaimPolicy: Retain
nfs:
server: nfs-server.example.com
path: /exports/data
Create Matching PVC¶
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: pvc-nfs
spec:
accessModes:
- ReadWriteMany
resources:
requests:
storage: 50Gi
volumeName: pv-nfs
Volume Snapshots¶
Create VolumeSnapshotClass¶
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshotClass
metadata:
name: csi-snapclass
driver: ebs.csi.aws.com
deletionPolicy: Delete
Create Snapshot¶
apiVersion: snapshot.storage.k8s.io/v1
kind: VolumeSnapshot
metadata:
name: myapp-snapshot
spec:
volumeSnapshotClassName: csi-snapclass
source:
persistentVolumeClaimName: myapp-pvc
Restore from Snapshot¶
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: myapp-restored
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 10Gi
dataSource:
name: myapp-snapshot
kind: VolumeSnapshot
apiGroup: snapshot.storage.k8s.io
ConfigMaps and Secrets as Volumes¶
ConfigMap Volume¶
apiVersion: v1
kind: ConfigMap
metadata:
name: app-config
data:
config.json: |
{
"key": "value"
}
---
apiVersion: v1
kind: Pod
metadata:
name: myapp
spec:
containers:
- name: myapp
image: myapp:latest
volumeMounts:
- name: config
mountPath: /etc/config
volumes:
- name: config
configMap:
name: app-config
Secret Volume¶
apiVersion: v1
kind: Secret
metadata:
name: app-secret
type: Opaque
data:
password: cGFzc3dvcmQ=
---
apiVersion: v1
kind: Pod
metadata:
name: myapp
spec:
containers:
- name: myapp
image: myapp:latest
volumeMounts:
- name: secret
mountPath: /etc/secret
readOnly: true
volumes:
- name: secret
secret:
secretName: app-secret
EmptyDir Volumes¶
Temporary Storage¶
apiVersion: v1
kind: Pod
metadata:
name: myapp
spec:
containers:
- name: myapp
image: myapp:latest
volumeMounts:
- name: cache
mountPath: /cache
volumes:
- name: emptyDir
emptyDir: {}
Managing Storage¶
CLI Commands¶
# List PVCs
oc get pvc
# Describe PVC
oc describe pvc myapp-pvc
# Delete PVC
oc delete pvc myapp-pvc
# Expand PVC (if supported)
oc patch pvc myapp-pvc -p '{"spec":{"resources":{"requests":{"storage":"20Gi"}}}}'
# View PV
oc get pv
Storage Troubleshooting¶
Check PVC Status¶
# Get PVC status
oc get pvc myapp-pvc
# Common statuses:
# - Pending: Waiting for provisioning
# - Bound: Successfully bound to PV
# - Lost: PV no longer exists
Debug Storage Issues¶
# Check events
oc get events --field-selector involvedObject.name=myapp-pvc
# Check storage class
oc describe sc standard
# Verify pod mounting
oc describe pod myapp-pod
Best Practices¶
- Use Storage Classes: Leverage dynamic provisioning
- Right-Size: Request appropriate storage sizes
- Access Modes: Choose correct access mode for workload
- Backup: Implement regular snapshot/backup strategy
- Monitoring: Monitor storage usage and performance
- Reclaim Policy: Set appropriate reclaim policies
- Encryption: Enable encryption for sensitive data