JSX-компиляция в esbuild опирается на заранее заданные параметры
трансформации, а не на богатую систему директив внутри исходного кода,
как это реализовано в Babel или частично в TypeScript. В контексте
экосистемы JavaScript под «директивой @jsxRuntime в комментариях» обычно
понимается механизм управления режимом JSX-трансформации через
специальные комментарии вида /** @jsxRuntime automatic */
или /** @jsxRuntime classic */, которые позволяют
переключать поведение JSX-компилятора на уровне файла.
JSX может компилироваться двумя основными способами:
Classic runtime предполагает явный вызов функции создания элементов:
JSX:
<App />Преобразуется в:
React.createElement(App, null)Automatic runtime (новый формат JSX transform):
JSX:
<App />Преобразуется в:
import { jsx as _jsx } from "react/jsx-runtime";
_jsx(App, {});Ключевое различие заключается в том, что automatic runtime не требует
явного импорта React в каждом файле и использует функции из
react/jsx-runtime или альтернативного источника, заданного
через конфигурацию.
Комментарий вида:
/** @jsxRuntime automatic */
или
/** @jsxRuntime classic */
служит инструкцией для трансформера JSX, определяя, какой runtime использовать при компиляции конкретного файла.
Основная идея:
В классическом Babel-пайплайне эта директива может учитываться через соответствующие плагины, а в TypeScript — через совместимую JSX-трансформацию.
В esbuild важно учитывать принципиальную особенность: инструмент не реализует полноценный парсинг JSX-директив из комментариев на уровне Babel-плагинов. Вместо этого он использует строго конфигурационный подход.
JSX-трансформация в esbuild задаётся через параметры:
jsxjsxFactoryjsxFragmentjsxImportSourceПример конфигурации:
esbuild.build({
jsx: "automatic",
})
или:
esbuild.build({
jsx: "transform",
jsxFactory: "h",
jsxFragment: "Fragment",
})
Таким образом, поведение JSX определяется глобально для всего процесса сборки или конкретного файла через loader/опции, но не через inline-комментарии.
С точки зрения архитектуры esbuild:
Нет AST-уровня Babel-плагинов Esbuild реализует собственный быстрый парсер и трансформер, оптимизированный под скорость, а не под расширяемые AST-правила.
Отсутствие директивного анализа комментариев JSX Комментарии не участвуют в выборе runtime.
Конфигурация вместо контекстных инструкций Любая настройка должна быть задана до начала компиляции.
Это приводит к тому, что:
/** @jsxRuntime automatic */ игнорируетсяjsx
опциюПри миграции проектов, где ранее использовались JSX-директивы в комментариях, возникает типичная ситуация:
Babel-проект:
/** @jsxRuntime automatic */
/** @jsxImportSource preact */Esbuild-проект требует замены на конфигурацию:
esbuild.build({
jsx: "automatic",
jsxImportSource: "preact",
})
Это означает, что управление переносится:
В современном JSX pipeline ключевую роль играет
jsxImportSource. Он определяет, из какого пакета
импортируются функции JSX runtime.
Пример:
esbuild.build({
jsx: "automatic",
jsxImportSource: "preact",
})
Тогда JSX:
<div />
будет компилироваться в:
import { jsx as _jsx } from "preact/jsx-runtime";
_jsx("div", {});
Это полностью заменяет необходимость в комментариях, которые ранее могли переключать runtime.
Использование директив в комментариях, подобных
@jsxRuntime, имеет ряд особенностей:
В esbuild подход противоположный:
При использовании React 17+ или альтернативных JSX runtime (Preact, Solid, Inferno) ключевым становится не директива в комментариях, а конфигурация:
React:
jsx: "automatic"jsxImportSource: "react"Preact:
jsxImportSource: "preact"Solid:
Esbuild выступает как низкоуровневый инструмент, который лишь применяет выбранную стратегию трансформации.
При переносе кода часто предполагается, что:
Фактически:
Это приводит к расхождениям между ожидаемым и реальным результатом сборки, особенно в монорепозиториях с разными UI-фреймворками.
Директива @jsxRuntime в комментариях относится к более
гибким трансформерам JSX, где код может нести метаинформацию о
компиляции. В контексте esbuild эта модель не применяется: JSX runtime
определяется исключительно конфигурацией сборщика, а не содержимым
исходных файлов.