Tanpa sharding, seluruh data dalam sebuah koleksi berada di satu shard, sedangkan shard lainnya menganggur. Sharding mendistribusikan data ke seluruh shard sehingga setiap shard menangani sebagian beban kerja.
Contoh berikut menunjukkan output db.stats() sebelum sharding dikonfigurasi. Satu shard (mgset-xxx65) tidak menyimpan data sama sekali, sedangkan seluruh 1.000.021 objek berada di shard lainnya (mgset-xxx67):
mongos> db.stats()
{
"raw" : {
"mgset-xxx65/xxx" : {
"db" : "mongodbtest",
"collections" : 0,
"views" : 0,
"objects" : 0,
"avgObjSize" : 0,
"dataSize" : 0,
"storageSize" : 0,
"numExtents" : 0,
"indexes" : 0,
"indexSize" : 0,
"fileSize" : 0,
"ok" : 1,
"$gleStats" : {
"lastOpTime" : Timestamp(0, 0),
"electionId" : ObjectId("7fffffff0000000000000001")
}
},
"mgset-xxx67/xxx" : {
"db" : "mongodbtest",
"collections" : 2,
"views" : 0,
"objects" : 1000021,
"avgObjSize" : 352.4417477232978,
"dataSize" : 352449149,
"storageSize" : 209125376,
"numExtents" : 0,
"indexes" : 1,
"indexSize" : 10141696,
"ok" : 1,
"$gleStats" : {
"lastOpTime" : Timestamp(0, 0),
"electionId" : ObjectId("7fffffff0000000000000001")
}
}
}
}Prasyarat
Instans harus merupakan instans kluster sharded.
Pemilihan kunci shard
Kunci shard menentukan cara MongoDB mendistribusikan data ke seluruh shard. Pilih kunci shard dengan cermat karena secara langsung memengaruhi performa kueri dan distribusi data. Untuk informasi lebih lanjut tentang kunci shard, lihat Shard keys dan Cara memilih kunci shard.
Kunci shard yang baik memiliki tiga sifat:
Cardinality tinggi: Kunci memiliki banyak nilai unik, memungkinkan distribusi data yang detail halus.
Frekuensi rendah: Tidak ada satu nilai kunci yang mendominasi. Nilai yang sering muncul menghasilkan chunk besar yang tidak dapat dipindahkan.
Perubahan non-monotonik: Nilai kunci tidak terus-menerus meningkat atau menurun. Kunci monotonik mengarahkan seluruh operasi write ke satu shard.
Kemampuan mengubah kunci shard bergantung pada versi MongoDB:
Sebelum 4.4: Kunci shard tidak dapat dimodifikasi atau dihapus setelah dibuat.
4.4 dan seterusnya: refineCollectionShardKey menambahkan bidang sufiks ke kunci shard yang sudah ada.
5.0 dan seterusnya: reshardCollection mengganti kunci shard sepenuhnya.
Strategi sharding
MongoDB mendukung range sharding, hashed sharding, dan kunci shard majemuk (compound).
| Properti | Range sharding | Hashed sharding |
|---|---|---|
| Mekanisme | Membagi data menjadi chunk berdasarkan rentang nilai kunci shard | Melakukan hash terhadap nilai satu bidang dan mendistribusikan data berdasarkan rentang hash |
| Distribusi | Dapat tidak merata; berpotensi menciptakan hot spot tanpa distribusi write | Distribusi merata di seluruh node shard; menyediakan distribusi write |
| Kueri rentang | Efisien. Router mongos langsung menentukan shard target. | Tidak efisien. Kueri dikirim ke semua node shard. |
| Paling cocok untuk | Kunci non-monotonik dengan cardinality tinggi dan frekuensi rendah; workload yang mengandalkan kueri rentang | Kunci yang terus-menerus meningkat atau menurun dengan cardinality tinggi; workload yang memerlukan read dan write acak |
| Nilai kunci shard | 1 (ascending) atau -1 (descending) | "hashed" |
Kunci shard majemuk (compound) menggabungkan beberapa bidang. Gunakan kunci majemuk ketika tidak ada satu bidang pun yang memberikan cardinality cukup, atau ketika kueri melakukan filter berdasarkan beberapa bidang. Misalnya, gabungkan kunci dengan cardinality rendah dengan kunci yang nilainya terus meningkat.
Pilih strategi
Gunakan range sharding ketika kueri sering memindai rentang nilai kunci shard. Pastikan kuncinya non-monotonik untuk menghindari hot spot.
Gunakan hashed sharding ketika volume write tinggi dan data harus didistribusikan secara merata. Terima kompromi bahwa kueri rentang akan mengenai semua node shard.
Shard sebuah koleksi
Prosedur berikut menggunakan database mongodbtest dan koleksi customer sebagai contoh.
Langkah 1: Hubungkan ke kluster sharded
Hubungkan ke instans kluster sharded melalui mongo shell. Untuk metode koneksi, lihat Masuk ke instans kluster sharded.
Langkah 2: Aktifkan sharding untuk database
Lewati langkah ini jika instans menjalankan MongoDB 6.0 atau versi lebih baru. Mulai MongoDB 6.0, sh.enableSharding() tidak lagi diperlukan.
Jalankan perintah berikut untuk mengaktifkan sharding pada database target:
sh.enableSharding("mongodbtest")Langkah 3: Buat indeks pada kunci shard
Sebelum melakukan sharding pada koleksi, buat indeks yang mendukung kunci shard.
Sintaks:
db.<collection>.createIndex(<keyPatterns>, <options>)Untuk informasi lebih lanjut, lihat db.collection.createIndex().
Contoh range sharding (indeks ascending pada bidang name):
db.customer.createIndex({ name: 1 })Contoh hashed sharding (indeks hashed pada bidang name):
db.customer.createIndex({ name: "hashed" })Nilai tipe indeks:
| Nilai | Tipe |
|---|---|
1 | Ascending |
-1 | Descending |
"hashed" | Hashed |
Langkah 4: Shard koleksi
Jalankan sh.shardCollection() untuk melakukan sharding pada koleksi.
Sintaks:
sh.shardCollection("<database>.<collection>", { "<key>": <value> })Contoh range sharding:
sh.shardCollection("mongodbtest.customer", { "name": 1 })Contoh hashed sharding:
sh.shardCollection("mongodbtest.customer", { "name": "hashed" })Parameter <value> menentukan strategi sharding:
| Nilai | Strategi |
|---|---|
1 | Range sharding |
"hashed" | Hashed sharding |
Langkah 5: Tunggu balancer mendistribusikan data
Setelah Anda mengonfigurasi sharding, balancer secara otomatis membagi data yang memenuhi kriteria dan memigrasikan chunk ke seluruh node shard.
Balancer mengonsumsi sumber daya instans selama migrasi data. Lakukan sharding awal pada jam sepi. Atur jendela aktif untuk balancer guna membatasi aktivitas balancer pada periode waktu tertentu dan mencegah dampak performa selama jam sibuk.
Verifikasi konfigurasi sharding
Periksa distribusi data
Jalankan sh.status() untuk melihat status sharding dan distribusi data di seluruh node shard:
mongos> sh.status()
--- Sharding Status ---
sharding version: {
"_id" : 1,
"minCompatibleVersion" : 5,
"currentVersion" : 6,
"clusterId" : ObjectId("5xxx")
}
shards:
{ "_id" : "d-bpxxx3c4", "host" : "mgset-xxx29/xxx", "state" : 1 }
{ "_id" : "d-bpxxx834", "host" : "mgset-xxx27/xxx", "state" : 1 }
active mongoses:
"3.4.6" : 2
autosplit:
Currently enabled: yes
balancer:
Currently enabled: yes
Currently running: no
Failed balancer rounds in last 5 attempts: 0
Migration Results for the last 24 hours:
51 : Success
databases:
{ "_id" : "mongodbtest", "primary" : "d-bpxxx834", "partitioned" : true }
mongodbtest.customer
shard key: { "name" : 1 }
unique: false
balancing: true
chunks:
d-bpxxx3c4 51
d-bpxxx834 52
too many chunks to print, use verbose if you want to force print
{ "_id" : "test", "primary" : "d-bpxxx834", "partitioned" : false }Periksa penyimpanan per shard
Jalankan db.stats() untuk melihat statistik penyimpanan tiap node shard:
mongos> db.stats()
{
"raw" : {
"mgset-xxx" : {
"db" : "mongodbtest",
"collections" : 2,
"views" : 0,
"objects" : 496075,
"avgObjSize" : 353.0421932167515,
"dataSize" : 175135406,
"storageSize" : 434943968,
"numExtents" : 0,
"indexes" : 2,
"indexSize" : 17107270,
"ok" : 1,
"$gleStats" : {
"lastOpTime" : Timestamp(0, 0),
"electionId" : ObjectId("7fffffff0000000000000001")
}
},
"mgset-xxx" : {
"db" : "mongodbtest",
"collections" : 2,
"views" : 0,
"objects" : 505423,
"avgObjSize" : 352.9883444164591,
"dataSize" : 178408428,
"storageSize" : 501801512,
"numExtents" : 0,
"indexes" : 2,
"indexSize" : 17493372,
"ok" : 1,
"$gleStats" : {
"lastOpTime" : Timestamp(0, 0),
"electionId" : ObjectId("7fffffff0000000000000001")
}
}
}
}Setelah sharding, kedua node shard menyimpan jumlah data yang hampir sama (masing-masing sekitar 496.075 dan 505.423 objek).