kok202
쿠버네티스 입문 - 08 - 볼륨

2020. 4. 8. 23:40[정리] 기능별 개념 정리/Kubernetes

볼륨

컨테이너는 기본적으로 상태가 없는 앱 컨테이너를 사용한다.

컨테이너가 실행 되지 않거나 삭제되었을 때 현재까지 저장한 데이터가 사라진다.

한편 앱의 특성에 따라 컨테이너에 문제가 생겨도 데이터를 보존해야할 때가 있다.

대표적인 예가 데이터를 파일로 저장하는 젠킨스, 데이터베이스인 MySQL 등이 있다.

이럴 때 볼륨을 사용한다.

 

볼륨 관련 필드중에 .spec.container.volumeMounts.mountPropagation 이 있다.

이 설정을 이용하면 파드 하나 안의 컨테이너들끼리 볼륨을 공유할지 같은 노드 안의 파드들 끼리 볼륨을 공유할지 설정할 수 있다.

이는 다음 3가지 타입을 가진다.

  • None
    호스트에서 해당 볼륨 하위에 마운트 된 다른 디렉토리들은 해당 볼륨이 볼 수 없게한다.
    컨테이너가 만들어 놓은 마운트를 호스트에서도 볼 수 없다. 
  • HostToContainer
    호스트에서 해당 볼륨 하위에 마운트 된 다른 디렉토리들은 해당 볼륨이 볼 수 있게한다.
  • Bidirectional
    호스트에서 해당 볼륨 하위에 마운트 된 다른 디렉토리들은 해당 볼륨이 볼 수 있게한다.
    호스트 안의 다른 컨테이너나 파드에서 같은 볼륨을 사용할 수 있다.

 

 

 

볼륨 플러그인

쿠버네티스 에서 사용할 수 있는 볼륨 플러그인에는 몇가지가 있다. 

대표적인 3가지는 아래 가지가 있다.

  • empty
  • hostPath
  • NFS 서버

 

 

 

emptyDir

호스트의 디스크를 임시로 컨테이너 볼륨에 할당해서 사용한다.

파드가 사라지면 emprtDir 에 할당했던 컨테이너 볼륨의 데이터도 사라진다.

단순히 컨테이너를 재시작 했을 때 데이터를 보존하는 역할이다.

메모리와 디스크를 함께 이용하는 대용량 데이터 계산을 하는 경우와 연산 결과를 중간 데이터 저장용으로 디스크가 필요할 때 사용한다.

apiVersion: v1
kind: Pod
metadata:
  name: kubernetes-simple-pod
spec:
  containers:
  - name: kubernetes-simple-pod
    image: arisu1000/simple-container-app:latest
    volumeMounts:
    - mountPath: /emptydir
      name: emptydir-vol
    ports:
    - containerPort: 8080
  volumes:
  - name: emptydir-vol
    emptyDir: {}

 

 

 

hostPath 

파드가 실행된 호스트의 파일이나 디렉토리를 파드에 마운트한다.

컨테이너 재시작시 데이터를 보존하는 역할이다.

apiVersion: v1
kind: Pod
metadata:
  name: kubernetes-hostpath-pod
spec:
  containers:
  - name: kubernetes-hostpath-pod
    image: arisu1000/simple-container-app:latest
    volumeMounts:
    - mountPath: /test-volume
      name: hostpath-vol
    ports:
    - containerPort: 8080
  volumes:
  - name: hostpath-vol
    hostPath:
      path: /tmp
      type: Directory

 

 

 

NFS 서버 

NFS 볼륨은 기존에 사용하는 NFS 서버를 파드에 마운트한다.

.spec.containers[].securityContext 는 컨테이너의 보안 설정을 한다.

컨테이너가 실행중인 호스트 장치의 접근권한을 설정하는 priviledged 필드값으로 모든 호스트 장치에 접근할 수 있도록 할 수 있다.

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nfs-server
  labels:
    app: nfs-server
spec:
  replicas: 1
  selector:
    matchLabels:
      app: nfs-server
  template:
    metadata:
      labels:
        app: nfs-server
    spec:
      containers:
      - name: nfs-server
        image: arisu1000/nfs-server:latest
        ports:
        - name: nfs
          containerPort: 2049
        - name: mountd
          containerPort: 20048
        - name: rpcbind
          containerPort: 111
        securityContext:
          privileged: true
        volumeMounts:
        - mountPath: /exports
          name: hostpath-vol
      volumes:
      - name: hostpath-vol
        hostPath:
          path: /tmp
          type: Directory

 

 

 

PV (Persistent Volume) 와 PVC (Persistent Volume Claim)

실무에서는 볼륨을 구성해서 마운트 할 때는 Deployment 에 볼륨을 생성하진 않는다.

PV 로 마운트 해서 안정성을 높인다.

NFS 서버 접근도 NFS 서버용 파드에 바로 접근하는게 아니라 서비스를 생성해서 연결한다.

 

쿠버네티스에서 볼륨을 사용하는 구조는 PV 와 PVC 를 분리하여 사용한다.

쿠버네티스는 볼륨을 파드에 직접 할당하는 게 아니라 중간에 PVC 를 둬서 파드와 파드가 사용할 스토리지를 분리한다.

파드에서 직접 연결하는 것이 아니라 PVC를 거치므로 파드는 어떤 스토리지를 사용하는지 신경쓰지 않아도 된다.

 

 

 

PV

쿠버네티스 볼륨 자체

클러스터 안에서 자원을 다룬다.

파드하고는 별개의 생명주기를 가진다.

 

 

 

PVC

사용자가. PV 에 하는 요청

사용하고 싶은 용량은, 읽기/쓰기 모드 설정등을 요청한다.

 

 

 

 

PV와 PVC 의 생명주기

  1. 프로비저닝
    PV 를 만드는 단계.
    정적 방법 : PV 를 미리 만들어두고 사용하는 방법. 사용할 수 있는 스토리지 용량에 제한이 있을 때 유용하다.
    동적 방법 : PV 를 요청이 있을 때마다 만드는 방법. 사용자가 PVC 를 거쳐서 PV 를 요쳥할 때 생성해서 제공한다.
  2. 바인딩
    프로비저닝으로 PV를 PVC 로 연결하는 단계
    PVC 에서 원하는 스토리지의 용량과 접근 방법을 명시하면 이에 맞는 PV 가 할당된다.
    PV 와 PVC 는 1 대 1 매핑관계다.
  3. 사용
    할당된 PVC 를 파드를 유지하는 동안 사용한다. 시스템에서 임의로 삭제할 수 없다.
  4. 반환
    PVC 는 삭제되고 PVC 를 사용하던. PV 를 초기화 하는 단계
     - Retain : PV 를 그대로 보존한다. PV 는 해제 상태가 되고 PVC 가 재사용할 수 없다. 그대로 데이터가 PV 안에 남으므로 PV 를 재사용하려면 관리자가 수기로 초기화 해줘야한다.
     - Delete : PV 를 삭제하고 연결된 외부 스토리지 쪽 볼륨도 삭제한다.
     - Recycle : PV 의 데이터들을 삭제하고 새로운 PVC 에 PV 를 사용할 수 있게 해준다. (다만 해당 타입은 곧 지원 종료될 예정이다.)

 

 

 

PV 샘플

apiVersion: v1
kind: PersistentVolume
metadata:
  name: pv-hostpath
spec:
  capacity:
    storage: 2Gi
  volumeMode: Filesystem
  accessModes:
  - ReadWriteOnce
  storageClassName: manual
  persistentVolumeReclaimPolicy: Delete
  hostPath:
    path: /tmp/k8s-pv

.spec.capacity.storage : PV 의 용량

.spec.accessModes : PV 의 읽기/쓰기 설정

.spec.storageClassName : PV 에 스토리지 클래스를 설정, 해당 클래스에 맞는 PVC와만 연결된다.

.spec.persistentVolumeReclaimPolicy : PV 가 해제 되었으 ㄹ때 초기화 옵션을 설정한다. Retain, Recycle, Delete 중 하나를 설정한다.

.spec.hostPath  PV 의 볼륨 플러그인을 명시한다.

 

 

 

PVC 샘플

kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: pvc-hostpath
spec:
  accessModes:
  - ReadWriteOnce
  volumeMode: Filesystem
  resources:
    requests:
      storage: 1Gi
  storageClassName: manual

.spec.resources.requests.storage : 자원을 얼마나 요청할 것인가.

 

 

 

파드에서 PVC 로 PV 사용하기 샘플

apiVersion: apps/v1
kind: Deployment
metadata:
  name: kubernetes-simple-app
  labels:
    app: kubernetes-simple-app
spec:
  replicas: 1
  selector:
    matchLabels:
      app: kubernetes-simple-app
  template:
    metadata:
      labels:
        app: kubernetes-simple-app
    spec:
      containers:
      - name: kubernetes-simple-app
        image: arisu1000/simple-container-app:latest
        ports:
        - containerPort: 8080
        imagePullPolicy: Always
        volumeMounts:
        - mountPath: "/tmp"
          name: myvolume
      volumes:
      - name: myvolume
        persistentVolumeClaim:
          claimName: pvc-hostpath

.spec.volumes[].persistentVolumeClaim : 사용할 PVC 를 설정한다.

 

 

 

 

 

 

기타

PV는 쿠버네티스 안에서 사용되는 자원이다.

PVC 는 해당 자원을 사용하겠다고 요청하는 것이다.

파드와 서비스를 연결할 때처럼 레이블 / 셀렉터를 사용할 수도 있다.

https://github.com/arisu1000/kubernetes-book-sample/blob/master/volume/pv-hostpath-label.yaml

https://github.com/arisu1000/kubernetes-book-sample/blob/master/volume/pvc-hostpath-label.yaml