데이터를 영구적으로 저장하는 매커니즘 Persistent Storage

PV / PVC 의 주요 개념

PV (Persistent Volume)

  • K8s 어드민이 설정한 클러스터 레벨의 스토리지 볼륨군이며, 클러스터 리소스의 일ㅈ오.
  • 관리자가 프로비저닝하거나 Storage Class를 통해 동적으로 프로비저닝 됨
  • 일반 볼륨과의 차이점
    • 일반 볼륨은 Pod와 같은 라이프사이클을 가짐. 함께 생성되고 함께 내려간다는 뜻
    • PV는 Pod와 별개의 라이프사이클을 가지므로, Pod가 종료되어도 PV에 기록된 데이터는 삭제되지 않음

PV 생성하기

# ex) pv-definition.yaml

apiVersion: v1
kind: PersistentVolume
metadata:
	name: pv-vol-1
spec:
	accessModes: # 스토리지 볼륨 접근 방식
		- ReadWriteOnce 
		
	capacity:
		storage: 1Gi # PV로 선점하고자 하는 용량
		
	# 볼륨 타입 정의
	hostPath:   # hostPath 는 해당 노드의 local directory이므로, 프로덕션에서는 권장되지 않음.
		path: /tmp/data
		
	awsElasticBlockStore:
		volumeID: <volume-id>
		fsType: ext4
  • 생성: kubectl create -f pv-definition.yaml
  • 조회: kubectl get persistentvolume

accessModes 유형

  • ReadOnlyMany
  • ReadWriteOnce
  • ReadWriteMany

PVC (Persistent Volume Claim)

  • Persistent Volume (PV) 을 사용할 수 있게끔 유저가 생성하는 오브젝트
  • PVC가 생성되면 K8s는 이를 기반으로 PVC에서 요청한 기준에 부합하는 (그리고 용량이 여유가 있는) PV를 찾아 PVC 와 바인드(bind) 함
  • 만일 조건에 부합하는 PV가 여러개 존재하는 경우에는 label과 selector를 써서 매칭 함
  • 만일 최적의 매칭 조합을 찾지 못해 PVC에서 정의된 용량보다 더 큰 용량의 PV와 바인드가 되면, 남아도는 용량은 다른 PVC가 사용할 수 없게 됨 (PV와 PVC는 1:1 매칭)
  • 이후 더 이상 가용할 수 있는 PV가 없는 상태에서 PVC가 생성되면, 매칭 가능한 PV가 추가되기 전까지는 바인딩이 pending 됨.
  • 만일 다음과 같이 생성된 PV가 유일한 PV이고, 이어서 PVC가 생성된다면, 용량은 부합하지 않지만, 다른 선택지가 없으므로 매칭됨.

PVC 생성하기

PV 정의 및 생성

# ex) pv-definition.yaml

apiVersion: v1
kind: PersistentVolume
metadata:
	name: pv-vol-1
spec:
	accessModes: 
		- ReadWriteOnce 
		
	capacity:
		storage: 1Gi 
		
	awsElasticBlockStore:
		volumeID: <volume-id>
		fsType: ext4
		
	persistentVolumeReclaimPolicy: Retain # default

PV에 매칭되는 PVC 정의

# ex) pvc-definition.yaml

apiVersion: v1
kind: PersistentVolumeClaim
metadata:
	name: myclaim
spec:
	accessModes:
		- ReadWriteOnce
		
	resources:
		requests:
			storage: 500Mi
  • 생성: kubectl -f pvc-definition.yaml
  • 조회: kubectl get persistentvolumeclaim

PVC 바인딩 방법

  • PVC를 사용하고자 할 때, Pod 정의는 아래 yaml 파일과 같음.
  • ReplicaSet과 Deployment에서도 동일하게 적용
# ex) pod-definition.yaml

apiVersion: v1
kind: Pod
metadata:
	name: random-number-generator

spec:
	containers:
		- image: alpine
			name: alpine
			command: ["/bin/sh", "-c"]
			args: ["shuf -i 0-100 -n 1 >> /opt/number.out;"]
			volumeMounts:
				- mountPath: /opt
					name: data-volume
			
	# 볼륨 생성
	volumes:
		- name: random-number-generator
		
			persistentVolumeClaim:
				claimName: myclaim

PVC 삭제

  • 삭제: kubectl delete persistentvolumeclaime <pvc-name>

단, PVC가 삭제되더라도 persistentVolumeReclaimPolicy: Retain 으로 설정되어 있기 때문에, 매뉴얼로 삭제하지 않는 한, PV는 삭제되지 않음.

persistentVolumeReclaimPolicy: Delete 으로 설정된 경우, PVC가 삭제되면 PV도 함께 삭제됨.

PV / PVC 의 라이프사이클 (Lifecycle of a volume)

2.1. 프로비저닝

  • 정적 프로비저닝
    • 스토리지 기술을 명세해서 PV를 사전에 만드는 방식
    • 리소스가 한정된 온프레미스 환경에서 사용
    • PV 생성 이후 PV 리소스를 사용하겠다는 PVC를 생성
      • PVC에서 storageClassName: '' 의 설정 유의
      • 미리 생성한 PV 안에서 가능한 PV를 바인딩하겠다는 뜻
    • 이후 Pod에서 PVC를 참조하면 PV를 사용할 수 있게 됨
    • Note:
      • PVC를 설정하지 않고, Pod 생성 시 곧장 PV를 참조할 수도 있음
      • PVC 활용은 기존 Storage의 기술을 자세히 알지 못 하더라도 PV만 명시하면 K8s가 알아서 자원을 할당시켜주기 때문에 용이함. (따라서 권장사항)
  • 동적 프로비저닝
    • PV 프로비저너를 배포하고 storage class만 명시하면 동적으로 프로비저닝 함.
    • PVC에서 stroageClassName만 제공하면 프로비저너가 알아서 PV를 생성해주고 PVC와 연결도 해줌.
    • GKE를 비롯한 Cloud Service에서는 PV 프로비저너를 제공함.

2.2. 바인딩

  • PV와 PVC가 연결되는 동작.
  • 정적 프로비저닝
    • PVC를 배포하면 쿠버네티스가 가능한 PV안에서 PVC를 바인딩해줌.
    • 동적 프로비저닝의 경우는 Storage Class의 Provisioner가 PV를 동적으로 생성하고 PVC와 바인딩해줌.

2.3. 사용, 사용 중

  • 바인딩 이후로 PV는 Pod에 속해 사용 됨.

2.4. 반환 (Reclaiming)

  • 볼륨을 다 사용한 뒤, 리소스 반환 API를 사용해 PVC 오브젝트를 삭제할 수 있음.
  • PVC의 반환
    1. 볼륨에서 클레임 해제
    2. 볼륨에 수행할 작업을 클러스터에 알려줌
  • 볼륨의 반환 정책
    • Retain
      • 리소스를 수동으로 반환하는 정책
      • PVC삭제되어도 PV는 존재하기에, 관리자가 수동으로 볼륨을 반환해야 함
    • Delete
      • PV와 외부 인프라 등, 관련된 스토리지 자산을 모두 삭제함.
      • 동적 프로비저닝 된 볼륨의 경우에는 Storage Class의 반환 정책을 상속받음.
    • Recycle (deprecated)

Reference

Persistent Volumes

쿠버네티스(k8s) Persistent Storage란?