Магические комментарии в Webpack представляют собой специальные
директивы, встроенные в динамические import(), которые
позволяют управлять поведением сборщика при разбиении кода на чанки, их
именовании и стратегиях загрузки. Они не являются частью стандарта
JavaScript и обрабатываются исключительно Webpack во время сборки.
Основное назначение таких комментариев — тонкая настройка механизма code splitting без изменения логики приложения.
При динамическом импорте Webpack по умолчанию генерирует числовые или хешированные имена файлов:
import('./modules/UserProfile');
Результат сборки может выглядеть как:
0.js
1.js
Это затрудняет отладку и анализ бандла. Для решения используется
магический комментарий webpackChunkName.
import(/* webpackChunkName: "user-profile" */ './modules/UserProfile');
При сборке Webpack создаёт файл с читаемым именем:
user-profile.js
Webpack поддерживает шаблонные выражения:
import(/* webpackChunkName: "user-[request]" */ './modules/UserProfile');
Здесь [request] заменяется на часть пути модуля.
Также используются дополнительные шаблоны:
[id] — идентификатор модуля[name] — имя модуля (если доступно)[chunkhash] — хеш чанкаПример:
import(/* webpackChunkName: "chunk-[id]" */ './modules/UserProfile');
webpackPrefetch используется для указания браузеру, что
определённый чанк может понадобиться в будущем, и его можно загрузить в
простое время.
import(
/* webpackPrefetch: true */
'./modules/Comments'
);
Webpack добавляет в HTML метаинструкцию:
<link rel="prefetch" href="comments.js">
Это означает:
Prefetch:
В отличие от prefetch, webpackPreload
указывает на необходимость загрузить ресурс с высоким приоритетом
параллельно с текущей страницей.
import(
/* webpackPreload: true */
'./modules/DashboardWidgets'
);
Webpack генерирует:
<link rel="preload" href="dashboard-widgets.js">
Preload:
| Характеристика | preload | prefetch |
|---|---|---|
| Приоритет загрузки | высокий | низкий |
| Время загрузки | сразу | в простое время |
| Назначение | текущий экран | будущие переходы |
| Риск перегрузки | выше | ниже |
Webpack позволяет использовать несколько директив одновременно:
import(
/* webpackChunkName: "dashboard" */
/* webpackPrefetch: true */
'./modules/Dashboard'
);
Или:
import(
/* webpackChunkName: "analytics" */
/* webpackPreload: true */
'./modules/Analytics'
);
webpackChunkName влияет только на имя файлаprefetch и preload влияют на стратегию
загрузкиprefetch и
preload для одного чанка не имеет практического смысла, так
как они конфликтуют по приоритетуМагические комментарии работают в связке с системой разбиения кода Webpack.
При наличии splitChunks:
output.chunkFilenamewebpackChunkName становится подсказкой, но не
абсолютным правиломoutput: {
chunkFilename: '[name].[contenthash].js'
}
При этом:
import(/* webpackChunkName: "user" */ './user');
может дать:
user.8f3a9c1d.js
Webpack анализирует строку комментария статически во время компиляции. Это означает:
Неправильно:
const name = 'user';
import(/* webpackChunkName: name */ './module');
Правильно:
import(/* webpackChunkName: "user" */ './module');
Использование магических комментариев влияет на стратегию кэширования браузера и CDN.
В production режиме Webpack:
При этом:
webpackChunkName сохраняет влияние только на имя
чанкаprefetch и preload трансформируются в HTML
link hintsПодключение большого числа preload-чанков приводит к конкуренции за сетевые ресурсы и замедляет критический путь загрузки.
Имя чанка не гарантирует отдельный файл — Webpack может объединить его с другими модулями.
Prefetch не подходит для логики, необходимой при первом рендере интерфейса.
Магические комментарии часто используются вместе с ленивой загрузкой компонентов:
const UserProfile = () =>
import(/* webpackChunkName: "user-profile" */ './UserProfile');
Дополнительная оптимизация:
const Comments = () =>
import(
/* webpackChunkName: "comments" */
/* webpackPrefetch: true */
'./Comments'
);
Такой подход позволяет одновременно:
Поддержка магических комментариев стабилизировалась начиная с Webpack 4, однако нюансы различаются: