ایجاد storageClass از یک گلاستر استوریج در kubernetes
با سلام
امروز قراره که واستون یک گلاستر راه بندازیم و به عنوان StrorageClass به Kubernetes متصلش کنیم.
همینطور که میدونید یکی از روش های اختصاص Volume در کوبرنتیز به صورت Dynamic یا پویا می باشد که در این حالت StorageClass تعریف و میزان درخواستی حجم و پارامترهای volume از طریق persistence volume claim یا pvc ایجاد میشه.
یکسری پیشنیاز ها داریم سناریو های مختلفی می تونین استفاده کنین ولی من تو این سناریو تمامی ماشین های مجازی رو جدا درست میکنم ولی شما میتونین از همون ماشین های موجود در کلاسنتر کوبر هم استفاده کنید.
مواد لازم برای پخت :
- یک کلاستر ۴ نودی کوبرنتیز (یک مستر و سه تا ورکر)
- یک کلاستر سه نودی گلاستر
- یک ماشین مجازی جدا برای اجرای Heketi
خوب تو این آموزش فرض بر این است که شما کلاستر کوبر رو راه اندازی کردین و کلاستر برقرار است.
برای ساخت کلاستر گلاستر میتونین به آموزش بررسی و ساخت گلاستر اف اس (Glusterfs) مراجعه کنین. فقط با توجه به این آموزش شما نباید Volume ای بسازین و این کار توسط خود سرویس Heketi انجام میشه. حالا اینکه Heketi چیه و چ کاربردی داره جلوتر بحث میکنیم.
همچنین شما می بایست دیسک های گلاستر را به طور خام به این سرویس ارایه بدین خود این سرویس کارای پارتیشن بندی و اختصاص و ساخت volume رو با توجه به درخواست های ارسالی از سمت کوبر انجام میده.
مرحله پنجم – نصب و راه اندازی heketi
ابزار heketi یک فریمورک بر پایه RESTful است که برای مدیریت گلاستر از آن استفاده میشود. api دارد و شما می تونین توی برنامه هاتون از این api ها استفاده کنین و گلاستر خودتون رو مدیریت کنین.
کوبرنتیز درخواست های خودش رو از طریق apiserver به این سرویس ارسال می کنه و این سرویس کارای پارتیشن بندی ساخت و اختصاص رو انجام میده. این سرویس heketi مختص استفاده ی کوبر نیست چون api داره راحت میتونین ی برنامه اختصاصی برای کار با گلاسترتون واسه خودتون بنویسین و از api های اون تو برنامتون استفاده کنید
داکیومنتیشن api و تمامی امکاناتی که heketi رو می تونین از طریق لینک زیر یک بررسی داشته باشین. لینک doc و امکانات heketi
این بخش می تونه روی یکی از نود های گلاستر یا روی یک ماشین جدا و یا هم به صورت یک pod در کوبرنتیز بیاد بالا . توی این مثال من قراره که اونو رو یک ماشین جدا بیارمش بالا. خوب یک ماشین داریم که می تونه هر توزیعی داشته باشه من از centos7 می خوام استفاده کنم و آدرس و نام زیر رو واسش میزارم.
تمامی کارهای مربوط به مرحله پنجم روی سرور heketi انجام میشه
192.168.200.55 gluster-gw-heketi
گام اول – به روزرسانی و اضافه کردن رپازیتوری EPEL
yum install epel-release yum update -y
گام دوم – اصلاح DNS
اگر در شبکه سرویس دی ان اس دارین حتما موارد آدرس و نام نود heketi را روی آن اصلاح کنید. اگر هم از این سرویس استفاده نمی کنید بهتر است مقادیر زیر را در فایل etc/hosts/ روی همه ی نود ها (هر ۴ نود – ۳نود گلاستر و یک نود heketi ) اضافه کنید تا نود ها همدیگر رو با نام ببینند. مقادیر زیر می بایست به فایل etc/hosts/ همه نود ها اضافه شود
192.168.200.51 gluster-node-1 192.168.200.52 gluster-node-2 192.168.200.53 gluster-node-3 192.168.200.55 gluster-gw-heketi
گام سوم – دانلود و نصب پیکج های مورد نیاز
دو پکیچ heketi , heketi-cli رو می بایست دانلود از حالت فشرده خارح و در درون یکی از دایرکتوری های قابل اجرای متغیر مح+یطی $PATH قرار داد (در این مثال از /usr/local/bin/ استفاده میکنیم).
curl -s https://api.github.com/repos/heketi/heketi/releases/latest \ | grep browser_download_url \ | grep linux.amd64 \ | cut -d '"' -f 4 \ | wget -qi - for i in `ls | grep heketi | grep .tar.gz`; do tar xvf $i; done sudo cp heketi/{heketi,heketi-cli} /usr/local/bin
حال با اجرای دستورات زیر میباست ورژن هرکدام از دو ابزار را مشاهده کنید
$ heketi --versionHeketi v10.1.0 $ heketi-cli --version heketi-cli v10.1.0
گام چهارم -ساخت یوزر و گروه
یوزر گروه و دایرکتوری های مدنظر را ایجاد و فایل heketi.json را به etc/heketi/ کپی می کنیم
sudo groupadd --system heketi sudo useradd -s /sbin/nologin --system -g heketi heketi sudo mkdir -p /var/lib/heketi /etc/heketi /var/log/heketi sudo cp heketi/heketi.json /etc/heketi
گام پنجم – ویرایش فایل پیکربندی heketi
حال به سراغ فایل etc/heketi/heketi.json/ رفته و آن را ادیت میکنیم.
## sudo vim /etc/heketi/heketi.json { "_port_comment": "Heketi Server Port Number", "port": "8080", "_enable_tls_comment": "Enable TLS in Heketi Server", "enable_tls": false, "_cert_file_comment": "Path to a valid certificate file", "cert_file": "", "_key_file_comment": "Path to a valid private key file", "key_file": "", "_use_auth": "Enable JWT authorization. Please enable for deployment", "use_auth": false, "_jwt": "Private keys for access", "jwt": { "_admin": "Admin has access to all APIs", "admin": { "_key_comment": "Set the admin key in the next line", "key": "############" }, "_user": "User only has access to /volumes endpoint", "user": { "_key_comment": "Set the user key in the next line", "key": "################" } }, "_backup_db_to_kube_secret": "Backup the heketi database to a Kubernetes secret when running in Kubernetes. Default is off.", "backup_db_to_kube_secret": false, "_profiling": "Enable go/pprof profiling on the /debug/pprof endpoints.", "profiling": false, "_glusterfs_comment": "GlusterFS Configuration", "glusterfs": { "_executor_comment": [ "Execute plugin. Possible choices: mock, ssh", "mock: This setting is used for testing and development.", " It will not send commands to any node.", "ssh: This setting will notify Heketi to ssh to the nodes.", " It will need the values in sshexec to be configured.", "kubernetes: Communicate with GlusterFS containers over", " Kubernetes exec api." ], "executor": "ssh", "_sshexec_comment": "SSH username and private key file information", "sshexec": { "keyfile": "/etc/heketi/heketi_key", "user": "root", "port": "22", "fstab": "/etc/fstab" }, "_db_comment": "Database file name", "db": "/var/lib/heketi/heketi.db", "_refresh_time_monitor_gluster_nodes": "Refresh time in seconds to monitor Gluster nodes", "refresh_time_monitor_gluster_nodes": 120, "_start_time_monitor_gluster_nodes": "Start time in seconds to monitor Gluster nodes when the heketi comes up", "start_time_monitor_gluster_nodes": 10, "_loglevel_comment": [ "Set log level. Choices are:", " none, critical, error, warning, info, debug", "Default is warning" ], "loglevel" : "debug", "_auto_create_block_hosting_volume": "Creates Block Hosting volumes automatically if not found or exsisting volume exhausted", "auto_create_block_hosting_volume": true, "_block_hosting_volume_size": "New block hosting volume will be created in size mentioned, This is considered only if auto-create is enabled.", "block_hosting_volume_size": 500, "_block_hosting_volume_options": "New block hosting volume will be created with the following set of options. Removing the group gluster-block option is NOT recommended. Additional options can be added next to it separated by a comma.", "block_hosting_volume_options": "group gluster-block", "_pre_request_volume_options": "Volume options that will be applied for all volumes created. Can be overridden by volume options in volume create request.", "pre_request_volume_options": "", "_post_request_volume_options": "Volume options that will be applied for all volumes created. To be used to override volume options in volume create request.", "post_request_volume_options": "" } }
خط «port»: «8080» پورت سرویس دهی heketi را مشخص میکند که می توانید آن را ویرایش کنید. بلاک زیر تنظیمات یوزر و سکرت مربوط به اتصال api را نشان میدهد که می بایست عوض شود – این مقادیر بعدا می بایست در فایل مربوط به معرفی StorageClass در کوبر مقدار دهی شود.
"_jwt": "Private keys for access", "jwt": { "_admin": "Admin has access to all APIs", "admin": { "_key_comment": "Set the admin key in the next line", "key": "###############" ## secret for user with name of admin }, "_user": "User only has access to /volumes endpoint", "user": { "_key_comment": "Set the user key in the next line", "key": "##############" ## secret for user with name of user } },
بلاک بعدی که خیلی هم مهم است نحوه اتصال heketi به نود های گلاستر را نشان میدهد. executor میبایست ssh باشد و در قسمت keyfile می بایست آدرس کلید خصوصی قرار گیرد
نکته : اتصال heketi به نود های گلاستر می بایست به صورت passwordless باشد به همین دلیل برای یوزر اجرا کننده heketi یک کلید عمومی و خصوصی ایجاد می کنیم. جلوتر بررسیش می کنیم.
"executor": "ssh", "_sshexec_comment": "SSH username and private key file information", "sshexec": { "keyfile": "/etc/heketi/heketi_key", "user": "root", "port": "22", "fstab": "/etc/fstab" },
در قسمت user نام یوزر اس اس اچ را و در قسمت port شماره پورت اس اس اچ برای نود های گلاستر قرار گرفته میشود. مقدار fstab هم به صورت پیشفرض همونه و فایل fstab رو نشون میده چون بعدا می خواد ادیتش کنه.
گام ششم – ساخت کلید ssh انتقال آن به سرورها
خوب برای ساخت کلید اس اس اچ از دستور زیر استفاده و حق دسترسی آنن را اصلاح می کنیم :
sudo ssh-keygen -f /etc/heketi/heketi_key -t rsa -N ' ' sudo chown -R heketi:heketi /etc/heketi/
حال کلید عمومی را می بایست به فایل root/.ssh/authorized_keys/ درون همه نود های گلاستر اضافه کرد این کار به صورت دستی هم میشه انجام داد ولی به صورت اتوماتیک از دستور زیر استفاده میکنیم.
for i in gluster-node-1 gluster-node-2 gluster-node-3; do ssh-copy-id -i /etc/heketi/heketi_key root@$i done
خوب اتصال heketi به نود های گلاستر به صورت passwordless شد الان باید بتونین بدون پسورد از نود heketi به همه نود ها ssh بزنین.
گام هفتم – ساخت سرویس heketi
گام بعدی ایجاد یک سرویس از این heketi است که به راحتی بتوان ان را با دستور systemctl مدیریت کرد.
sudo vim /etc/systemd/system/heketi.service[Unit] Description=Heketi Server [Service] Type=simple WorkingDirectory=/var/lib/heketi EnvironmentFile=-/etc/heketi/heketi.env User=heketi ExecStart=/usr/local/bin/heketi --config=/etc/heketi/heketi.json Restart=on-failure StandardOutput=syslog StandardError=syslog [Install] WantedBy=multi-user.target
فایل مختص متغیرهای hektei را دانلود و در دایرکتوری تنظیمات آن قرار می دهیم
sudo wget -O /etc/heketi/heketi.env https://raw.githubusercontent.com/heketi/heketi/master/extras/systemd/heketi.env sudo chown -R heketi:heketi /var/lib/heketi /var/log/heketi /etc/heketi
روی centos پیشفرض SELinux فعال است و نیاز است تا غیرفعال شود.
sudo setenforce 0 sudo sed -i 's/^SELINUX=.*/SELINUX=permissive/g' /etc/selinux/config
حال تنظیمات سرویس را لود و آن را در استارت آپ قرار میدهیم.
sudo systemctl daemon-reloadsudo systemctl enable --now heketi systemctl status heketi ● heketi.service - Heketi Server Loaded: loaded (/etc/systemd/system/heketi.service; enabled; vendor preset: disabled) Active: active (running) since Thu 2020-11-05 11:59:05 UTC; 1 day 22h ago Main PID: 4280 (heketi) CGroup: /system.slice/heketi.service └─4280 /usr/local/bin/heketi --config=/etc/heketi/heketi.json
حال سرویس می بایست بالا و روی پورت 8080 سرویس دهی کند.
گام هشتم – ساخت فایل Topology و بارگذاری آن
فایل topology مهمیترین فایل heketi می باشد چرا که در آن آدرس نود های گلاستر و مکان دیسک های خام مشخص شده است
# vim /etc/heketi/topology.json { "clusters": [ { "nodes": [ { "node": { "hostnames": { "manage": [ "gluster-node-1" ], "storage": [ "192.168.200.51" ] }, "zone": 1 }, "devices": [ "/dev/sdb" ] }, { "node": { "hostnames": { "manage": [ "gluster-node-2" ], "storage": [ "192.168.200.52" ] }, "zone": 1 }, "devices": [ "/dev/sdb" ] }, { "node": { "hostnames": { "manage": [ "gluster-node-3" ], "storage": [ "192.168.200.53" ] }, "zone": 1 }, "devices": [ "/dev/sdb" ] } ] } ] }
در این فایل ما یک کلاستر تعریف کردیم که دارای سه نود و هر نود آدرس و نام اون مشخص شده در قسمات device هم می بباست آدرس دیسک های خام رو وارد کنیم توی این مثال یکی هست ولی شما می تونین به ازای هر دیسک یک خط به devices اضافه کنید. این فایل در قسمت های مختلف آن پارامتر های دیگه ای هم داره که می تونین رفتار کلاسترتون رو باهاش کنترل کنین موارد مطرح شده بالا حداقل ها برای ساخت این فایل هستند
خوب بعد از ساخت این فایل میریم سراغ لود آن
heketi-cli topology load --user admin --secret heketi_admin_secret --json=/etc/heketi/topology.json
به جای مقدار heketi_admin_secret می بایست سکرتی که دی فایل heketi.json وارد کردیم را قرار دهیم. این دستور شروع به آماده سازی و فورمت دیسک های خام و آماده ساخات ولیوم میکند. از این به بعد برای زدن دستور heketi-cli حتما میبایست user,secret مشخص شود ولی برای راحت تر شدن مقادیر زیر در .bashrc یوزر ذخیره تا مجدد در دستورات تکرار نشود.
$ vim ~/.bashrc export HEKETI_CLI_SERVER=http://gluster-gw-heketi:8080 export HEKETI_CLI_USER=admin export HEKETI_CLI_KEY="AdminPass"
دستور زیر تمامی موارد استفاده دستور heketi-cli را به شما نشان میدهد.
heketi-cli --help
برای تست صحت کارکرد سرویس از دستور زیر می توانید استفاده کیند.
curl http://gluster-gw-heketi:8080/hello --- >> Hello from Heketi
تا به اینجا فقط گلاستر رو بالا آوردیم و heketi که یک مدیر restfull برای گلاستر بود رو پیکربندی کردیم.در ادامه میریم سراغ اتصال کوبرنتیز به heketi برای مدیریت گلاستر به عنوان StorageClass و تخصصی داینامیک ولیوم ها به PVC.
مرحله ششم – پیکربندی اتصال کوبرنتیز به hekti
خوب برای این مرحله شما نیاز دارین که یک کلاستر کوبرنتیز در حال اجرا داشته باشین اگه درحد تست دارین جلو میرین که minikube هم میتونه کارتون رو راه بندازه.
گام اول – نصب و پیکربندی کلاینت گلاستر اف اس تنظیمات dns
خوب برای استفاده از گلاستر می بایست نسخه کلاینت آن روی همه نود های مستر و ورکر در کوبرنتیز نصب شود. دقیقا مانند مرحله سوم جلو میرویم فقط در حین نصب پکیج glusterfs-server را نصب نمیکنیم.
اگر در شبکه سرویس دی ان اس دارین حتما موارد آدرس و نام نود همه نود های گلاستر و heketi را روی آن اصلاح کنید. اگر هم از این سرویس استفاده نمی کنید بهتر است مقادیر زیر را در فایل etc/hosts/ روی همه ی نود ها (هر ۴ نود – ۳نود گلاستر و یک نود heketi ) اضافه کنید تا نود ها همدیگر رو با نام ببینند. مقادیر زیر می بایست به فایل etc/hosts/ همه نود های کوبرنتیز اضافه شود
192.168.200.51 gluster-node-1 192.168.200.52 gluster-node-2 192.168.200.53 gluster-node-3 192.168.200.55 gluster-gw-heketi
تمامی گام های بعدی روی سرور مستر کوبرنتیز اتفاق می افتد
گام دوم – تعریف object برای StorageClass
خوب می بایست یک فایل به فورمت yml برای تعریف این نوع obj طراحی و آن را درون کوبر ایجاد کنیم. قبل از این مورد چون می خوایم از یوزر و سکرت استفاده کنیم برای اتصال به heketi بهتر است که مقدار پسورد به صورت plain text نباشد و آن را درون Object ی به نام Secret بزاریم.
# vim secret.yml apiVersion: v1 kind: Secret metadata: name: heketi-secret namespace: default type: "kubernetes.io/glusterfs" data: key: ######################
برای ساخت مقدار key از دستور زیر استفاده کنید
echo -n "PASSWORD" | base64
حال برای ایجاد این object می توانیم از دستور زیر استفاده کنیم.
kubectl create -f secret.yml OR kubectl apply -f secret.yml
بعد به سراغ تعریف فایل StorageClass می رویم.
# vim StorageClass.yml apiVersion: storage.k8s.io/v1 kind: StorageClass metadata: name: gluster provisioner: kubernetes.io/glusterfs reclaimPolicy: Retain volumeBindingMode: Immediate allowVolumeExpansion: true parameters: resturl: "http://gluster-gw-heketi:8080" clusterid: "#########################" restauthenabled: "true" restuser: "admin" # restuserkey: "###########" secretNamespace: "default" secretName: "heketi-secret" volumetype: "replicate:3" volumenameprefix: "k8s-dynamic-provisioning"
بررسی پارارمتر های فایل بالا :
-
پارامتر resturl : مشخص کننده آدرس و پورت سرویس heketi
-
پارامتر clusterid : مشخص کنند id کلاستر ایم مقدار می بایست با دستور زیر و از سرور heketi گرفته شود
heketi-cli cluster list Clusters: Id:################################ [file][block]
-
پارامتر restauthenabled : برای فعالسازی احراز هویت با یوزر و سکرت
-
پارامتر restuser : مشخص کننده یوزر احراز هویت
-
پارامتر restuserkey : اگر می خواین که از شی secret استفاده نکنین مقدار سکرت رو می تونین توی این پارامتر بزارین (اینجا کامنت کردم چون از شی secret میخوام استفاده کنم)
-
پارامترهای secretNamespace و secretName : نام obj و نام namespace برای secret ساخته شده در مرحله قبل است
-
پارامتر volumetype : نوع پیشفرض volume ایحاد شده را نشان میدهد
-
پارامتر volumenameprefix : پیشوندی است که به طور اتومات به اول همه volume ها اضافه میکند.
حال برای ایجاد این object می توانیم از دستور زیر استفاده کنیم.
kubectl create -f StorageClass.yml OR kubectl apply -f StorageClass-.yml
گام سوم – تست Kubernetes Dynamic Provisioning
برای تست این مرحله می بایست دوتا شی از نوع PersistentVolumeClaim , pod ایجاد و مراحل اختصاص ولیوم را بررسی کنیم.
برای ساخت یک PVC می توانیم از فایل زیر استفاده کنیم.فقط به جای storageClassName میبایست همان نامی را وارد کنیم که در قسمت metadata برای آن sc در فایل StorageClass.yml تعریف کرده ایم.
#vim pvc.yml apiVersion: v1 kind: PersistentVolumeClaim metadata: name: gluster1 spec: accessModes: - ReadWriteMany resources: requests: storage: 1Gi storageClassName: gluster
حال برای ایجاد این object می توانیم از دستور زیر استفاده کنیم.
kubectl create -f pvc.yml OR kubectl apply -f pvc-.yml
در ادامه میبایست این pvc را یه یک pod متصل کنیم.
## vim pod-sv.yml apiVersion: v1 kind: Pod metadata: name: gluster-pod1 labels: name: gluster-pod1 spec: containers: - name: gluster-pod1 image: nginx:1.14.2 ports: - name: web containerPort: 80 securityContext: privileged: true volumeMounts: - name: gluster-vol1 mountPath: /usr/share/nginx/html volumes: - name: gluster-vol1 persistentVolumeClaim: claimName: gluster1 --- apiVersion: v1 kind: Service metadata: name: nginx labels: name: gluster-sv1 spec: type: NodePort ports: - port: 8080 targetPort: 80 protocol: TCP name: http selector: name: gluster-pod1
حال برای ایجاد این object می توانیم از دستور زیر استفاده کنیم.
kubectl create -f pod-sv.yml OR kubectl apply -f pod-sv-.yml
حال با دستورات زیر می توانیم وضعیت پاد و volume را بررسی کنیم.
kubectl get pod,pv,pvc,sc kubectl describe pvc kubectl describe pod
امیدوارم مفید بوده باشه
یا حق