HOWTO

Kubernetes 에서 Wordpress + MySQL 구성하기 (Persistent Volume)

한크크 2019. 1. 9. 09:25
반응형
Pods 에서 Persistent volume 을 사용하기 위해 각 Node 마다 50GB 볼륨을 할당하고 마운트 한다. (예제에서는 /data001 로 마운트 함)

아래 구성에서 Kubernetes 환경은 네이버클라우드플랫폼 싱가폴 리전에서 VM 으로 구성했으며, CNI 는 Calico 로 구성하였다.


1. PV (Persistent Volume) 생성

PV 는 K8S 관리자가 설정하는 클러스터의 저장소로 사용자가 PVC 를 생성하기 위해 설정해 두는 물리적인 공간이라고 볼 수 있다. 
지금 구성에서는 K8S Cluster 를 스스로 운영하기 때문에 PV 설정이 필요하고, GKE 와 같이 Cluster 를 구성해 주는 서비스의 경우 PVC 만 설정해서 사용하면 된다.

50GB 파일시스템을 마운트 했으므로 25GB 짜리 PV 를 2개 생성한다.  

# vi pv1.yaml


kind: PersistentVolume
apiVersion: v1
metadata:
  name: pv0001
  labels:
    type: local
spec:
  capacity:
    storage: 25Gi
  accessModes:
    - ReadWriteOnce
  hostPath:

    path: "/data001/pv0001" 


# vi pv2.yaml

kind: PersistentVolume
apiVersion: v1
metadata:
  name: pv0002
  labels:
    type: local
spec:
  capacity:
    storage: 25Gi
  accessModes:
    - ReadWriteOnce
  hostPath:

    path: "/data001/pv0002"


# kubectl create -f pv1.yaml

# kubectl create -f pv2.yaml

# kubectl get pv
NAME     CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS      CLAIM   STORAGECLASS   REASON   AGE
pv0001   25Gi       RWO            Retain           Available                                   8s
pv0002   25Gi       RWO            Retain           Available                                   5s                                   



2. PVC (Persistent Volume Claim) 생성 

PVC 는 사용자가 Pod 를 만들면서 요청하는 스토리지로 PV 가 있어야 생성된다. 별도로 PV 를 지정하지 않아도  PV 에 알아서 할당된다. 

Wordpress 와 MySQL 이 각각 다른 PVC 를 사용하도록 생성한다.  


# vi wordpress-volumeclaim.yaml


kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: wordpress-volumeclaim
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:

      storage: 10Gi 


# vi mysql-volumeclaim.yaml


kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: mysql-volumeclaim
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:

      storage: 10Gi 


# kubectl create wordpress-volumeclaim.yaml

# kubectl create mysql-volumeclaim.yaml

# kubectl get pvc
NAME                    STATUS   VOLUME   CAPACITY   ACCESS MODES   STORAGECLASS   AGE
mysql-volumeclaim       Bound    pv0002   25Gi       RWO                           4s
wordpress-volumeclaim   Bound    pv0001   25Gi       RWO                           12s 



3. MySQL Root 패스워드 저장

mysql root 패스워드를 mysql-password 라는 secret object 에 저장한다.  


# kubectl create secret generic mysql-password --from-literal=password=rP@ssw0rd


# kubectl describe secret mysql-password
Name:         mysql-password
Namespace:    default
Labels:       <none>
Annotations:  <none>

Type:  Opaque

Data
====
password:  9 bytes 



4. MySQL Pod 배포

MySQL 이 설치된 Pod 를 배포하면서 Database , User, User password 도 함께 설정해준다. 

아래 예제에서 k8suser 의 패스워드를 노출했는데 위 Root 패스워드의 설정과 같이 secret 오브젝트 형태로 저장해도 된다.  

# vi mysql.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: mysql
  labels:
    app: mysql
spec:
  replicas: 1
  selector:
    matchLabels:
      app: mysql
  template:
    metadata:
      labels:
        app: mysql
    spec:
      containers:
        - image: mysql:5.6
          name: mysql
          env:
            - name: MYSQL_ROOT_PASSWORD
              valueFrom:
                secretKeyRef:
                  name: mysql-password
                  key: password
            - name: MYSQL_DATABASE # 구성할 database명
              value: k8sdb
            - name: MYSQL_USER # database에 권한이 있는 user
              value: k8suser
            - name: MYSQL_ROOT_HOST # 접근 호스트
              value: '%'  
            - name: MYSQL_PASSWORD # database에 권한이 있는 user의 패스워드
              value: P@ssw0rd!!
          ports:
            - containerPort: 3306
              name: mysql
          volumeMounts:
            - name: mysql-persistent-storage
              mountPath: /var/lib/mysql
      volumes:
        - name: mysql-persistent-storage
          persistentVolumeClaim:
            claimName: mysql-volumeclaim 


# kubectl get pods -o wide

NAME                         READY   STATUS    RESTARTS   AGE     IP               NODE      NOMINATED NODE
mysql-86bb7c99f9-62jmj       1/1     Running   0          3m28s   172.27.116.214   c2node3   <none> 



5. MySQL 서비스 생성

앞에서 생성한 MySQL 컨테이너를 노출하기 위해 서비스를 생성하고 뒤에서 생성할 Wordpress 컨테이너가 접근할 수 있도록 설정한다.  


# vi mysql-service.yaml


apiVersion: v1

kind: Service
metadata:
  name: mysql
  labels:
    app: mysql
spec:
  type: ClusterIP
  ports:
    - port: 3306
  selector:
    app: mysql 


# kubectl create -f mysql-service.yaml

# kubectl get svc -o wide
NAME         TYPE           CLUSTER-IP       EXTERNAL-IP   PORT(S)        AGE     SELECTOR

mysql        ClusterIP      172.20.12.226    <none>        3306/TCP       3m40s   app=mysql



6. Wordpress Pod 배포

wordpress pod 배포 파일에는 MySQL 접근이 가능한 정보가 포함되어야 한다.  


# vi wordpress.yaml


apiVersion: apps/v1

kind: Deployment
metadata:
  name: wordpress
  labels:
    app: wordpress
spec:
  replicas: 1
  selector:
    matchLabels:
      app: wordpress
  template:
    metadata:
      labels:
        app: wordpress
    spec:
      containers:
        - image: wordpress
          name: wordpress
          env:
          - name: WORDPRESS_DB_HOST
            value: mysql:3306
          - name: WORDPRESS_DB_NAME
            value: k8sdb
          - name: WORDPRESS_DB_USER
            value: k8suser
          - name: WORDPRESS_DB_PASSWORD
            value: P@ssw0rd!!
          ports:
            - containerPort: 80
              name: wordpress
          volumeMounts:
            - name: wordpress-persistent-storage
              mountPath: /var/www/html
      volumes:
        - name: wordpress-persistent-storage
          persistentVolumeClaim:
            claimName: wordpress-volumeclaim 


# kubectl get pods -o wide

NAME                         READY   STATUS    RESTARTS   AGE     IP               NODE      NOMINATED NODE
mysql-86bb7c99f9-62jmj       1/1     Running   0          3m28s   172.27.116.214   c2node3   <none>

wordpress-7ff695b6c6-vp5rc   1/1     Running   0          2m52s   172.27.116.215   c2node3   <none>



7. Wordpress 서비스 배포

Kubernetes Pod IP 를 사설 IP 로 설정하여 직접 접근이 불가하므로 Node IP 와 Node Port 를 통해 접근할 수 있도록 Wordpress 서비스를 기동한다.  


# vi wordpress-service.yaml


apiVersion: v1
kind: Service
metadata:
  labels:
    app: wordpress
  name: wordpress
spec:
  type: NodePort
  ports:
    - port: 80
      targetPort: 80
      protocol: TCP
  selector:

    app: wordpress


# kubectl get svc -o wide

NAME         TYPE           CLUSTER-IP       EXTERNAL-IP   PORT(S)        AGE     SELECTOR
mysql        ClusterIP      172.20.12.226    <none>        3306/TCP       3m40s   app=mysql

wordpress    NodePort       172.17.70.243   <none>        80:31776/TCP   26s    app=wordpress


8. Wordpress 웹 접속 및 설정 

Wordpress 가 기동된 Pod 의 노드 IP 와 Wordpress 서비스의 Node Port 로 웹 브라우저를 통해 접속한다. 

아래와 같은 페이지가 노출되면 정상적으로 서비스 구성이 완료된 것이다.  



반응형