Cài đặt MongoDB Sharded Cluster trên K8S

Tram Ho

Lời mở đầu

Hello các bạn trở lại với series bài viết “Những gì mình biết về MongoDB”, series nói về một NoSQL DB cực kỳ phổ biến là MongoDB.

Trong phần trước mình đã giới thiệu cách cài đặt mongodb shard cluster trên các máy chủ Linux. Với cách cài đặt thủ công từng thành phần và cấu hình sharding, cấu hình các replicas sẽ giúp bạn hiểu rõ hơn về hệ thống.

Trong bài viết này mình sẽ hướng dẫn cách cài đặt mongodb shard cluster trên K8S sử dụng helm chart. Với cách cài đặt này thì yêu cầu các bạn cần hiểu về kiến trúc và các thành phần của MongoDB, từ đó mới dễ dàng tùy biến các tham số cấu hình có sẵn được cung cấp bởi bộ helmchart này.

Việc cài đặt mongodb trên k8s sử dụng helm chart khá đơn giản. Bởi hầu hết các bước cài đặt, cấu hình đều đã được tự động hóa rồi. Việc của mình chỉ là lựa chọn cấu hình cụ thể cho từng thành phần mà mình muốn (mongos, configserver, shard), ví dụ:

  • Có dùng sharding hay không
  • Sử dụng bao nhiêu shard
  • Mỗi shard có cấu hình replicaset hay không
  • ConfigServer có cấu hình Replicaset hay không..

Mô hình triển khai

Mình sẽ cài đặt trên cụm K8S cài đặt trên các máy chủ EC2 như sau:

Cụm mongodb mình sẽ cài theo mô hình giống bài trước đó là cài đặt 3 shardsvc (mỗi shardsvr có 3 replicas), configsvr có 3 replicas và 2 service mongos.

Mục tiêu cần đạt được:

  • Đảm bảo các replicas của cùng 1 shardsvr sẽ không nằm chung node
  • Đảm bảo các replicas của configsvr sẽ không nằm chung node

Để lưu trữ dữ liệu cho mongodb trên k8s thì mình sẽ sử dụng Persistent Volume (Sử dụng luôn EBS Storage của AWS thông qua việc tạo một Storage Class để cấp phát PV tự động).
Nếu các bạn sử dụng K8S Onprem thì các bạn có thể sử dụng NFS làm phần storage backend cho k8s.

Triển khai

Tóm tắt các bước triển khai như sau:

  • Chuẩn bị môi trường: K8S, Storage Class
  • Chuẩn bị helm-chart
  • Tùy biến các tham số cài đặt
  • Cài đặt helm-chart và kiểm tra kết quả.

Chuẩn bị môi trường Kubernetes

K8S mình đã dựng xong, gồm 4 worker node (để đặt được mô hình cài 3 shard thì nên có ít nhất 3 node nhé). Bây giờ mình sẽ cài đặt thêm phần storage class sử dụng AWS EBS.

Để làm được việc này thì cần thực hiện:

  • Phân quyền cho các EC2 có quyền đọc ghi vào EBS
  • Cài đặt EBS CSI Driver trên K8S
  • Cài đặt Storage Class trên K8S

Các nội dung trên chủ yếu liên quan tới AWS mình sẽ không nói sâu về nó. Kết quả là mình có một Storage Class để tạo PV tự động và tên của Storage Class này sẽ được dùng cho các config khi cài mongo bằng helm chart.

Tải helmchart của mongodb

Tạo thư mục cài đặt và tải về helmchart của mongodb:

Mình sẽ sử dụng helmchart bitnami/mongodb-sharded để cài đặt. Trước tên là tải helmchart về lưu trên máy để tùy biến và sử dụng:

Lúc này ta sẽ có thư mục mongodb-sharded chứa helmchart cài đặt mongodb. Trong đó có chứa một file values.yaml lưu các tham số để tùy biến khi cài đặt helmchart này. Mình sẽ copy nó ra ngoài để tùy biến các tham số phù hợp với nhu cầu của mình. Lúc này thư mục chứa file cài đặt sẽ như sau:

Tùy biến tham số cài đặt

Đây sẽ là phần quan trọng nhất khi cài một phần mềm từ helmchart và cũng đòi hỏi kinh nghiệm nhiều nhất. Bởi một file tham số (helm-value file) thường sẽ rất dài, có khi tới vài nghìn dòng. Nên trước khi cấu hình tham số, mình cần phải biết mình sẽ cài gì, và cần tùy biến các tham số gì.

Bài toán ban đầu mình đặt ra là cài mongo shard cluster với các mục tiêu:

    • Có 3 shard, mỗi shard 3 replicas
    • Configsvr có 3 replicas
    • Mongos có 2 replicas
    • Mongo sẽ dùng cho các ứng dụng trong k8s do đó không cần expose ra bên ngoài (sẽ chỉ cần service dạng ClusterIP là đủ). Trong trường hợp cần expose ra bên ngoài thì có thể sử dụng NodePort.
    • Enable Metrics để sau này có thể monitor được nó trên Prometheus và Grafana

 

 

Về cơ bản thì các tham số của file helm-value sẽ cho phép chúng ta tùy biến các đối tượng chính là mongos, configsvr, shardsvr và phần metric để phục vụ cho việc monitor ứng dụng.

Mình sẽ check giải thích một số tham số cơ bản nhất để tùy biến từng thành phần bên trên.

Các tham số chung

Trong phần này mình sẽ cần quan tâm tới thông tin image. Mình hay có thói quan tag các public image về private registry thì mình phải sửa thông tin image theo private registry ở phần này. Một lưu ý nữa là khi sử dụng private registry thì các bạn cần phải tạo secret để sử dụng cho việc pull image từ private registry này.

Tùy biến giá trị của helm-value

Về cơ bản các tham số mặc định của bộ helm chart này đã rất ổn rồi, cơ bản mình cũng chỉ cần thay đổi rất ít. Một số tham số chính cần thay đổi tùy vào cấu hình mình muốn triển khai.

Cấu hình xác thực, ở đây mình không cấu hình password cho các replicaset.

Cấu hình số lượng Shardsvr trong cluster, mình set là 3 đúng theo mô hình ban đầu:

Cấu hình service thì mặc định là ClusterIP và port 27017, cơ bản mình ko phải update gì ở đây nhưng vẫn nêu ra để nếu cần mình có thể đổi thành NodePort để expose ra bên ngoài chẳng hạn:

Tùy biến cấu hình của configsvr: Thì mình sẽ set tham số để tạo 3 replicas cho configsvr và cấu hình persistent volume cho nó gồm thông tin storageClass và dung lượng lưu trữ cần thiết:

Tùy biến cấu hình của mongos: Đơn giản là set 2 replicas. Tham số podAntiAffinityPreset sẽ tự động ra một rule podAntiAffinity với mục tiêu cố gắng phân bổ các Pod của ứng dụng này trên các node khác nhau:

Tùy biến cấu hình của shardsvr: Tương tự mình set 3 replicas cho mỗi shard, cấu hình podAntiAffinityPreset: soft để các Pod của các shardsvr sẽ ưu tiên không chạy cùng trên một node.

Lưu ý chúng ta chỉ nên setup tham số PodAntiAffinity ở dạng soft, tương ứng với cấu hình preferredDuringSchedulingIgnoredDuringExecution. Việc này sẽ tránh trường hợp Pod không tìm dc node thỏa mãn điều kiện về antiAffinity và ở trạng thái Pending.

Tổng hợp lại mình sẽ có file custom-mongo-val.yaml chứa các tham số tùy chỉnh như sau:

Cài đặt

Trước khi cài đặt mình có thể review lại một lượt cấu hình sẽ triển khai thực tế trước khi apply vào hệ thống. Mình sẽ sử dụng lệnh helm template để kiểm tra xem với cấu hình tùy biến như trên thì bộ helmchart này sẽ tạo ra các resource ntn:

Với các cấu hình affinity mặc định như trên thì bộ helmchart đã tạo cho chúng ta rule của affinity kiểu như sau:

Với mỗi thành phần sẽ có label app.kubernetes.io/component tương ứng là mongos, configsvr hay shardsvr và đó sẽ yếu tố chính để thực hiện rule PodAntiAffinity.

Hiểu một cách đơn giản là hệ thống sẽ ưu tiên không tạo Pod của configsvr khi node đó đã có Pod có label app.kubernetes.io/component=configsvr chạy trên đó. Và từ đó sẽ giúp “phân bổ” các Pod của cùng một chức năng trên các node khác nhau.

Đến đây ta có thể thực hiện cài đặt:

Kiểm tra kết quả:

Như vậy ta có thể thấy:

  • 2 Pod của mongos chạy trên 2 node là node-2node-3
  • 3 Pod của configsvr chạy trên 3 node khác nhau là node-1, node-2node-3
  • 3 Pod đầu tiên của các shardsvr chạy trên 3 node khác nhau

Bản chất ở đây khi ta tạo ra 3 shard thì helmchart này sẽ tạo cho chúng ta 3 statefulset tương ứng 3 shardsvr:

Và theo đặc tính của statefulset thì các Pod của nó sẽ sinh ra tuần tự, do vậy 3 Pod đầu của mỗi Statefulset sẽ tạo ra trước, khi Pod này tạo ok thì tiếp tục tạo Pod thứ 2, thứ 3.

Và kết quả cuối cùng khi cài đặt xong:

Và với mỗi Pod của statefulset ta sẽ có 1 PVC,PV tương ứng:

Kiểm tra kết nối vào DB

Khi cài đặt xong bằng helmchart sẽ out ra cho chúng ta hướng dẫn để kết nối tới db. Mình tạo Pod có mongodb client để kết nối vào cluster vừa cài:

Việc tạo và add các shardsvr vào cluster, cũng như cấu hình replicas cho các shardsvr/configsvr được setup tự động hoàn toàn. Mình có thể kiểm tra trạng thái sharding của cluster như sau:

Như vậy là mình đã cài đặt xong mongodb shard cluster trên K8S một cách khá đơn giản. Tóm tắt lại khi quen tay thì các bạn chỉ phải sửa vài tham số và cài câu lệnh là setup xong được một cụm mongodb rồi.

Cảm ơn các bạn đã dành thời gian đọc tới đấy. Nếu thấy bài viết hữu ích thì hãy để lại 1 upvote và bookmark bài viết ủng hộ mình nhé!

Chia sẻ bài viết ngay

Nguồn bài viết : Viblo