MongoDB และชุดข้อมูลที่ไม่พอดีกับ RAM ไม่ว่าคุณจะผลักอย่างไร


12

สิ่งนี้ขึ้นอยู่กับระบบเป็นอย่างมาก แต่มีโอกาสใกล้ที่แน่นอนว่าเราจะขยายขอบเขตหน้าผาตามอำเภอใจและเข้าสู่ปัญหาจริง ฉันอยากรู้ว่ากฎของหัวแม่มือมีอยู่เท่าไหร่สำหรับอัตราส่วน RAM ต่อพื้นที่ว่างในดิสก์ที่ดี เรากำลังวางแผนระบบรอบต่อไปของเราและต้องเลือกตัวเลือกบางอย่างเกี่ยวกับ RAM, SSD และจำนวนโหนดใหม่ที่จะได้รับ

แต่ตอนนี้สำหรับรายละเอียดประสิทธิภาพ!

ในช่วงเวิร์กโฟลว์ปกติของการดำเนินการโครงการเดียว MongoDB จะได้รับผลกระทบสูงมากจากการเขียน (70-80%) เมื่อขั้นตอนที่สองของไปป์ไลน์การประมวลผลได้รับผลกระทบการอ่านจะสูงมากเนื่องจากต้องทำซ้ำระเบียนที่ระบุในการประมวลผลครึ่งแรก นี่คือเวิร์กโฟลว์ที่สร้าง "ชุดการทำงานของคุณไว้ใน RAM" และเรากำลังออกแบบตามสมมติฐานนั้น

ชุดข้อมูลทั้งหมดถูกตีอย่างต่อเนื่องโดยมีการสุ่มแบบสอบถามจากแหล่งที่มาของผู้ใช้ปลายทาง แม้ว่าความถี่จะไม่สม่ำเสมอ แต่ขนาดมักจะค่อนข้างเล็ก (10 กลุ่มของเอกสาร) เนื่องจากเป็นแบบผู้ใช้การตอบกลับจึงต้องอยู่ภายใต้เกณฑ์ "เบื่อตอนนี้" เป็นเวลา 3 วินาที รูปแบบการเข้าถึงนี้มีโอกาสน้อยที่จะอยู่ในแคชดังนั้นจะมีแนวโน้มที่จะเกิดการพบดิสก์มาก

เวิร์กโฟลว์การประมวลผลรองคือการอ่านค่าสูงของการประมวลผลก่อนหน้าซึ่งอาจเป็นวันสัปดาห์หรือเดือนเก่าและมีการเรียกใช้ไม่บ่อยนัก แต่ยังคงต้องมีกำลังใจ สามารถเข้าถึงเอกสารได้สูงสุด 100% ในการดำเนินการประมวลผลก่อนหน้า ฉันสงสัยว่าจะไม่มีแคชอุ่นเครื่องในจำนวนนี้

ขนาดเอกสารเสร็จแตกต่างกันไป แต่ขนาดเฉลี่ยอยู่ที่ประมาณ 8K

ส่วนที่มีการอ่านสูงของการประมวลผลโครงการปกติแนะนำอย่างยิ่งให้ใช้ Replicas เพื่อช่วยกระจายปริมาณการอ่าน ฉันได้อ่านที่อื่นว่า 1:10 RAM-GB ถึง HD-GB เป็นกฎที่ดีสำหรับดิสก์ช้าเนื่องจากเรากำลังพิจารณาอย่างจริงจังว่าจะใช้ SSD ที่เร็วกว่ามากฉันต้องการทราบว่ามีกฎที่คล้ายคลึงกันหรือไม่ ของหัวแม่มือสำหรับดิสก์ที่รวดเร็ว

ฉันรู้ว่าเรากำลังใช้ Mongo ในวิธีที่แคชทุกอย่างไม่ได้บินไปด้วยเหตุนี้ฉันจึงมองหาวิธีในการสร้างระบบที่สามารถอยู่รอดได้ในการใช้งานดังกล่าว ทั้งชุดข้อมูลที่มีแนวโน้มที่จะมากที่สุดของวัณโรคภายในครึ่งปีและการเจริญเติบโตให้


คำถามที่ยากถามดี
gWaldo

ดูเหมือนว่าคุณอาจจะประสบปัญหาการล็อคการเขียนก่อนที่คุณจะสามารถปรับแต่งสำหรับ IO มากโดยสุจริต ถ้าคุณใช้ฐานข้อมูลด้วยการเขียนคุณอาจหยุดการเขียนไว้นานพอที่การสืบค้นจะหยุดลงโดยไม่คำนึงว่า IO พื้นฐานนั้นจะเร็วแค่ไหน บางอย่างเช่น Fusion IO สามารถลดการล็อคการเขียนได้เล็กน้อย แต่เพียงซื้อเวลาก็ไม่ใช่การแก้ไขที่แท้จริง
MrKurt

@MrKurt ส่วนหนึ่งของสิ่งที่ฉันพยายามที่จะคิดออกคือเมื่อฉันต้องการเศษนอกจากวิธีอ้วนฉันสามารถทำแบบจำลองแต่ละโหนด ข้อมูลจำเพาะชั่วคราวของฉันมีการ์ด SSD แบบ PCIe ที่เกี่ยวข้อง
sysadmin1138

อ่าเข้าใจแล้ว คุณอาจจะลองคิดว่าตั้งแต่เริ่มแรกเราใช้เซิร์ฟเวอร์ตัวเดียวมาก มันช่วยให้คุณสามารถเขียนล็อกและปรับขนาดการเขียนไปยังคอร์ทั้งหมดได้อย่างมีประสิทธิภาพ นอกจากนี้ยังง่ายต่อการย้ายเศษระหว่างเซิร์ฟเวอร์ในภายหลัง
MrKurt

คำตอบ:


5

นี่จะเป็นจุดเล็ก ๆ อย่างไรก็ตามไม่มีคำตอบเดียวสำหรับคำถามของคุณ

MongoDB อนุญาตให้เคอร์เนลระบบปฏิบัติการจัดการหน่วยความจำได้ นอกเหนือจากการขว้างแรมมากที่สุดเท่าที่เป็นไปได้แล้วยังมีเพียงไม่กี่อย่างที่สามารถทำได้เพื่อ 'จัดการ' ชุดการทำงานของคุณ

สิ่งหนึ่งที่คุณสามารถทำได้เพื่อเพิ่มประสิทธิภาพการเขียนคือการสอบถามครั้งแรกสำหรับระเบียนนั้น (อ่าน) เพื่อให้มันอยู่ในหน่วยความจำที่ใช้งานได้ สิ่งนี้จะหลีกเลี่ยงปัญหาประสิทธิภาพการทำงานที่เกี่ยวข้องกับ Global Lock ทั่วทั้งกระบวนการ (ซึ่งควรจะเป็นแบบต่อฐานใน v2.2)

ไม่มีกฎที่ยากและรวดเร็วสำหรับอัตราส่วน RAM vs SSD แต่ฉันคิดว่า IOPS แบบดิบของ SSD ควรอนุญาตให้คุณใช้อัตราส่วนที่ต่ำกว่ามาก จากด้านบนของหัวฉัน 1: 3 น่าจะเป็นสิ่งที่ต่ำที่สุดที่คุณต้องการ แต่ด้วยค่าใช้จ่ายที่สูงขึ้นและความสามารถที่ลดลงคุณก็จะต้องลดอัตราส่วนนั้นลง

เกี่ยวกับ 'Write vs Reading phases' ฉันกำลังอ่านอย่างถูกต้องหรือไม่ว่าเมื่อมีการเขียนเร็กคอร์ดจะมีการอัปเดตน้อยมาก ("พลิกผัน")? หากเป็นกรณีนี้มันอาจจะคุ้มค่าที่จะโฮสต์สองคลัสเตอร์ คลัสเตอร์เขียนปกติและอ่านเพิ่มประสิทธิภาพคลัสเตอร์สำหรับข้อมูลของ "อายุ" ที่ยังไม่ได้รับการแก้ไขใน[ระยะเวลา X] แน่นอนฉันจะเปิดใช้งานทาส - อ่านในคลัสเตอร์นี้ (โดยส่วนตัวแล้วฉันจัดการด้วยการใส่ค่าวันที่แก้ไขในเอกสารวัตถุของ db ของคุณ)

หากคุณมีความสามารถในการทดสอบโหลดก่อนเข้าสู่ Prod ตรวจสอบนรกให้ดีก่อน MongoDB เขียนขึ้นโดยมีข้อสันนิษฐานว่ามันมักจะถูกนำไปใช้ใน VMs (ระบบอ้างอิงของพวกเขาอยู่ใน EC2) ดังนั้นอย่ากลัวที่จะแตกออกจาก VMs


ในระหว่างการประมวลผล stub เอกสารเริ่มต้นจะถูกสร้างขึ้นและถูกอัพเดทอย่างต่อเนื่องโดยขั้นตอนย่อยต่างๆในส่วนแรกของการประมวลผล เราได้ชั่งน้ำหนักความเป็นไปได้ในการทำแผ่นรองมือในส่วนเริ่มต้นเพื่อลดปริมาณการขยายที่เรากำลังทำอยู่ แต่เปอร์เซ็นต์ล็อกการเขียนปัจจุบันของเราต่ำอย่างมีความสุข
sysadmin1138

คำแนะนำในการอ่านบันทึกก่อนที่จะเขียนลงไปเพื่อนำไปไว้ในหน่วยความจำ RAM ไม่ใช่คำแนะนำที่ดี ตั้งแต่ 2.0 (กลางปี ​​2011) MongoDB ให้ผลผลิตถ้าข้อมูลที่จะเข้าถึงไม่ได้อยู่ใน RAM ดังนั้นคุณแค่เพิ่มการอ่านและการออกรอบพิเศษไปยังเซิร์ฟเวอร์โดยไม่มีเหตุผลถ้าคุณทำเช่นนั้นตั้งแต่การล็อค จะไม่ถูกจัดขึ้นในช่วงเวลานั้น
Asya Kamsky

13

นี่เป็นส่วนเพิ่มเติมของคำตอบอื่น ๆ ที่โพสต์ไว้ที่นี่ซึ่งจะพิจารณาองค์ประกอบที่เกี่ยวข้องจำนวนมากที่นี่ อย่างไรก็ตามยังมีอีกปัจจัยหนึ่งที่มักถูกมองข้ามเมื่อคำนึงถึงการใช้ RAM อย่างมีประสิทธิภาพในระบบการเข้าถึงแบบสุ่ม - อ่านแล้ว

คุณสามารถตรวจสอบการตั้งค่าปัจจุบันสำหรับ readahead (บน Linux) โดยเรียกใช้blockdev --report(โดยปกติจะต้องใช้สิทธิ์ sudo / root) สิ่งนี้จะพิมพ์ตารางที่มีหนึ่งแถวสำหรับแต่ละอุปกรณ์ดิสก์ คอลัมน์ RA มีค่าสำหรับ readahead ค่านั้นคือจำนวนของเซกเตอร์ 512 ไบต์ (ยกเว้นว่าขนาดเซกเตอร์ไม่ใช่ค่าเริ่มต้น - โปรดทราบว่า ณ เวลาที่เขียนโพสต์นี้แม้ดิสก์ที่มีขนาดใหญ่กว่าจะถือว่าเป็นเซกเตอร์ 512 ไบต์โดยเคอร์เนล) ที่อ่านทุก การเข้าถึงดิสก์

คุณสามารถกำหนดการตั้งค่า readahead สำหรับอุปกรณ์ดิสก์ที่กำหนดโดยเรียกใช้:

blockdev --setra <value> <device name>

เมื่อใช้ระบบ RAID ที่ใช้ซอฟต์แวร์ตรวจสอบให้แน่ใจว่าได้ตั้งค่าหัวอ่านบนอุปกรณ์ดิสก์แต่ละตัวรวมถึงอุปกรณ์ที่สอดคล้องกับคอนโทรลเลอร์ RAID

ทำไมสิ่งนี้จึงสำคัญ อ่านแล้วใช้ทรัพยากรเดียวกัน MongoDB พยายามใช้เพื่อเพิ่มประสิทธิภาพการอ่านของคุณสำหรับการเข้าถึงลำดับ - RAM เมื่อคุณทำการอ่านตามลำดับบนดิสก์หมุน (หรืออุปกรณ์ที่มีลักษณะคล้ายดิสก์หมุนอยู่แล้ว - EBS ฉันกำลังมองคุณอยู่) การดึงข้อมูลที่อยู่ใกล้เคียงลงใน RAM สามารถเพิ่มประสิทธิภาพได้อย่างมากช่วยคุณในการค้นหาและตั้งค่า readahead สูงใน สภาพแวดล้อมที่เหมาะสมสามารถให้ผลลัพธ์ที่น่าประทับใจแก่คุณ

สำหรับระบบอย่างเช่น MongoDB ที่การเข้าถึงของคุณโดยทั่วไปจะเป็นการเข้าถึงแบบสุ่มในชุดข้อมูลนี่เป็นเพียงการสูญเสียหน่วยความจำที่ใช้ในที่อื่นดีกว่า ระบบดังกล่าวที่อื่นจัดการหน่วยความจำสำหรับ MongoDB ด้วยกำลังจะจัดสรรหน่วยความจำให้กับ readahead เมื่อมีการร้องขอดังนั้นจึงปล่อยให้ RAM น้อยลงเพื่อให้ MongoDB ใช้งานได้อย่างมีประสิทธิภาพ

การเลือกขนาดหัวอ่านที่ถูกต้องนั้นมีความยุ่งยากและขึ้นอยู่กับฮาร์ดแวร์ของคุณการกำหนดค่าขนาดบล็อกขนาดแถบและข้อมูล หากคุณย้ายไปยัง SSD คุณจะต้องการการตั้งค่าต่ำ แต่จะขึ้นอยู่กับข้อมูล

เพื่ออธิบาย: คุณต้องการตรวจสอบให้แน่ใจว่าหัวอ่านสูงพอที่จะดึงเอกสารฉบับเต็มและไม่ต้องกลับไปที่ดิสก์ ลองใช้ขนาดเฉลี่ยของคุณที่กล่าวถึง 8k - เนื่องจากส่วนบนดิสก์โดยทั่วไปคือ 512 ไบต์มันจะใช้เวลาเข้าถึงดิสก์ 16 ครั้งในการอ่านเอกสารทั้งหมดโดยไม่ต้องอ่าน หากคุณมีส่วนหัวอ่าน 16 ส่วนขึ้นไปคุณจะอ่านเอกสารทั้งหมดด้วยการเดินทางไปยังดิสก์เพียงครั้งเดียว

ที่จริงแล้วเนื่องจากถังเก็บดัชนี MongoDB เป็น 8k คุณจะไม่ต้องการตั้งค่า readahead ที่ต่ำกว่า 16 ใหม่อีกต่อไปหรือจะใช้การเข้าถึงดิสก์ 2 แผ่นเพื่ออ่านในที่เก็บดัชนีหนึ่งชุด แนวปฏิบัติที่ดีทั่วไปคือเริ่มต้นด้วยการตั้งค่าปัจจุบันของคุณลดลงครึ่งหนึ่งจากนั้นประเมินการใช้ RAM และ IO อีกครั้งและดำเนินการต่อจากที่นั่น


1
ข้อมูลที่มีค่าซึ่งจะมีประโยชน์เมื่อเรานำฮาร์ดแวร์มาเอง ขอบคุณ!
sysadmin1138

3

คุณควรพิจารณาใช้แบบจำลองสำหรับการสืบค้นของผู้ใช้ปลายทางและทำให้เวิร์กโฟลว์ของคุณทำบนเครื่องอื่น

ด้วยการใช้กฏหัวแม่มือ 1:10 ของคุณคุณกำลังดู RAM ขนาด 128GB สำหรับพื้นที่เก็บข้อมูล 1TB; ในขณะที่ SSD ราคาไม่แพงบางตัวในปัจจุบันเรียกร้องให้ถึง> 60K IOPS ตัวเลขในโลกแห่งความเป็นจริงอาจแตกต่างกันเล็กน้อยเช่นเดียวกับว่าคุณใช้ RAID กับ SSD ของคุณหรือไม่และถ้าคุณเป็นเช่นนั้นการ์ด RAID ก็สำคัญอย่างยิ่งเช่นกัน .

ในขณะที่โพสต์นี้เพิ่มขึ้นจาก 128GB ของ DDR3 ECC ram เป็น 256GB ดูเหมือนว่าจะเพิ่มขึ้นประมาณ 2,000 $ สำหรับเซิร์ฟเวอร์ 1U Intel และจะให้อัตราส่วน 1: 5 กับข้อมูล 1TB ซึ่งฉันรู้สึกว่าเป็น อัตราส่วนที่ดียิ่งขึ้น หากคุณต้องการให้ปริมาณงานของคุณเสร็จเร็วที่สุดหน่วยความจำเพิ่มเติมจะช่วยได้แน่นอน แต่นั่นเป็นเรื่องเร่งด่วนจริงหรือ

คุณจะต้องทำการปรับแต่งระบบไฟล์บางอย่างเช่น "noatime, data = writeback, nobarrier" บน ext4 และคุณอาจต้องทำการปรับแต่งเคอร์เนลบางตัวเพื่อปรับแต่งประสิทธิภาพที่ดีที่สุดที่คุณสามารถทำได้ ระบบ.

หากคุณใช้ RAID RAID-10 จะเป็นตัวเลือกที่ดีและด้วยคอนโทรลเลอร์ RAID ที่เหมาะสมจะให้ประสิทธิภาพที่เพิ่มขึ้น แต่ด้วยพื้นที่ว่างที่เหลืออยู่ของคุณ นอกจากนี้คุณยังสามารถดูใน RAID50 หากคุณต้องการเพิ่มประสิทธิภาพที่เหมาะสมโดยไม่ต้องลดพื้นที่ว่างลง ความเสี่ยงในการใช้งาน RAID คือคุณไม่สามารถเข้าถึง TRIM บนไดรฟ์ของคุณได้อีกต่อไปซึ่งหมายความว่าคุณจำเป็นต้องย้ายข้อมูลออกเป็นครั้งคราวสลาย RAID, TRIM ไดรฟ์และสร้าง RAID ใหม่

ในที่สุดคุณจะต้องตัดสินใจว่าต้องการความซับซ้อนเท่าใดคุณต้องใช้เงินเท่าไหร่และต้องการให้ปริมาณงานของคุณประมวลผลเร็วแค่ไหน ฉันจะประเมินด้วยว่า MongoDB เป็นฐานข้อมูลที่เหมาะที่จะใช้หรือไม่เพราะคุณยังสามารถใช้ Mongo เพื่อค้นหาผู้ใช้ปลายทางที่ต้องการการตอบสนองที่รวดเร็ว แต่ใช้อย่างอื่นเพื่อประมวลผลข้อมูลของคุณซึ่งไม่จำเป็นต้องพร้อมในไม่กี่วินาที และยังช่วยให้คุณสามารถกระจายภาระงานของคุณในหลาย ๆ เครื่องได้อย่างง่ายดายยิ่งขึ้น

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.