Node.js 26.7.0: трассировка через Perfetto
Релиз Node.js 26.7.0 вышел 5 августа 2026 года, и в списке Notable Changes затерялась строка из трёх слов: add perfetto support (#64565). Выглядит как сноска. На деле это перестройка одной из самых старых и наименее любимых подсистем платформы — слоя трассировки.
Проблема: формат трейсов из другой эпохи
Годами встроенная трассировка в Node.js работала так:
node --trace-event-categories v8,node,node.async_hooks server.jsНа выходе — файл node_trace.1.log. Несмотря на расширение, внутри лежит JSON в устаревшем Trace Event Format, пришедшем из Chrome. Формат полностью текстовый, поэтому файлы разбухают под любой реальной нагрузкой, а традиционный просмотрщик chrome://tracing давно превратился в заброшенный инструмент.
Но главное уже не в удобстве. В обсуждении nodejs/diagnostics#654 было зафиксировано: V8 — источник значительной части трейс-данных, которые отдаёт Node (GC, компиляция, исполнение), — переходит исключительно на Perfetto и отказывается от старого механизма трассировки. Поскольку V8 находится в самом ядре Node.js, вариантов было два: двигаться следом или постепенно потерять самый содержательный источник данных в рантайме.
Что изменилось
В 26.7.0 появился новый бэкенд трассировки на базе Perfetto SDK, включаемый на этапе сборки:
./configure --with-perfetto
make -j"$(nproc)"Дальше всё остаётся прежним — те же флаги, те же категории:
node --trace-event-categories node.perf,node.async_hooks,v8 \
--trace-event-file-pattern '${pid}-${rotation}.pftrace' \
server.jsРазница — в результате. Вместо JSON Node пишет protobuf-файл node_trace.1.pftrace, который открывается напрямую в ui.perfetto.dev. И это не просто таймлайн: Perfetto даёт SQL-слой поверх трейса, так что данные можно спрашивать, а не пролистывать.
Программный API тоже не тронут:
import { createTracing } from 'node:trace_events';
const tracing = createTracing({
categories: ['node.perf', 'v8'],
});
tracing.enable();
// измеряемая работа
await handleRequest(req);
tracing.disable();Это осознанное решение: замена происходит внизу, а привычная поверхность остаётся на месте. Категории тоже прежние — node.perf для измерений Performance API, node.async_hooks для асинхронных операций, node.fs.sync и node.fs.async для файловых вызовов, v8 для данных движка. Изменилось то, куда эти события попадают и в каком виде записываются, а не то, как они собираются.
Оговорки, о которых стоит сказать прямо
- В официальных сборках не включено.
--with-perfetto— опция этапаconfigure, то есть текущие официальные бинарники её не содержат. На практике это означает собственную сборку либо ожидание решения включить её по умолчанию. - JSON-вывода в этом режиме нет. Исключение сделано намеренно. Любая внутренняя тулза, которая читает
node_trace.*.logи парсит его как JSON, потребует другого пути. - Трассировка через inspector отключается. При активном Perfetto домен NodeTracing поверх inspector выключен: протоколу здесь нужны сырые байты, а не объекты протокола.
- Бэкпорта не будет. Изменение ограничено веткой 26.x и не попадёт в 22.x или 24.x, а 26.x — это Current, не LTS.
Вывод
Наблюдаемость продолжает переезжать из категории «прикрутили сбоку» в категорию того, чем владеет сам рантайм. Запрашиваемый protobuf-трейс — не просто формат опрятнее JSON: это данные, которые понимают инструменты, и которые понимают агенты, всё чаще участвующие в разборе проблем производительности. Разница между пролистыванием JSON-файла на несколько сотен мегабайт и SQL-запросом к тем же данным — это разница между медленным ручным чтением и структурированным расследованием.
Пока шаг остаётся опцией сборки, но направление читается однозначно: путь трассировки в Node.js пересобирают так, чтобы он говорил на одном языке с остальной инструментальной экосистемой. Кто следил за тем, что приехало в Node.js 26.6, заметит: линейка 26.x несёт структурные изменения, а не косметику.
Первоисточник: release notes Node.js 26.7.0, детали реализации — в PR #64565.