Подготовка
Для запуска ts tsx файлов в Node.js устанавливаем пакет ts-node:npm i ts-node
Чтобы при запуске игнорировать импорт стилей в файле компонента (который может выглядеть примерно так: import './MyComponent.scss';), устанавливаем пакет ignore-styles:
npm i ignore-styles
Создание файла с бенчмарком
Создаём tsx файл, в котором импортируем наш компонент MyComponent, задаём props и вызываем renderToString():import * as React from 'react';
import { renderToString } from 'react-dom/server';
import { MyComponent } from './MyComponent';
const props = {/* ... */};
console.log(renderToString(<MyComponent {...props} />));
Запускаем его, чтобы убедиться, что всё работает без ошибок, компонент рендерится и в консоль выводится правильная разметка компонента:
NODE_ENV=production node -r ts-node/register -r ignore-styles MyComponent.perf-test.tsx
Если не хватит памяти, надо добавить параметр --max_old_space_size=4096
NODE_ENV=production node --max_old_space_size=4096 -r ts-node/register -r ignore-styles MyComponent.perf-test.tsx
Если памяти всё равно не хватит - надо поставить вместо 4096 число побольше. Запоминаем подобранные параметры.
Убедившись, что всё работает, в файле бенчмарка убираем вывод в консоль и дописываем вызов renderToString() в цикле:
import * as React from 'react';
import { renderToString } from 'react-dom/server';
import { MyComponent } from './MyComponent';
const props = {/* ... */};
for (let i = 0; i < 1000; i++) {
renderToString(<MyComponent {...props} />);
}
Запуск бенчмарка
Запускаем бенчмарк (в подобранную ранее командную строку добавляется параметр --prof):NODE_ENV=production node --prof -r ts-node/register -r ignore-styles MyComponent.perf-test.tsx
или
NODE_ENV=production node --prof --max_old_space_size=4096 -r ts-node/register -r ignore-styles MyComponent.perf-test.tsx
Первый запуск после изменения файла будет долгим и даст совсем неправильные результаты, т.к. под капотом компилируется TypeScript, и процесс компиляции тоже попадёт в собранный профиль, что нам не нужно. Поэтому после каждого редактирования запускаем бенчмарк по два раза, второй раз он выполнится быстрее.
После каждого запуска должны создаваться файлы isolate*.log.
Теперь вместо числа 1000 надо подобрать такое, чтобы второй запуск бенчмарка занимал достаточно продолжительное время (десятки секунд): меняем число, запускаем два раза, оцениваем продолжительность второго запуска.
После этого удаляем все накопившиеся файлы isolate*.log, запускаем бенчмарк ещё раз - мы должны получить ровно один файл isolate*.log.
Обработка и анализ собранного профиля
Полученный файл isolate*.log надо обработать, чтобы получить на выходе читабельный профиль выполнения:node --prof-process isolate-0x104000800-v8.log >isolate-0x104000800-v8.txt
Вместо isolate-0x104000800-v8 надо подставить своё имя файла. Также для обработки лога можно использовать отдельный пакет https://www.npmjs.com/package/tick-processor, часто он лучше обрабатывает лог и не теряет данные, в обличие от встроенного в саму ноду процессора логов:
tick-processor isolate-0x104000800-v8.log >isolate-0x104000800-v8.txt
В текстовом файле мы видим, какие именно методы v8 и нативного C++ кода вызывались и сколько времени заняли. Подробное описание содержимого и методов его анализа - тема, достойная отдельной большой статьи.