Node.js แนะนำ“ max-old-space-size”


95

ฉันมีปัญหาบางอย่างที่จะเข้าใจวิธีการ Node.js max-old-space-sizeกระทำบนพื้นฐานของพารามิเตอร์

ตัวอย่างเช่นในกรณีของฉันฉันใช้งานt2.smallอินสแตนซ์ AWS สองอินสแตนซ์ (RAM 2GB)

ไม่แน่ใจว่าทำไม แต่ฉันตั้งค่าmax-old-space-size=4096(4GB) โหนดทำอะไรในกรณีนี้ การกำหนดค่านี้อาจทำให้เกิดความล้มเหลวในการจัดสรรหน่วยความจำได้หรือไม่

ฉันจะกำหนดค่าที่ถูกต้องmax-old-space-sizeตามทรัพยากรเซิร์ฟเวอร์ได้อย่างไร

แอปพลิเคชันของฉันมีการใช้งานหน่วยความจำเพิ่มขึ้นอย่างต่อเนื่องและฉันพยายามทำความเข้าใจทุกอย่างเกี่ยวกับโหนดภายใน


8
ฉันกำลังเพิ่มความคิดเห็นตอนนี้ฉันเห็นว่าฉันกำลังดูเงียบลงไปมาก ฉันใช้เวลาหนึ่งสัปดาห์เต็มในการรับรู้ว่าแอป NodeJS ของฉันไม่มีหน่วยความจำรั่ว แต่ตัวเก็บขยะไม่เคยเตะเข้ามาโปรดระวังเรื่องนี้ในระบบที่มีหน่วยความจำต่ำเช่นอินสแตนซ์ t2.micro หรือ t2.small เซิร์ฟเวอร์กำลังจะหยุดทำงานเนื่องจากแรมที่ไม่พร้อมใช้งาน
Borjante

มีวิธีเอาคนเก็บขยะมาเตะไหม?
ZG101

@Borjante ทำไมคนเก็บขยะไม่วิ่ง
ศักดิ์สิทธิ์

2
ขนาดพื้นที่สูงสุดเก่าที่กำหนดค่าไว้มีขีด จำกัด สูงกว่าจำนวน RAM ทั้งหมดที่เครื่องมี
Borjante

คำตอบ:


129

"พื้นที่เก่า" เป็นส่วนที่ใหญ่ที่สุดและสามารถกำหนดค่าได้มากที่สุดของฮีปที่มีการจัดการ (หรือที่เรียกว่าเก็บขยะ) ของ V8 (เช่นที่ที่วัตถุ JavaScript อาศัยอยู่) และ --max-old-space-sizeแฟล็กจะควบคุมขนาดสูงสุดของมัน เมื่อการใช้หน่วยความจำเข้าใกล้ขีด จำกัด V8 จะใช้เวลาในการรวบรวมขยะมากขึ้นเพื่อพยายามปลดปล่อยหน่วยความจำที่ไม่ได้ใช้

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

โดยสรุปในเครื่องที่มีหน่วยความจำ 2GB ฉันอาจตั้งค่าไว้--max-old-space-sizeที่ประมาณ 1.5GB เพื่อให้เหลือหน่วยความจำไว้ใช้งานอื่น ๆ และหลีกเลี่ยงการแลกเปลี่ยน


4
นั่นคือสิ่งที่ฉันหวังว่าจะได้รับคำตอบโดยอธิบายถึงกรณีขอบที่ระบบหรือโหนดมีหน่วยความจำหมด
Borjante

2
@jmrk: ดูเหมือนว่าคุณพูดถูกทั้งหมด แต่เมื่อฉันใช้ RAM 2GB และ 4GB สลับและตั้งค่า "--max-old-space-size" เป็น 4GB กระบวนการโหนดจะใช้หน่วยความจำ RAM ทั้งหมดและติดอยู่ที่ 1.9GB คำถามอยู่ที่นี่ "เหตุใดจึงหลีกเลี่ยงการใช้ swap ??" (โหนดเวอร์ชัน 8.11.1)
Manish Trivedi

1
ธงควรแทนที่สิ่งอื่นใด โปรดตรวจสอบการพิมพ์ผิดอีกครั้ง
jmrk

2
From d8 --help:--max-old-space-size (max size of the old space (in Mbytes))
jmrk

11

อัปเดตปี 2020

ตัวเลือกเหล่านี้จะได้รับการบันทึกในขณะนี้อย่างเป็นทางการโดยโหนด สำหรับเครื่อง 2GB คุณควรใช้:

NODE_OPTIONS=--max-old-space-size=1536

การกำหนดจำนวนเงินที่จะใช้ : คุณสามารถดูหน่วยความจำที่มีอยู่บนเครื่อง Linux free -mใช้ โปรดทราบว่าคุณสามารถใช้freeและbuffers/cacheหน่วยความจำรวมกันได้ตามที่buffers/cacheสามารถโยนทิ้งไปได้ (บัฟเฟอร์และแคชเหล่านี้เป็นวิธีที่ดีในการใช้หน่วยความจำที่ไม่ได้ใช้)

หมายเหตุเอกสารอย่างเป็นทางการสำหรับการmax-old-space-sizeกล่าวถึง:

ในเครื่องที่มีหน่วยความจำ 2GB ให้ลองตั้งค่านี้เป็น 1536 (1.5GB)

ดังนั้นค่าข้างต้น พิจารณาว่าจำนวนหน่วยความจำที่จำเป็นสำหรับระบบปฏิบัติการพื้นฐานนั้นไม่ได้เปลี่ยนแปลงมากนักดังนั้นคุณสามารถทำ 3.5 บนเครื่อง 4GB ได้อย่างมีความสุขเป็นต้น


1
จากลิงก์ที่คุณแชร์จากเอกสาร Node.js ระบุว่า: "ในเครื่องที่มีหน่วยความจำ 2GB ให้ลองตั้งค่านี้เป็น 1536 (1.5GB)"
Idan Dagan

1
ขอบคุณ @IdanDagan ฉันจะเพิ่มคำตอบนั้น
mikemaccana

11

ข้อผิดพลาดนี้เกิดขึ้นเมื่อหน่วยความจำที่จัดสรรสำหรับแอ็พพลิเคชันที่เรียกใช้งานน้อยกว่าหน่วยความจำที่ต้องการ ตามค่าเริ่มต้นขีด จำกัด หน่วยความจำใน Node.js คือ 512 MB —-max-old-space-sizeเพื่อเพิ่มจำนวนนี้คุณจะต้องตั้งข้อโต้แย้งขีด จำกัด ของหน่วยความจำ จะช่วยหลีกเลี่ยงปัญหาการ จำกัด หน่วยความจำ

node --max-old-space-size=1024 index.js #increase to 1gb
node --max-old-space-size=2048 index.js #increase to 2gb
node --max-old-space-size=3072 index.js #increase to 3gb
node --max-old-space-size=4096 index.js #increase to 4gb
node --max-old-space-size=5120 index.js #increase to 5gb
node --max-old-space-size=6144 index.js #increase to 6gb
node --max-old-space-size=7168 index.js #increase to 7gb
node --max-old-space-size=8192 index.js #increase to 8gb

https://medium.com/@vuongtran/how-to-solve-process-out-of-memory-in-node-js-5f0de8f8464c


และควรจะมากกว่าหน่วยความจำ Ram ที่จัดสรร
HD ..

ฉันไม่แน่ใจว่านี่เป็นความจริงอีกต่อไป แน่นอนในระบบเดียวที่ฉันสามารถเข้าถึงโหนดที่รัน 10.20.1 ฉันเห็น (ด้วยnode --v8-options) ว่าค่าเริ่มต้นที่รายงานคือ 4096 และโดยไม่ต้องตั้งค่าmax-old-space-sizeชุดทดสอบที่ฉันใช้งานอยู่จะได้รับการจัดสรรสูงสุด 1.5Gb โดยไม่มีปัญหา บทความขนาดกลางที่เชื่อมโยงมาจากปี 2559 ดังนั้นจึงมีแนวโน้มว่าสิ่งต่างๆจะดำเนินต่อไปนับตั้งแต่มีการเขียน
JaySeeAre

1
เป็นการยากที่จะพบการยืนยันในเรื่องนั้น ฉันไม่พบสิ่งที่ชัดเจนในเอกสารสำหรับ V8 หรือโหนด ระบบอื่นฉันรายงานค่าเริ่มต้นสำหรับ v10, 12 & 14 เป็น 0 FWIW ฉันพบบล็อกเกอร์ล่าสุดสองสามรายระบุหน่วยความจำสูงสุดเป็น 1.5Gb ( tejom.github.io/general/nodejs/v8/debugging/2017/ 01/16 / … ) และ v12 นั้นมีค่าสูงสุดแบบไดนามิกตามระบบ ( idginsiderpro.com/article/3257673/… )
JaySeeAre

3
node -e "console.log(`node heap limit = ${require('v8').getHeapStatistics().heap_size_limit / (1024 * 1024)} Mb`)"-> v12.18.0 และ v14.3.0 -> 2096Mb, v10.20.1 -> 1432Mb
JaySeeAre

@JaySeeAre ขอบคุณสำหรับคำสั่งนั้นเพื่อแสดงไฟล์heap_size_limit. สำหรับ UNIX เชลล์ปกติจะต้องมีการอ้างอิงแตกต่างกัน:node -e 'console.log(`node heap limit = ${require("v8").getHeapStatistics().heap_size_limit / (1024 * 1024)} Mb`)'
Sam Watkins

-6

หากคุณต้องการเพียงแค่ทำให้มันใช้งานได้จากโปรเจ็กต์ที่คุณกำลังดำเนินการอยู่ให้ทำตามสองขั้นตอน:

  1. ในโครงการของคุณ cd เป็น node_module / @ angular cd node_module / @ angular

  2. ตอนนี้รันคำสั่งด้านล่างส่งออก NODE_OPTIONS = - max-old-space-size = 8192


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