kubeflow를 급히 써봐야 할 일이 있어서 minikube 환경에서 설치를 해보려고 했는데...

 

주위에 계신 어떤 한 분이 손쉽게 성공하셨다고 하셔서 나도 그렇게 될거라 믿고 해봤는데,

뭔가의 이유로 잘 진행이 되지 않아서 짜증이 솓구쳐서 결국은 Kubernetes 환경에서 진행했다.

 

 

이하 포스팅은 설치 가이드라기 보다는

Kubeflow 설치 성공한 과정에 대한 기록이다.

 

 

0. Kubernetes

- 다음 링크의 포스트와 동일한 방법으로 설치된 환경이다.

  . https://www.whatwant.com/entry/Kubernetes-Install-1

 

단, 이 때 Kubernetes를 설치한 3대 VM의 Spec은 좀 높여야 한다.

Memory가 부족하면 Kubeflow 설치가 안된다.

memory

 

Processor도 좀 더 잡아주는 것이 좋다.

CPU

 

처음에 4GB memory, 2 core 환경에서 Kubeflow 설치를 진행했을 때 제대로 진행이 안되었다.

 

일부 Pod가 pending 상태에 있길래 살펴봤었는데

자기가 실행될 여유 memory가 있는 worker node가 없어서 였다.

 

테스트가 쉽지 않아서 세부 Spec 조정까지는 못해봤고

8GB memory, 4 core 환경으로 했을 때 성공을 했다.

 

 

1. Kubeflow & Kubernetes version

 

현재 설치되어있는 Kubernetes version은 다음과 같다.

- Kubernetes v1.25.6

kubectl get nodes

 

현재 Kubeflow 최신 Version은 v1.7이다.

https://www.kubeflow.org/docs/releases/kubeflow-1.7/

Kubeflow v1.7

 

다행히 Kubernetes v1.25와 궁합이 잘 맞는다 !!!

 

 

2. How to install Kubeflow

뒤늦게 Kubeflow를 살펴본다 ^^

- https://www.kubeflow.org/

https://www.kubeflow.org/

 

공식 가이드에서 알려주는 설치법에는 어떤 것이 있을까?

How to install

 

① Use a packaged distribution

주로 Cloud 업체에서 maintain 하면서 제공되는 배포판들이다. 즉, 나에겐 쓸모없는....^^

Active Distributions

 

② Use the raw manifests

advanced user를 위한 설치 방법이란다 ^^

Raw Kubeflow Manifests

 

manifests는 GitHub를 통해 배포되고 있다.

- https://github.com/kubeflow/manifests#installation

https://github.com/kubeflow/manifests#installation

 

우리는 이제 manifests를 이용한 Kubeflow 설치를 진행할 것이다.

 

 

3. Prerequisites

앞에서 살펴봤듯이 3개의 사전 준비 항목이 있다.

 

① Kubernetes (up to 1.26) with a default StorageClass

- Kubernetes v1.25에서도 잘 된다 ^^

- 여기서 무심히 넘기면 안되는 항목이 default StorageClass 이다. 뒤에서 깊게 살펴보겠다!

 

② kustomize 5.0.3

Kubernetes native configuration management

최근에는 kubectl 내부에 포함되어 있다고 하는데, manifests를 사용하기 위해서는 별도로 설치를 해줘야 한다.

- https://kubectl.docs.kubernetes.io/installation/kustomize/binaries/

https://kubectl.docs.kubernetes.io/installation/kustomize/binaries/

 

❯ curl -s "https://raw.githubusercontent.com/kubernetes-sigs/kustomize/master/hack/install_kustomize.sh"  | bash

❯ sudo install -o root -g root -m 0755 kustomize /usr/local/bin/kustomize

 

가이드에서 요구한 버전은 v5.0.3 이지만, 설치된 버전은 v5.1.1이다.

잘된다 ^^

 

③ kubectl

kubernetes 버전과 동일한 버전의 kubectl을 사용하는 것이 좋다.

Kubernetes node가 아닌 다른 workspace에서 kubectl을 사용하기 위해서는 직접 설치를 해줘야 한다.

 

❯ curl -LO "https://dl.k8s.io/release/v1.25.6/bin/linux/amd64/kubectl"

❯ sudo install -o root -g root -m 0755 kubectl /usr/local/bin/kubectl

 

kubectl을 새로 설치했다면, 자동완성 설정을 해주는 것이 편리하다.

zsh을 사용하는 경우 아래와 같은 명령어를 사용하거나, ~/zshrc에 넣어주면 좋다.

 

 source <(kubectl completion zsh)

 

~/.zshrc 파일에서 plugin에도 추가로 넣어주면 더 좋다.

 

plugins=(kubectl kube-ps1 git zsh-syntax-highlighting zsh-autosuggestions)

 

접근 권한을 얻기 위한 인증 정보(config) 파일을 얻어오는 부분은 여기에서는 생략하겠다.

 

 

4. StorageClass

Kubeflow 설치 관련한 많은 포스팅에서 잘 언급해주지 않는 부분이 바로 이 부분이다.

 

Kubeflow 설치 과정에서 약 4개의 PV(PersistentVolume) 생성을 하게 된다.

- 10Gi 용량의 PV 2개

- 20Gi 용량의 PV 2개

 

60Gi 이상의 PV를 생성할 수 있는 환경이어야 하는 것이다.

 

처음에 간단히 설치한다고 낮은 Spec의 환경에서 설치 진행하면, 이런 부분 때문에 어려움을 겪게 된다.

나도 마찬가지였다. Worer Node의 Disk 용량을 충분히 잡아놓지 않았기 때문이다.

 

그래서, NFS를 이용해서 StorageClass 설정을 진행하기로 했다.

 

① NFS Server 설치

NFS Server를 만드는 방법은 다음 포스팅을 참고하기 바란다.

- https://www.whatwant.com/entry/NFS-Server-Ubuntu-1804

 

② NFS Provisioner

Kubernetes에서 NFS를 사용하기 위한 Provisioner를 설치하자.

- https://github.com/kubernetes-sigs/nfs-subdir-external-provisioner

 

Helm을 이용하려고 하는데, 혹시 Helm이 설치 안되어 있다면 다음과 같이 진행하면 된다.

- https://github.com/helm/helm/releases

 

❯ wget https://get.helm.sh/helm-v3.12.3-linux-amd64.tar.gz

tar zxvf helm-v3.12.3-linux-amd64.tar.gz

sudo install -o root -g root -m 0755 helm /usr/local/bin/helm

 

NFS Provisioner 설치는 다음과 같이 하면 된다.

 

❯ helm repo add nfs-subdir-external-provisioner https://kubernetes-sigs.github.io/nfs-subdir-external-provisioner/

❯ helm install nfs-subdir-external-provisioner nfs-subdir-external-provisioner/nfs-subdir-external-provisioner \                 
    --set nfs.server=192.168.100.153 \
    --set nfs.path=/srv/nfs

❯ kubectl patch storageclass nfs-client -p '{"metadata": {"annotations":{"storageclass.kubernetes.io/is-default-class":"true"}}}'

 

잘 되는지 테스트를 해보면 다음과 같다.

 

 kubectl create -f https://raw.githubusercontent.com/kubernetes-sigs/nfs-subdir-external-provisioner/master/deploy/test-claim.yaml -f https://raw.githubusercontent.com/kubernetes-sigs/nfs-subdir-external-provisioner/master/deploy/test-pod.yaml

❯ kubectl delete -f https://raw.githubusercontent.com/kubernetes-sigs/nfs-subdir-external-provisioner/master/deploy/test-claim.yaml -f https://raw.githubusercontent.com/kubernetes-sigs/nfs-subdir-external-provisioner/master/deploy/test-pod.yaml

 

NFS 서버에 생성된 디렉토리와 SUCCESS 파일이 확인되면 된다.

필요 없어진 디렉토리/파일 삭제는, 직접 수작업으로 NFS Server에서 진행하면 된다.

 

 

5. kubeflow install

이제 준비는 끝났다. manifest를 이용한 설치를 진행해보자.

- https://github.com/kubeflow/manifests#install-with-a-single-command

https://github.com/kubeflow/manifests#installation

 

Kubeflow 실제 설치는 정말 쉽다.

kubeflow install

 

❯ git clone https://github.com/kubeflow/manifests.git 

❯ cd manifests   

❯ while ! kustomize build example | kubectl apply -f -; do echo "Retrying to apply resources"; sleep 10; done

 

끝!

 

이제 기다리면 된다. 시간이 좀 걸린다.

k9s

 

모든 Pod가 Running이면 된 것이다.

 

 

6. Service

웹 접근을 위해서는 현재 ClusterIP로 설정되어 있는 서비스를 NodePort 또는 LoadBalancer로 변경해주는 것이 좋다.

ClusterIP

 

설정을 변경해보자.

 

> kubectl edit service istio-ingressgateway -n istio-system

 

type 부분을 수정하고 저장하면 된다.

NodePort

 

다시 확인해보자.

NodePort

 

이제 웹브라우저로 접근하면 된다. (IP는 각자 상황에 맞게, 포트는 위와 같이 확인되는대로)

- http://192.168.100.150:31537/

login

 

기본 계정 정보는 다음과 같다.

- Email: user@example.com

- Password: 1234123 

 

kubeflow

 

수고 많으셨습니다!!!

반응형

https://minikube.sigs.k8s.io/

 

Kubernetes를 공부할 때 실습 환경으로 종종 minikube가 언급되지만

개인적으로 Kubernetes 공부 용도로는 minikube를 절대 추천하지 않는다.

 

사실 여러 부분에서 K8s를 제대로 구성한 것과의 차이가 꽤 크기 때문이다.

 

그리고 제대로 K8s 공부하기 위해서는 3대 이상의 머신 구성이 필요하지만

minikube로는 그런 상황에 대해서 실습을 할 수 없다.

 

그리고, 결정적으로 실제 업무 용도로 minikube를 사용하지 않기에

굳이 minikube에 시간 투자할 필요가 없다고 생각했었다.

 

하지만, 세상 모든 것은 나름의 쓸모가 있다!

 

그렇다. minikube가 필요해서 설치 과정을 정리해보고자 한다 ^^

 

 

0. What you’ll need

- 2 CPUs or more

- 2GB of free memory

- 20GB of free disk space

- Internet connection

- Container or virtual machine manager

  . such as: Docker, QEMU, Hyperkit, Hyper-V, KVM, Parallels, Podman, VirtualBox, or VMware Fusion/Workstation

 

1. 실습 환경

나는 VirtualBox를 이용하기로 했다.

VirtualBox

 

- 2 CPUs or more

- 4GB of free memory

- 50GB of free disk space

- Internet connection

 

VBox

 

- OS: Ubuntu 20.04 LTS

- Container or virtual machine manager : Docker

  . Docker 설치 방법: https://www.whatwant.com/entry/docker-buildx

docker

 

2. minikube 설치

- 공식 홈페이지에서는 각 환경 別 설치 방법을 상당히 편리한 UX로 제공해주고 있다.

  . https://minikube.sigs.k8s.io/docs/start/

 

https://minikube.sigs.k8s.io/docs/start/

 

> curl -LO https://storage.googleapis.com/minikube/releases/latest/minikube-linux-amd64

> sudo install minikube-linux-amd64 /usr/local/bin/minikube

 

그대로 실행하면 끝이다.

minikube install

 

3. minikube start

minikube를 구동시키면 귀여운 이모지들과 함께 다운로드 및 설치 등이 진행된다.

minikube start

 

4. kubectl 설치

Kubernetes(minikube)에 명령어를 전달하기 위해서는 'kubectl'가 필요하다.

  . https://kubernetes.io/docs/tasks/tools/install-kubectl-linux/

https://kubernetes.io/docs/tasks/tools/install-kubectl-linux/

 

가이드 문서에 있는 내용을 참조해서 설치 진행하면 된다.

kubectl install

 

❯ curl -LO "https://dl.k8s.io/release/$(curl -L -s https://dl.k8s.io/release/stable.txt)/bin/linux/amd64/kubectl"

❯ sudo install -o root -g root -m 0755 kubectl /usr/local/bin/kubectl

❯ kubectl version --client

 

잘 동작하는지 살펴보자.

kubectl

 

5. Dashboard

대시보드도 손쉽게 볼 수 있다.

dashboard

 

❯ minikube addons enable metrics-server

❯ minikube dashboard 

 

 

간단하게 Kubernetes를 맛보기 하는 용도로 정말 간단하게 설치할 수 있는 좋은 도구이다!!!

 

반응형

Kubernetes 설치를 저와 같이 했다면, addon으로 Dashboard도 설치가 되었을 것이다.

https://www.whatwant.com/entry/Kubernetes-Install-1

 

 

그런데, 정말 설치가 잘 되었을까?

K8s master 서버에 접속 후 한 번 살펴보자.

 

(master)$ kubectl get deployments --namespace kube-system

NAME                         READY   UP-TO-DATE   AVAILABLE   AGE
calico-kube-controllers      1/1     1            1           3d19h
coredns                      2/2     2            2           3d19h
dns-autoscaler               1/1     1            1           3d19h
kubernetes-dashboard         1/1     1            1           3d19h
kubernetes-metrics-scraper   1/1     1            1           3d19h
metrics-server               1/1     1            1           3d19h

 

오옷! 뭔가 보인다.

"kubernetes-dashboard"라는 항목이 보인다.

 

어떻게 접근해야할지 확인하기 위해 service 항목들을 살펴보자.

 

(master)$ kubectl get services --namespace kube-system

NAME                        TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)                  AGE
coredns                     ClusterIP   10.233.0.3      <none>        53/UDP,53/TCP,9153/TCP   3d19h
dashboard-metrics-scraper   ClusterIP   10.233.43.183   <none>        8000/TCP                 3d19h
kubernetes-dashboard        ClusterIP   10.233.51.126   <none>        443/TCP                  3d19h
metrics-server              ClusterIP   10.233.30.232   <none>        443/TCP                  3d19h

 

아직 ClusterIP로만 연결되었기 때문에 K8s 밖에서 연결해볼 수 없는 상태다.

밖에서 접근할 수 있는 경로를 만들어보자.

 

dashboard의 service 항목을 수정해보자.

 

(master)$ kubectl edit service --namespace kube-system kubernetes-dashboard

 

ClusterIP 부분을 "NodePort"로 변경하면 된다.

 

...
  selector:
    k8s-app: kubernetes-dashboard
  sessionAffinity: None
  type: ClusterIP
status:
  loadBalancer: {}

 

다시 확인해보자.

 

(master)$ kubectl get services --namespace kube-system

NAME                        TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)                  AGE
coredns                     ClusterIP   10.233.0.3      <none>        53/UDP,53/TCP,9153/TCP   3d21h
dashboard-metrics-scraper   ClusterIP   10.233.43.183   <none>        8000/TCP                 3d21h
kubernetes-dashboard        NodePort    10.233.51.126   <none>        443:31934/TCP            3d21h
metrics-server              ClusterIP   10.233.30.232   <none>        443/TCP                  3d21h

 

NodePort로 잘 변경되었으며 "31934"포트로 연결할 수 있음을 알려주고 있다.

바로 웹브라우져로 열어보자.

 

 

kubernetes-dashboard는 기본적으로 443포트, https 방식으로 제공되고 있다.

하지만, 당연하게도 인증서가 공인 인증서가 아니기에 ...

 

그러나, 고급 버튼을 누르면 길이 보인다.

 

 

안전하지 않다고 하지만, 전부 내거인데 뭐~ 그냥 이동하자 ^^

 

 

어!? 인증이 필요하단다.

이런...

 

그래... 권한이 필요하겠지...

 

 

dashboard를 위한 Service Account를 하나 생성하자.

 

(master)$ nano dashboard-serviceaccount.yaml

apiVersion: v1
kind: ServiceAccount
metadata:
   name: k8s-dashboard
   namespace: kube-system

 

ClusterRole Admin 권한을 부여하자.

 

(master)$ nano dashboard-clusterrolebinding.yaml

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: k8s-dashboard
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: cluster-admin
subjects:
- kind: ServiceAccount
  name: k8s-dashboard
  namespace: kube-system

 

전부 create 해주면 된다.

 

(master)$  kubectl create -f dashboard-serviceaccount.yaml

(master)$  kubectl create -f dashboard-clusterrolebinding.yaml

 

만들어진 Service Account 정보를 살펴보자.

 

(master)$ kubectl describe serviceaccounts --namespace kube-system k8s-dashboard

Name:                k8s-dashboard
Namespace:           kube-system
Labels:              <none>
Annotations:         <none>
Image pull secrets:  <none>
Mountable secrets:   <none>
Tokens:              <none>
Events:              <none>

 

어?! Tokens 부분에 아무런 정보가 없다! 이게 뭐지!?

https://kubernetes.io/docs/concepts/configuration/secret/#service-account-token-secrets

 

Kubernetes 1.22 이후 버전부터는 token이 자동 생성되지 않는단다! 이런!

 

(master)$ kubectl get nodes

NAME       STATUS   ROLES           AGE     VERSION
master     Ready    control-plane   3d20h   v1.25.6
worker01   Ready    <none>          3d20h   v1.25.6
worker02   Ready    <none>          3d20h   v1.25.6

 

나는 지금 v1.25.6 버전이구나.

그럼 직접 token을 생성하는 수밖에 ...

 

(master)$ nano dashboard-token.yaml

apiVersion: v1
kind: Secret
metadata:
  name: k8s-dashboard-secret
  annotations:
    kubernetes.io/service-account.name: "k8s-dashboard"
type: kubernetes.io/service-account-token

 

Service Account가 있는 kube-system namespace에다가 만들어주면 된다.

 

(master)$ kubectl create -f dashboard-token.yaml --namespace kube-system

 

만들어진 secret 정보를 살펴보면 token 정보도 보일 것이다.

 

(master)$ kubectl describe secrets --namespace kube-system k8s-dashboard-secret

Name:         k8s-dashboard-secret
Namespace:    kube-system
Labels:       <none>
Annotations:  kubernetes.io/service-account.name: k8s-dashboard
              kubernetes.io/service-account.uid: 037ee808-781e-424b-a17a-215113708a3b

Type:  kubernetes.io/service-account-token

Data
====
ca.crt:     1099 bytes
namespace:  11 bytes
token:      eyJhbGciOiJSUzI1NiIsImtpZCI6IkdBa0Mtc29XS1NGYl9pb1VuZzhpOHhQWlZaZEVOVTBIMWFQTHlVY21VNVUifQ.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJrOHMtZGFzaGJvYX...

 

그러면, Service Account 정보를 다시 살펴보자.

 

(master)$ kubectl describe serviceaccounts --namespace kube-system k8s-dashboard

Name:                k8s-dashboard
Namespace:           kube-system
Labels:              <none>
Annotations:         <none>
Image pull secrets:  <none>
Mountable secrets:   <none>
Tokens:              k8s-dashboard-secret
Events:              <none>

 

token 정보가 연결되었음을 볼 수 있다.

 

이제, 앞에서 확인한 token 정보를 복사한 뒤에 dashboard에 입력해보자.

 

 

음?! 표시할 데이터가 없단다.

얼마나 힘들게 여기까지 들어왔는데!!!!

 

 

검색창 옆에 namespace 부분을 "kube-system"으로 변경해보자.

 

 

뭔가 많이 보인다~~~!!!

 

 

 

눈에 뭔가 보이니까 좋다! ^^

반응형

간만에 Kubernetes 실습 환경 구축할 일이 생겨서

새로운 마음으로 진행하면서 기록으로 남겨 보고자 한다.

 

 

1. Server

  - master 1대 + worker 2대 = 총 3대의 Server를 준비하자.

  - 실습 환경은 VirtualBox로 하겠지만, 물리적인 Server로 이하 과정을 진행해도 무방하다.

 

VirtualBox

 

① CPU / Memory

  - Kubernetes 설치를 위해서는 다음과 같은 최소 사양이 필요하다

    . master: 2core, 2048MB

    . worker: 1core, 1280MB

  - 하지만, 원활한 동작을 위해서는 모두 2core, 2GB Spec으로 구성하자

 

CPU

 

Memory

 

② Network

  - VirtualBox의 경우 사실 NAT 방식으로도 Kubernetes 설치가 가능하긴 하다.

  - 하지만, 실제 서버 구성과 같은 환경으로 실습을 진행해보기 위해서는 브리지 방식으로 구성해보자.

 

네트워크

 

  - 보통 집에서 인터넷을 쓰는 방식이라고 하면 아래 그림과 같은 구성이 될 것이다.

 

 

③ Hostname, IP

  - 각 서버의 hostname 및 IP를 확인해 놓자.

 

hostname, IP

 

  - worker01 / worker02 서버들의 정보도 추가 확인하자.

 

 

2. Server Configure

  - Kubernetes 설치를 위해 서버 환경 셋팅을 좀 해줘야 한다.

  - 아래 과정은 서버 3대 모두 똑같이 진행해줘야 한다.

 

① swap off

  - K8s에서는 swap 기능이 켜져 있으면 문제가 발생할 수 있으므로 꺼줘야 한다.

 

(master/worker)$ sudo swapoff -a

(master/worker)$ sudo nano /etc/fstab

 

  - 재부팅되더라도 유지될 수 있도록 아래와 같이 swap 부분을 주석 처리해준다.

 

# /swap.img   none    swap    sw  0   0

 

② ip_forward

  - 가상화 머신끼리 패킷을 주고받을 수 있도록 ip_forward 기능을 켜줘야 한다.

 

(master/worker)$ sudo sh -c 'echo 1 > /proc/sys/net/ipv4/ip_forward'

 

③ hosts

  - 서버끼리 서로 알 수 있도록 hosts 정보도 등록해주자.

 

(master/worker)$ sudo nano /etc/hosts

 

  - 정보는 각자 상황에 맞춰서...

 

192.168.100.150 master
192.168.100.151 worker01
192.168.100.152 worker02

 

  - 혹시 상단에 아래와 같은 부분이 있으면 삭제하자

 

127.0.0.1 master

 

 

 

여기까지 진행했으면 깔끔한 진행을 위해 재부팅을 한 번 해주자.

VirtualBox의 장점을 살리기 위해서는 안전한 진행을 위해 snapshot 한 번 찍어주는 것도 좋다.

 

 

3. Kubernetes 설치

  - Kubespray를 이용해서 Kubernetes 설치를 진행하도록 하겠다.

 

① Python3 설치

  - 일단 기본 패키지로 설치하자

 

(master)$ sudo apt install -y python3 python3-pip

 

② ssh-key 생성

  - 서버間 연결을 위해 ssh-key 생성 및 등록 과정이 필요하다.

  - 이와 관련해 가장 깔끔한 가이드 문서는 아래와 같다. 참고하면 좋다.

    . https://cloud.google.com/compute/docs/connect/create-ssh-keys?hl=ko 

 

  - 여기에서는 가장 간단하게 그냥 무조건 기본값으로 그냥 막 엔터만 쳐서 생성하도록 하자.

 

(master)$ ssh-keygen

Generating public/private rsa key pair.
Enter file in which to save the key (/home/whatwant/.ssh/id_rsa):
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in /home/whatwant/.ssh/id_rsa
Your public key has been saved in /home/whatwant/.ssh/id_rsa.pub
The key fingerprint is:
SHA256:MtIQVARuKNcksL0D3beQ2aMMbMYfcdybNFVZVRGgDnQ whatwant@master
The key's randomart image is:
+---[RSA 3072]----+
|....*=+. o.E.+o+*|
| * B B. = . o    |
|+ @ @ +. = .     |
| * * B oo o      |
|  o = = S  .     |
|   . . o         |
|                 |
|                 |
|                 |
+----[SHA256]-----+

 

③ copy key

  - ssh-key 인증을 통해 master에서 worker로 접속할 수 있도록 하기 위한 과정이다

  - 명령어에 있는 IP는 worker들의 IP이다. 각자 상황에 맞춰 사용하면 된다.

  - 자기 자신(master)에도 등록을 하자.

 

(master)$ ssh-copy-id 192.168.100.151

/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/home/whatwant/.ssh/id_rsa.pub"
The authenticity of host '192.168.100.151 (192.168.100.151)' can't be established.
ED25519 key fingerprint is SHA256:Nu127IO/HdpFbO3HvWB8J61ZdhGjXpYDBSb3qg3rSY8.
This key is not known by any other names
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed
/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted now it is to install the new keys
whatwant@192.168.100.151's password:

Number of key(s) added: 1

Now try logging into the machine, with:   "ssh '192.168.100.151'"
and check to make sure that only the key(s) you wanted were added.

(master)$ ssh-copy-id 192.168.100.152

(master)$ ssh-copy-id 192.168.100.150

 

④ Kubespray 내려받기

  - git clone 방식으로 내려 받고, 최신 버전으로 switch 하자.

 

(master)$ git clone https://github.com/kubernetes-sigs/kubespray.git

(master)$ cd kubespray

(master)$ git switch release-2.21

 

⑤ 의존성 패키지 설치

  - Kubespray에서 필요로 하는 의존성 패키지들을 설치해주자

 

(master)$ sudo pip3 install -r requirements.txt

 

⑥ 인벤토리 생성

  - sample을 기반으로 나만의 설정을 업데이트해주면 된다.

  - 당연히 아래 IP 정보는 각자 상황에 맞춰서...

 

(master)$ cp -rfp inventory/sample inventory/mycluster


(master)$ declare -a IPS=(192.168.100.150 192.168.100.151 192.168.100.152)
(master)$ CONFIG_FILE=inventory/mycluster/hosts.yaml python3 contrib/inventory_builder/inventory.py ${IPS[@]}

 

  - 이렇게 생성된 hosts.yaml 파일을 확인 및 수정하자.

 

(master)$ nano ./inventory/mycluster/hosts.yaml

 

  - 아래 수정 내역은 공부를 위한 설정이다. 실제 운영 환경이라면 기본 설정대로 하는 것이 낫다.

 

all:
  hosts:
    master:
      ansible_host: 192.168.100.150
      ip: 192.168.100.150
      access_ip: 192.168.100.150
    worker01:
      ansible_host: 192.168.100.151
      ip: 192.168.100.151
      access_ip: 192.168.100.151
    worker02:
      ansible_host: 192.168.100.152
      ip: 192.168.100.152
      access_ip: 192.168.100.152
  children:
    kube_control_plane:
      hosts:
        master:
    kube_node:
      hosts:
        worker01:
        worker02:
    etcd:
      hosts:
        master:
    k8s_cluster:
      children:
        kube_control_plane:
        kube_node:
    calico_rr:
      hosts: {}

 

  - addon은 다음 3가지 정도만 설정해보자.

 

(master)$ nano ./inventory/mycluster/group_vars/k8s_cluster/addons.yml
dashboard_enabled: true
helm_enabled: true
metrics_server_enabled: true

 

  - proxy mode도 iptables로 설정하자.

 

(master)$ nano ./inventory/mycluster/group_vars/k8s_cluster/k8s-cluster.yml
# Kube-proxy proxyMode configuration.
# Can be ipvs, iptables
kube_proxy_mode: iptables

 

⑦ install

  - 이제 설치를 진행하자 !

 

(master)$ ansible-playbook -i inventory/mycluster/hosts.yaml --become --become-user=root cluster.yml

 

  - 혹시라도 에러가 발생하면 윗 단계들을 다시 한 번 꼼꼼하게 살펴보기 바란다.

  - 지금 직접 해보면서 포스팅하는 것이기에, 분명히 된다 !!! ^^

 

 

4. kubectl

  - master 서버에서 root 아닌 계정도 kubectl 명령을 사용할 수 있도록 하자

 

① 인증 정보 복사

  - root 계정에 등록된 인증 정보를 복사해오면 된다.

 

(master)$ mkdir -p ~/.kube

(master)$ sudo cp -i /etc/kubernetes/admin.conf ~/.kube/config

(master)$ sudo chown $(id -u):$(id -g) ~/.kube/config

 

② 자동완성

  - bash 쉘 환경에서 자동완성 기능을 추가하려면 다음과 같이 하면 된다.

 

(master)$ echo 'source <(kubectl completion bash)' >>~/.bashrc

(master)$ source ~/.bashrc

 

③ check

  - 잘 동작하는지 해보자.

 

(master)$ kubectl cluster-info

Kubernetes control plane is running at https://127.0.0.1:6443

To further debug and diagnose cluster problems, use 'kubectl cluster-info dump'.


(master)$ kubectl get nodes

NAME       STATUS   ROLES           AGE   VERSION
master     Ready    control-plane   21m   v1.25.6
worker01   Ready    <none>          20m   v1.25.6
worker02   Ready    <none>          20m   v1.25.6

 

 

잘 된다!!!!!

 

반응형

 

매번 잊어먹어서 기록을 위해 작성

 

[ Reference ]

- https://kubernetes.io/ko/docs/tasks/tools/install-kubectl-linux/

 

 

[ Environment ]

- `kubectl` 설치할 환경은 다음과 같다.

  . OS: Ubuntu 18.04

  . Shell: zsh

 

- `kubernetes master(control plane)` 환경은 다음과 같다.

  . IP: 192.168.100.200

 

 

[ kubectl - Install ]

- `curl` 이용하여 설치

> mkdir /srv/install/kubectl
> cd /srv/install/kubectl

> curl -LO "https://dl.k8s.io/release/$(curl -L -s https://dl.k8s.io/release/stable.txt)/bin/linux/amd64/kubectl"

> sudo install -o root -g root -m 0755 kubectl /usr/local/bin/kubectl

 

 

[ shell 자동완성 ]

- zsh 을 위한 completion 적용

> nano ~/.zshrc

---add---
source <(kubectl completion zsh)
---------

> source ~/.zshrc

 

 

[ connect K8s Cluster ]

- K8s Cluster에 접근할 수 있는 권한 얻기

> mkdir ~/.kube
> scp vagrant@192.168.100.200:/home/vagrant/.kube/config ~/.kube/

> nano ~/.kube/config

---modify---
- server: https://127.0.0.1:6443
+ server: https://192.168.100.200:6443
---------

 

 

[ Check ]

- K8s master(control plane)을 잘 찾는지 확인해보자

❯ kubectl cluster-info
Kubernetes control plane is running at https://192.168.100.200:6443

To further debug and diagnose cluster problems, use 'kubectl cluster-info dump'.

 

반응형

MinIO

Amazon S3 서비스를 On-Premise 환경에서 사용할 수 있도록 해주는

최근 많은 인기를 얻고 있는 유명한 Object Storage 프로젝트이다.

 

https://min.io/

 

MinIO | High Performance, Kubernetes Native Object Storage

MinIO's High Performance Object Storage is Open Source, Amazon S3 compatible, Kubernetes Native and is designed for cloud native workloads like AI.

min.io

 

AI 개발환경을 On-Premise에서 구축할 때

사진, 동영상 같은 데이터 또는 컨테이너 이미지와 같은 비정형 데이터를 저장하기 위한 서비스 中

설치도 간편하고 Amazon S3와 호환이 되다보니 MinIO가 아주 유명세를 떨쳤다.

 

 

그래서, 신규 시스템을 구축할 때 스토리지 용도로 MinIO를 선택했는데...

막상 해보니... 쉬운 아이가 아닌 것 같다는....

 

 

 

지금부터 설명할 과정은 다음과 같은 환경에서 진행하였다.

 

- VirtualBox Guest 3개 구성

  . Guest OS : Ubuntu 20.04 Server - 64bit

  . Guest HW : CPU 2 core, MEM 4 GB

 

- Kubernetes : 1 master, 2 worker node 구성

  . 설치 도구 : Kubespray

  . K8s version : 1.20.6

 

 

 

MinIO 설치는 Kubernetes 환경에서 Standalone 방식으로 진행해보고자 한다.

 

참고했던 컨텐츠는 아래와 같다.

 

https://github.com/kubernetes/examples/tree/master/staging/storage/minio

 

kubernetes/examples

Kubernetes application example tutorials. Contribute to kubernetes/examples development by creating an account on GitHub.

github.com

 

 

1. StorageClass

    - 특정 노드의 local storage를 실제 저장공간으로 사용하기 위한 내용으로 작성했다.

    - dynamic provisioning을 위해 volumeBindingMode를 'WaitForFirstComsumer'로 잡았다.

 

 

[ minio-standalone-storageclass.yaml ]

apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
  name: local-storage

provisioner: kubernetes.io/no-provisioner

volumeBindingMode: WaitForFirstConsumer

 

 

2. PersistentVolume

    - worker node 中 하나인, 'worker2'의 특정 디렉토리를 실제 저장 공간으로 정했다.

 

[ minio-standalone-pv.yaml ]

apiVersion: v1
kind: PersistentVolume
metadata:
  name: local-pv

spec:
  capacity:
    storage: 1Gi

  accessModes:
  - ReadWriteOnce

  persistentVolumeReclaimPolicy: Retain

  storageClassName: local-storage

  local:
    path: /data/volumes/pv1

  nodeAffinity:
    required:
      nodeSelectorTerms:
      - matchExpressions:
        - key: kubernetes.io/hostname
          operator: In
          values:
          - worker2

 

 

3. PersistentVolumeClaim

    - 앞에서 선언한 StorageClass, PersistentVolume과 매핑되는 PVC를 작성했다.

 

[ minio-standalone-pvc.yaml ]

apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: minio-pv-claim
  labels:
    app: minio-storage-claim

spec:
  accessModes:
    - ReadWriteOnce

  storageClassName: local-storage

  resources:
    requests:
      storage: 1Gi

 

 

4. Deployment

    - MinIO 서비스를 위한 Deployment이며, 당연히 앞에서 선언한 PVC를 사용했다.

 

[ minio-standalone-deployment.yaml ]

apiVersion: apps/v1
kind: Deployment
metadata:
  name: minio-deployment

spec:
  selector:
    matchLabels:
      app: minio

  strategy:
    type: Recreate

  template:
    metadata:
      labels:
        app: minio

    spec:
      volumes:
      - name: storage
        persistentVolumeClaim:
          claimName: minio-pv-claim

      containers:
      - name: minio
        image: minio/minio:latest
        args:
        - server
        - /storage
        env:
        - name: MINIO_ACCESS_KEY
          value: "minio"
        - name: MINIO_SECRET_KEY
          value: "minio123"
        ports:
        - containerPort: 9000
          hostPort: 9000
        volumeMounts:
        - name: storage
          mountPath: "/storage"

 

 

5. Service

    - MinIO 서비스를 외부로 노출하기 위한 Service를 선언해보았다.

 

[ minio-standalone-service.yaml ]

apiVersion: v1
kind: Service
metadata:
  name: minio-service

spec:
  type: NodePort

  ports:
    - port: 9000
      targetPort: 9000
      nodePort: 30333

  selector:
    app: minio

 

 

[ 결과 ]

여기까지

차례대로 create 하면 MinIO 서비스 웹을 볼 수 있다.

 

MinIO

 

Access Key / Secret Key 값은 Deployment YAML을 보면 확인할 수 있다.

 

 

MinIO

 

 

오른쪽 하단에 있는 "+" 버튼을 통해 bucket도 생성할 수 있고, 파일도 업로드 할 수 있다.

물론 다운로드도 가능한 Storage 웹서비스를 확인할 수 있다.

 

 

반응형

Kubernetes를 쌩으로(?) 설치하기 너무 귀찮기에

조금 편하게 설치하기 위해 Kubespray를 이용해보기로 했다.

 

   - kubernetes.io/ko/docs/setup/production-environment/tools/kubespray/

 

Kubespray로 쿠버네티스 설치하기

이 가이드는 Kubespray를 이용하여 GCE, Azure, OpenStack, AWS, vSphere, Packet(베어메탈), Oracle Cloud infrastructure(실험적) 또는 베어메탈 등에서 운영되는 쿠버네티스 클러스터를 설치하는 과정을 보여준다. Kub

kubernetes.io

설치를 진행한 환경은 다음과 같다.

 

  - Location : Home (SKB Internet - 500Mbps)

  - Host OS : Windows 10 64bit

  - VM S/W : VirtualBox

  - Guest OS : Ubuntu 20.04 Server 64bit (3개 VM)

    . CPU : 2 Core

    . Mem : 4096 MB

    . N/W : Bridge

 

 

1. python 설치

  - 설치되어 있는 python을 확인해보자.

 

$ ls /usr/bin | grep python
python3
python3.8

 

  - ubuntu 20.04 에서는 기본적으로 3.8이 설치되어 있는듯하다.

  - 사용하기 편하도록 기본 `python`에 mapping 하자.

 

$ sudo update-alternatives --config python
update-alternatives: error: no alternatives for python

$ sudo update-alternatives --install /usr/bin/python python /usr/bin/python3.8 1
$ sudo update-alternatives --config python

$ python --version
Python 3.8.5

 

  - `pip`도 설치해보자.

 

$ sudo apt install python3-pip

$ sudo update-alternatives --install /usr/bin/pip pip /usr/bin/pip3 1
$ sudo update-alternatives --config pip3

$ pip --version
pip 20.0.2 from /usr/lib/python3/dist-packages/pip (python 3.8)


2. ansible 설치

  - kubespray는 `ansible`을 기본으로 사용한다.

 

$ sudo apt install ansible python3-argcomplete

$ ansible --version
ansible 2.9.6
  config file = /etc/ansible/ansible.cfg
  configured module search path = ['/home/whatwant/.ansible/plugins/modules', '/usr/share/ansible/plugins/modules']
  ansible python module location = /usr/lib/python3/dist-packages/ansible
  executable location = /usr/bin/ansible
  python version = 3.8.5 (default, Jan 27 2021, 15:41:15) [GCC 9.3.0]

 

3. SSH 키 복사하기

  - `ansible`을 기본으로 사용하기에, 3대의 VM에 ssh 접속을 바로 할 수 있도록 SSH 키를 모두 복사해야 한다.

 

  - `master`로 사용할 VM에서 `ssh-keygen`으로 key를 생성한 뒤, copy하면 된다.

  - 개인적으로 사용하는 SSH 키가 있다면 그것을 사용하면 되고...

 

$ ssh-keygen

$ ssh-copy-id 192.168.122.10
(Master Node와 Worker Node에 모두 키를 복사)

 

 

4. swap 메모리 비활성화

  - kubernetes를 설치하기 위해선 swap 메모리를 모두 비활성화 해야 한다.

  - master/worker node에 사용할 3대의 VM 모두 꺼버리자!

 

$ sudo swapoff -a

 

 

5. ip forward 설정

  - K8s는 가상 네트워크 환경을 사용해야 하기에 ip_forward를 활성화 해야 한다.

  - master/worker node에 사용할 3대의 VM 모두 적용 !!!

 

$ sudo sh -c 'echo 1 > /proc/sys/net/ipv4/ip_forward'

$ cat /proc/sys/net/ipv4/ip_forward
1

 

  - 위와 같은 설정은 본래 재부팅하면 풀려야 하는데... 재부팅해도 그대로 유지되기에 내버려두고 있다.
  - 나중에 한 번 확인해봐야 할 것 같다.

 

 

6. hosts 등록

  - hostname으로 서버에 접속할 수 있도록 hosts 파일에 3개 VM hostname을 등록하자.

  - master/worker node에 사용할 3대의 VM 모두 적용 !!!

 

$ sudo nano /etc/hosts
192.168.100.111 master-stg
192.168.100.112 worker1
192.168.100.113 worker2

 

  - 각자의 hostname 과 IP 상황에 맞게 적용하면 된다.

 

 

7. kubespray 실행

  - `git clone` 받은 뒤, 필요한 패키지 설치하도록 하고, 나만의 환경 설정을 하자.

 

$ git clone https://github.com/kubernetes-sigs/kubespray.git

$ cd kubespray

$ git checkout release-2.15

$ sudo pip install -r requirements.txt

$ cp -rfp inventory/sample inventory/mycluster

$ declare -a IPS=(192.168.100.111 192.168.100.112 192.168.100.113)

$ CONFIG_FILE=inventory/mycluster/hosts.yaml python3 contrib/inventory_builder/inventory.py ${IPS[@]}

 

  - `cp`를 하는 것은, sample을 기본으로 나만의 inventory를 만들기 위함이다.

  - `declare`는 설치할 VM들의 IP를 적어주면 된다.

  - `CONFIG_FILE`을 실행하면 `declare`로 알려준 VM 정보들을 이용하여 config file을 만들어준다.

 

  - master node로 사용할 아이와 worker node를 사용할 아이들에 대해서 설정을 맞춰주자.

  - hostname도 맞춰서 적어주는 것이 좋다.

 

$ nano inventory/mycluster/hosts.yaml

all:
  hosts:
    master-stg:
      ansible_host: 192.168.100.111
      ip: 192.168.100.111
      access_ip: 192.168.100.111
    worker1:
      ansible_host: 192.168.100.112
      ip: 192.168.100.112
      access_ip: 192.168.100.112
    worker2:
      ansible_host: 192.168.100.113
      ip: 192.168.100.113
      access_ip: 192.168.100.113
  children:
    kube_control_plane:
      hosts:
        master-stg:
    kube_node:
      hosts:
        worker1:
        worker2:
    etcd:
      hosts:
        master-stg:
    k8s_cluster:
      children:
        kube_control_plane:
        kube_node:
    calico_rr:
      hosts: {}

 

  - addon도 필요한 것들을 true로 만들어주자.

 

$ nano ./inventory/mycluster/group_vars/k8s_cluster/addons.yml

dashboard_enabled: true
metrics_server_enabled: true
ingress_nginx_enabled: true

 

 

8. Static IP 설정

  - DHCP 설정으로 되어있으면 Node의 `/etc/resolv.conf`에 잡스러운(?) 내용이 들어가고

  - 그렇게 되면 K8s의 coredns에서 Node의 `/etc/resolv.conf`를 참고하게 되면서

  - Pod의 Container 안에 있는 `/etc/resolv.conf`에도 그 내용이 반영되어서

  - FQDN 관련해서 원하지 않는 결과가 나올 수 있다.

 

❯ cd /etc/netplan/

❯ sudo cp ./00-installer-config.yaml ./00-installer-config.yaml.210504

❯ sudo nano ./00-installer-config.yaml

network:
  ethernets:
    enp0s3:
      dhcp4: no
      dhcp6: no
      addresses: [192.168.100.111/24]
      gateway4: 192.168.100.1
      nameservers:
        addresses: [8.8.8.8,8.8.4.4]
  version: 2

 

 

 

 

9. 설치

  - 이제 준비는 끝났다. 고! 고!

 

$ ansible-playbook -i inventory/mycluster/hosts.yaml  --become --become-user=root cluster.yml

 

 

10. 사용자 계정 설정

  - root 계정이 아닌 사용자 계정에서 `kubectl` 명령어를 사용하기 위해서는 다음과 같이...

 

$ mkdir -p $HOME/.kube

$ sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config

$ sudo chown $(id -u):$(id -g) $HOME/.kube/config

 

11. zsh 자동 완성 셋팅

 

 

> echo "source <(kubectl completion zsh)" >> ~/.zshrc
> source ~/.zshrc

 

 

 

12. 재부팅 후

  - 희한하게 서버들을 재부팅 하고, `kubectl` 사용을 하면 API Server 연결을 거부당했다는 메시지가 나온다.

  - 그러면 swap 메모리 설정을 한 번 해주면 해결이 된다.

 

$ sudo swapoff -a

 

 

13. 결과

  - 이렇게 잘 나온다~

 

$ kubectl get nodes -o wide
NAME         STATUS   ROLES                  AGE   VERSION   INTERNAL-IP       EXTERNAL-IP   OS-IMAGE             KERNEL-VERSION     CONTAINER-RUNTIME
master-stg   Ready    control-plane,master   37h   v1.20.6   192.168.100.111   <none>        Ubuntu 20.04.2 LTS   5.4.0-72-generic   docker://19.3.15
worker1      Ready    <none>                 37h   v1.20.6   192.168.100.112   <none>        Ubuntu 20.04.2 LTS   5.4.0-72-generic   docker://19.3.15
worker2      Ready    <none>                 37h   v1.20.6   192.168.100.113   <none>        Ubuntu 20.04.2 LTS   5.4.0-72-generic   docker://19.3.15

 

반응형



최근 주력으로 공부하고 있는 것은 Kubernetes와 Machine-Learning이다.

특히 현재 업무와도 관련이 있어서 더 깊이 보고 있는 것이 바로 Kubernetes인데, 이와 관련된 새로운 책 하나를 살펴보게 되었다.



취향 저격!


요즘 IT 서적들은 표지도 너무 잘 만들고, 타이포그라피도 너무 잘 하는 것 같다.

그리고, 왠지 모르게 레벨업 욕구를 불러일으키게 "15단계"라니...




희한하게 요즘 보는 책들의 지은이가 계속 일본인이네...

지은이가 IBM 클라우드 소속이라서, 책에서도 IBM 클라우드를 소개했구나 ... ^^



15단계로 구성되었다고 하지만,

1장은 단계에 속하지 않은 사전 학습 내용으로 되어있다.



2장부터 1단계 시작이다.



그런데, 살펴보면 다른 책에서는 잘 보지 못하는 재미있는 항목이 보인다.



각 Step의 뒷 부분을 보면, "참고 자료"를 하나의 섹션으로 넣어 놓았다.


실제 내용을 보면 아래와 같이 되어있다.



추가적으로 공부를 더 해보고 싶은 경우, 이 내용을 참조하면 많은 도움이 될 것 같다.



책 내용은 깔끔하다.

다만, Why 에 대한 설명을 해주는 책은 아니고, How 위주로 설명을 해주는 책으로 보인다.




설명도 잘 되어 있고, 실행 예도 잘 보여주고 있다.


다만, 15단계에 따라 하나씩 직접 해보면서 어떤 명령어들을 사용하는지 배우기에는 적합하지만,

왜 이런 구성을 가지고 있는지 등에 대해서 파악하려면 다른 책을 보는 것이 나을 것 같다.


직접 몸으로 부딪히면서 배우는 것을 좋아하시는 분들에게 추천할 수 있는 책이다.




※ 제이펍 서평단 활동을 위해 지급 받은 도서에 대한 리뷰입니다.

반응형

+ Recent posts