No menu items!
No menu items!
More

    Thiết kế số lượng PGs trong Ceph

    1. Tổng quan.

    Dưới đây là một bài phân tích chi tiết về PGs (Placement Groups) trong Ceph, cách dữ liệu từ client ghi vào pool thông qua PGs, lý do tại sao PG nhiều không phải lúc nào cũng tốt cho performance.

    2. PG (Placement Group) là gì?

    Trong Ceph, PG (Placement Group)một nhóm logic để gom dữ liệu lại nhằm giúp quá trình phân bổ và quản lý dữ liệu hiệu quả hơn.

    • PG giống như “trung gian” giữa poolOSD.
    • Dữ liệu không ghi thẳng vào OSD, mà được ánh xạ vào PG trước, sau đó PG ánh xạ đến một tập hợp OSD cụ thể.

    3. Quá trình phân bổ dữ liệu từ client xuống pool.

    Giả sử:

    • Có một pool tên là video-pool với replica=2
    • Tổng có 6 OSDs: osd.0osd.5
    • Pool có 128 PGs

    Khi client ghi 1 file movie.mp4 (10GB), quá trình sẽ như sau:

    Client
       |
       | 1. Hash(object-name) --> PG ID
       v
    +------------------+
    |    PG Hashing    |
    +------------------+
            |
            | 2. PG ID (vd: 23.pg123)
            v
    +------------------+
    |   Placement Group (pg123)        |
    +------------------+
            |
            | 3. PG ánh xạ đến OSDs
            v
         Primary OSD (osd.2)
                |
                | 4. Ghi replica đến các OSD khác
                v
         Replica OSD (osd.4)
    
    (minh họa đơn giản)
         Client
            |
            v
         +----+      +----+      +----+
         |PG01| ---> |OSD2| ---> |OSD4|
         +----+      +----+      +----+

    🔍 Ví dụ khi bạn ghi một file movie.mp4 10GB vào video-pool với replica=2:

    • Ceph chia file thành các đối tượng nhỏ (objects), ví dụ mỗi object là 4MB → file sẽ chia thành khoảng 2560 objects.
    • Mỗi object sẽ được:
      • Hash để ánh xạ vào một PG
      • Mỗi PG đã biết ánh xạ đến 2 OSDs (primary + secondary vì replica=2)
    • Client gửi object đến Primary OSD → nó ghi object và đồng thời gửi bản sao đến Replica OSD

    💡 Tổng cộng, 10GB dữ liệu gốc sẽ chiếm khoảng 20GB dung lượng vật lý (vì replica=2).

    4. PG nhiều có phải performance tốt hơn?

    Không phải lúc nào cũng đúng.

    PG ÍtPG Nhiều
    Ít OSD xử lý → dễ quá tảiCân bằng tốt hơn giữa các OSD
    Ít context switch hơnTăng context switch CPU
    Dễ quản lýTăng overhead (bộ nhớ, CPU)
    Performance ổn định với cụm nhỏDễ bị “PG peering”, chậm nếu cụm không đủ tài nguyên

    🔎 Quy luật thực tiễn (Ceph guideline):

    Tổng PGs trong pool ≈ 100 × Số OSD / Số pool
    (giữ PGs mỗi OSD khoảng 100 – 200 là lý tưởng)

    Nếu quá nhiều PGs, CPU và RAM của monitor + OSD sẽ bị ăn tài nguyên nhiều, khiến hiệu năng giảm chứ không tăng.

    5. PG nhiều có giúp chịu lỗi tốt hơn không?

    PG nhiều sẽ không trực tiếp làm hệ thống chịu lỗi tốt hơn, nhưng có thể GIÁN TIẾP giúp hệ thống ổn định hơn nếu cụm đủ lớn và tài nguyên đủ mạnh.

    ✅ Khi nào PG nhiều giúp hệ thống ổn định hơn:

    • Tăng khả năng phân tán dữ liệu:
      • PG nhiều → object được phân bố đều hơn lên nhiều OSD → nếu 1 OSD chết thì mất ít dữ liệu hơn → ít PG phải “recovery” → phục hồi nhanh hơn.
    • Recovery song song hơn:
      • Khi OSD bị lỗi, các PG liên quan sẽ kích hoạt quá trình backfill/recovery.
      • PG nhiều → nhiều luồng phục hồi chạy song song hơn giữa các OSD → tốc độ phục hồi nhanh hơn nếu CPU + mạng tốt.
    • Tránh thắt cổ chai:
      • PG ít → 1 OSD có thể chứa nhiều PG → khi OSD chết, cluster sẽ cần phục hồi nhiều dữ liệu từ 1 điểm → rất chậm.

    ❌ Nhưng PG quá nhiều sẽ có mặt trái:

    • Tăng gánh nặng lên Monitor & OSD:
      • Mỗi PG có trạng thái riêng → nhiều PG → nhiều trạng thái phải theo dõi → tăng load cho MON, OSD daemon.
    • Tăng RAM và CPU tiêu thụ:
      • Mỗi PG cần RAM để lưu metadata, trạng thái, xử lý peering…
      • Quá nhiều PG khiến OSD bị “OOM” hoặc hoạt động kém hiệu quả.
    • Peering chậm hơn khi khởi động lại:
      • Ceph phải “peering” lại tất cả PG sau khi restart hoặc khi có sự cố network.
      • PG nhiều → thời gian peering kéo dài → cluster “inactive” lâu hơn.
    PG NhiềuẢnh hưởng
    ✅ Phân tán dữ liệu tốt hơn↗ Tăng khả năng phục hồi
    ✅ Recovery song song hơn↗ Phục hồi nhanh hơn nếu tài nguyên đủ
    ❌ Tăng tải cho MON/OSD↘ Có thể gây phản tác dụng nếu cụm yếu
    ❌ Peering chậm hơn↘ Dễ bị delay sau restart hoặc lỗi lớn

    🛠 Gợi ý cấu hình PG phù hợp (theo Red Hat/Ceph guideline):

    • Tổng PG trong cluster100 × số OSD / số pool
    • PG mỗi OSD nên trong khoảng 100–200

    Ví dụ 10 OSD, 2 pool → 100 × 10 / 2 = 500 PGs/pool

    6. Ví dụ thực tế để tính toán lượng PG.

    6.1. Ví dụ đầu là một cụm nhỏ cho dễ hiểu.

    Thông tin cụm như sau:

    • Replication: 2
    • Số node: 5
    • Disk mỗi node: 22
    • ⇒ Tổng OSD = 5 × 22 = 110
    • Số pool: 1

    Bước 1: Tính số PG lý tưởng theo công thức Ceph

    Tổng PG ≈ (Tổng OSD × 100) / (replica × số pool)
             = (110 × 100) / (2 × 1)
             = 11,000 / 2
             = 5,500 PG

    Bước 2: Chọn số PG hợp lý (bội số 2)

    Ta chọn số gần nhất là 4096 hoặc 8192

    PG TotalPG mỗi OSDGhi chú
    4096~37Nhẹ, dễ quản lý
    8192~74.5Tốt cho SSD, phục hồi ổn, cân bằng hơn
    16384~149Dành cho cluster được tuning kỹ

    📌 Khuyến nghị:

    → Với SSD, 110 OSD, dùng 8192 PG là hợp lý nhất

    🛠 Cách tạo pool:

    ceph osd pool create test-pool 8192 8192
    ceph osd pool set test-pool size 2

    💬 Giải thích:

    • Mỗi object Ceph được ánh xạ vào 1 PG.
    • PG sẽ quyết định OSD nào chứa object.
    • PG nhiều giúp phân tán dữ liệu đều hơn, giảm nguy cơ “hot” OSD.
    • Quá ít PG → unbalanced → recovery/hiệu năng kém
    • Quá nhiều PG → RAM/CPU tốn → latency tăng

    Dưới đây là một sơ đồ đơn giản để minh họa luồng ghi dữ liệu từ client → pool → PG → OSDs (replica=2) ở ví dụ này. Ta giả sử:

    • Cluster 5 node, mỗi node 22 OSD (tổng 110 OSD)
    • Pool tên là test-pool
    • Có 8192 PG trong pool
    • Client ghi 1 file .mp4 10GB vào pool

    📦 Luồng ghi file .mp4 10GB vào Ceph pool (replica=2)

    Client
      |
      v
    +------------------+
    | Ceph Client Lib  |
    | (librados)       |
    +------------------+
            |
            v
    +-------------------------+
    |  Băm tên file           |
    |  Ví dụ: "video1.mp4"    |
    |  => PG# = HASH % 8192   |
    +-------------------------+
            |
            v
    +-------------------------+
    |  Pool: test-pool        |
    |  PG: pg_id = 1234.test-pool |
    +-------------------------+
            |
            v
    +-------------------------+
    |  PG#1234 assigned to:   |
    |  Primary OSD: osd.17    |
    |  Replica  OSD: osd.44   |
    +-------------------------+
            |                    |
            v                    v
       osd.17 (node2)     osd.44 (node5)
           |                   |
           v                   v
    +-----------+       +-----------+
    | Writes    |       | Replicas  |
    | 5GB data  |       | 5GB copy  |
    +-----------+       +-----------+
    
    # Tổng cộng 10GB được nhân đôi → chiếm 20GB cluster space

    🧠 Quá trình ghi file

    • Client ghi file .mp4 10GB
      • Ceph client tính toán hash tên file → xác định PG (ví dụ PG#1234)
      • PG này được ánh xạ tới 2 OSD (do replica=2) – 1 primary, 1 secondary
      • Primary OSD nhận dữ liệu, sau đó replicate nội dung sang OSD thứ 2
      • Ghi thành công khi cả 2 OSD xác nhận OK

    🧯 Quá trình replica khi có lỗi

    • Nếu osd.17 chết:
      • osd.44 trở thành primary tạm thời
      • Ceph sẽ tự động re-replicate từ osd.44 sang 1 OSD mới (ví dụ osd.88)
      • Tạo lại 2 bản replica để đảm bảo redundancy

    🔍 Quá trình đọc file .mp4 từ Ceph pool

    Giả sử file nằm trên PG#1234 → ánh xạ tới:

    • Primary OSD: osd.17 (node2)
    • Replica OSD: osd.44 (node5)
    Client
      |
      v
    +------------------+
    | Ceph Client Lib  |
    +------------------+
            |
            v
    +-------------------------+
    | Tính hash "video1.mp4" |
    | → PG#1234              |
    +-------------------------+
            |
            v
    +-----------------------------+
    |  Lookup PG#1234            |
    |  Primary OSD = osd.17      |
    +-----------------------------+
            |
            v
         osd.17 (node2)
            |
            v
    +----------------+
    | Gửi dữ liệu về |
    | cho client     |
    +----------------+
    
    # Nếu osd.17 sống → đọc từ osd.17
    # Nếu osd.17 chết → đọc từ osd.44

    🛠️ Quá trình Recovery (khi 1 OSD chết)

    Giả sử osd.17 (primary) chết, osd.44 còn sống:

    osd.17 ✖ (node2 chết)
             ↓
    +----------------------+
    | Monitor phát hiện    |
    | PG#1234 mất 1 replica|
    +----------------------+
             ↓
    +----------------------+
    | Mark osd.17 down     |
    | Promote osd.44       |
    | → thành primary      |
    +----------------------+
             ↓
    +-------------------------------+
    | Tìm OSD khác để re-replicate |
    | → Chọn osd.88 (node4)        |
    +-------------------------------+
             ↓
    osd.44 (mới primary)
       |
       +--> Replicate PG#1234 data
       |     to osd.88
       v
    osd.88 (new replica)

    Khi hoàn tất:

    • PG#1234 lại có 2 replica (osd.44 và osd.88)
    • Cluster trở về trạng thái HEALTH_OK
    Tình huốngDiễn giải
    ĐọcClient lấy dữ liệu từ primary OSD của PG
    Primary chếtSecondary tự động trở thành primary
    RecoveryDữ liệu được replicate sang OSD mới để khôi phục đủ replica
    Replica=2Chỉ cần 1 OSD sống vẫn còn dữ liệu là có thể đọc và recovery được

    6.2. Ví dụ cách tính số lượng PG phù hợp cho một pool lớn.

    • 30 nodes
    • 22 disk SSD mỗi node
    • Tổng OSD = 30 × 22 = 660
    • Pool sử dụng replication 2 (replica = 2)

    🔢 Tính toán số lượng PG phù hợp

    Theo công thức khuyến nghị của Ceph (Red Hat guideline):

    Số PG trên pool ≈ (OSD tổng × 100) / (replica × số pool)

    Vì bạn đang nói về 1 pool duy nhất, ta thay vào:

    PG ≈ (660 × 100) / (2 × 1) = 66,000 / 2 = 33,000 PG

    ❗ Nhưng khoan!

    Đây là con số lý tưởng tổng PG cho cả cụm, nhưng bạn không nên tạo quá nhiều PG ngay từ đầu vì:

    • Ceph khuyến nghị PG mỗi OSD nên nằm trong khoảng 100–200
    • Với 660 OSD, tổng PG hợp lý nên khoảng:
      • 660 × 100 = 66,000 (tối đa)
      • 660 × 150 = 99,000 (nếu cluster mạnh và được tuning tốt)

    ✅ Gợi ý thực tế

    Tốt nhất là chọn PG là bội số của 2, để tối ưu hiệu năng hash và phân phối object:

    Số PGPG mỗi OSDGhi chú
    16,384~24.8An toàn, dễ quản lý
    32,768~49.6Trung bình, phù hợp sản xuất
    65,536~99.3Tối ưu nếu cụm mạnh như của bạn
    131,072~198.7Cực lớn – cần nhiều RAM/CPU

    📌 Khuyến nghị của mình:
    Dùng 65536 PG cho pool replica=2 (cân bằng giữa hiệu năng, phân tán và khả năng chịu lỗi)
    → Nếu bạn định tạo thêm nhiều pool sau này, hãy chia nhỏ hơn (ví dụ 32768/pool)

    🛠 Cách tạo pool với 65536 PG:

    ceph osd pool create video-pool 65536 65536
    ceph osd pool set video-pool size 2

    💬 Tổng kết

    • PG nhiều không trực tiếp tăng khả năng chịu lỗi, nhưng:
      • Giúp recovery phân tán hơn
      • Giảm ảnh hưởng khi OSD chết
    • Với 660 OSD + replica=2, số PG lý tưởng cho 1 pool là khoảng 65536
    • Tránh vượt quá 200 PG/OSD trừ khi bạn đã tuning rất kỹ

    Bài viết gần đây

    spot_img

    Related Stories

    Leave A Reply

    Please enter your comment!
    Please enter your name here

    Đăng ký nhận thông tin bài viết qua email