Как запросить сборщик мусора в node.js для запуска?

При запуске кажется, что мое приложение node.js использует около 200 МБ памяти. Если я оставлю это в покое на некоторое время, оно уменьшится до 9 МБ.

Возможно ли из приложения:

  1. Проверьте, сколько памяти использует приложение?
  2. Запросить сборщик мусора для запуска?

Причина, по которой я спрашиваю, состоит в том, что я загружаю несколько файлов с диска, которые временно обрабатываются. Это, вероятно, вызывает скачок использования памяти. Но я не хочу загружать больше файлов, пока GC не запустится, иначе есть риск, что мне не хватит памяти.

Какие-либо предложения?

4 ответа

Решение

Если вы запустите процесс узла с --expose-gc флаг, вы можете позвонить global.gc() заставить узел запустить сборку мусора. Помните, что все остальные операции в вашем приложении узла будут приостановлены до завершения GC, поэтому не используйте его слишком часто, иначе это повлияет на производительность.

Возможно, вы захотите включить проверку при выполнении вызовов GC из вашего кода, чтобы все не пошло плохо, если узел был запущен без флага:

if (global.gc) {
    global.gc();
} else {
    console.log('Garbage collection unavailable.  Pass --expose-gc '
      + 'when launching node to enable forced garbage collection.');
}

Узел позволяет вручную запускать сборку мусора. Это можно сделать, запустив Node с --expose-gc флаг (то есть node --expose-gc index.js).
Когда узел работает в этом режиме, вы можете программно запустить сборку мусора в любое время, вызвав global.gc() из вашей программы.

ex - // Принудительная сборка мусора при каждом вызове этой функции

try {
  global.gc();
} catch (e) {
  console.log("You must run program with 'node --expose-gc index.js' or 'npm start'");
  process.exit();
}

Когда вы не можете пройти мимо--expose-gcотметьте свой процесс node при запуске по любой причине, вы можете попробовать это:

      import { setFlagsFromString } from 'v8';
import { runInNewContext } from 'vm';

setFlagsFromString('--expose_gc');
const gc = runInNewContext('gc'); // nocommit
gc();

Примечания:

  • Это сработало для меня в узле 16.x
  • Вы можете проверить process.memoryUsage() до и после запуска gc
  • Используйте с осторожностью: Цитата из документации узла v8.setFlagsFromString:

Этот метод следует использовать с осторожностью. Изменение настроек после запуска ВМ может привести к непредсказуемому поведению, включая сбои и потерю данных; или он может просто ничего не делать.

Я хотел бы предложить одну вещь: если вам не нужны эти файлы при запуске, попробуйте загружать их только тогда, когда они вам нужны.

РЕДАКТИРОВАТЬ: обратитесь к посту выше.

Другие вопросы по тегам