Skip to content

aws-ebs-csi-driver

Permissions

IRSA

  • The controller runs on the worker nodes, so it needs access to the AWS EBS APIs with IAM permissions
  • The IAM permissions can either be setup using IAM roles for service accounts (IRSA) (preferred) or can be attached directly to the worker node IAM roles

  • AWS managed policy: AmazonEBSCSIDriverPolicy

# Create an OIDC provider
eksctl utils associate-iam-oidc-provider --cluster=attractive-gopher --approve

# Create IRSA
eksctl create iamserviceaccount \
  --name ebs-csi-controller-sa \
  --cluster foo \
  --namespace kube-system \
  --attach-policy-arn arn:aws:iam::aws:policy/service-role/AmazonEBSCSIDriverPolicy \
  --approve

Node Role

  • Another option (not recommended) is to attach the ebs policy directly to the role of the ec2 instances of the worker nodes
# Get the ARN policy of the worker nodes
kubectl describe cm/aws-auth -n kube-system

# Attach the ebs policy to the worker node role
aws iam attach-role-policy \
  --role-name "eksctl-foo-nodegroup-my-node-gro-NodeInstanceRole-tZDjAGAMF9gm" \
  --policy-arn "arn:aws:iam::aws:policy/service-role/AmazonEBSCSIDriverPolicy"

Installation

set account_id (aws sts get-caller-identity --query Account --output text)
eksctl create addon \
  --name aws-ebs-csi-driver \
  --cluster foo \
  --service-account-role-arn arn:aws:iam::$account_id:role/AmazonEKS_EBS_CSI_DriverRole
# Verify ebs-csi pods running
kubectl get po -n kube-system

# A "csidrivers" object is created
kubectl get csidrivers
  • Another option (not recommended) is to deploy the csi objects directly
kubectl apply -k "github.com/kubernetes-sigs/aws-ebs-csi-driver/deploy/kubernetes/overlays/stable/?ref=master"

Kubernetes Objects

  • After the driver is deployed you need to apply a StorageClass with the provisioner kubernetes.io/aws-ebs on the cluster
  • Then claim the volume (PVC) via the SC, this way a PV will be created automatically
  • The EBS volume is created with the name foo-dynamic-pvc-34bc1e7b-c864-4667-92bd-1141e114297c
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
  name: ebs-sc
provisioner: ebs.csi.aws.com
volumeBindingMode: WaitForFirstConsumer # waits for the pod to attach the volume for creating it
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: my-pvc
spec:
  storageClassName: ebs-sc
  resources:
    requests:
      storage: 4Gi # It's the AWS EBS Volume
  accessModes:
    - ReadWriteOnce
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: foo
spec:
  replicas: 1
  strategy:
    type: Recreate
  selector:
    matchLabels:
      app: foo
  template:
    metadata:
      labels:
        app: foo
    spec:
      containers:
        - image: nginx
          name: nginx-container
          volumeMounts:
            - name: my-storage
              mountPath: /mnt
      volumes:
        - name: my-storage
          persistentVolumeClaim:
            claimName: my-pvc