Eager-загрузка при glob-импорте

Механизм import.meta.glob в Vite предоставляет способ пакетного импорта файлов по шаблону пути с последующей обработкой на этапе сборки. Поведение по умолчанию ориентировано на ленивую загрузку: каждый найденный модуль представляется функцией, возвращающей динамический import(). Однако в ряде сценариев требуется противоположная модель — немедленная (eager) загрузка всех модулей в момент сборки.

Eager-загрузка включается через опцию eager: true, которая изменяет семантику результата glob-импорта и переводит его из ленивого режима в статически проинлайненный набор импортов.


Базовая форма glob-импорта

Конструкция import.meta.glob принимает строку-шаблон и возвращает объект соответствий:

const modules = import.meta.glob('./modules/*.js');

В стандартном режиме значение modules имеет следующий вид:

{
  './modules/a.js': () => import('./modules/a.js'),
  './modules/b.js': () => import('./modules/b.js')
}

Каждое значение — функция, инициирующая динамический импорт при вызове.


Принцип eager-загрузки

При включении eager: true Vite заменяет динамические функции на уже загруженные модули:

const modules = import.meta.glob('./modules/*.js', { eager: true });

Результирующая структура:

{
  './modules/a.js': ModuleA,
  './modules/b.js': ModuleB
}

Каждый модуль импортируется на этапе сборки и сразу включается в бандл, без отложенного выполнения.


Отличие lazy и eager моделей

Поведение glob-импорта принципиально зависит от режима:

Ленивый режим

  • Возвращаются функции () => import(...)
  • Импорт выполняется по требованию
  • Меньший initial bundle
  • Подходит для роутинга и редких компонентов

Eager-режим

  • Возвращаются уже импортированные модули
  • Все зависимости включаются в initial bundle
  • Отсутствует runtime-стоимость загрузки
  • Подходит для статических наборов данных и конфигураций

Структура данных при eager-загрузке

Eager-режим фактически трансформирует glob-выражение в набор статических импортов:

import * as A from './modules/a.js';
import * as B from './modules/b.js';

const modules = {
  './modules/a.js': A,
  './modules/b.js': B
};

Таким образом устраняется необходимость асинхронного разрешения модулей в рантайме.


Использование import: 'default' вместе с eager

Vite позволяет комбинировать eager-загрузку с извлечением конкретного экспорта:

const modules = import.meta.glob('./modules/*.js', {
  eager: true,
  import: 'default'
});

Результат:

{
  './modules/a.js': ADefaultExport,
  './modules/b.js': BDefaultExport
}

Каждый модуль возвращает только указанный экспорт, что уменьшает объем обрабатываемых данных.


Фильтрация и eager-загрузка

Glob-паттерны могут ограничивать набор импортируемых файлов, а eager-режим распространяется только на выбранные результаты:

const pages = import.meta.glob('./pages/**/*.js', {
  eager: true
});

В результате в память загружаются все модули, соответствующие глубокой структуре каталогов.


Комбинация с JSON и другими ресурсами

Eager-загрузка применяется не только к JavaScript-модулям, но и к поддерживаемым Vite типам ресурсов:

const data = import.meta.glob('./data/*.json', {
  eager: true,
  import: 'default'
});

Каждый JSON-файл преобразуется в объект на этапе сборки, исключая необходимость асинхронного парсинга через динамический импорт.


Влияние на сборку и производительность

Eager-режим напрямую влияет на стратегию бандлинга:

  • увеличивается размер начального бандла
  • уменьшается количество асинхронных чанков
  • устраняется задержка загрузки модулей
  • оптимизируется доступ к статическим коллекциям

Vite при этом выполняет предобработку glob-выражения во время билда, инлайнит импорты и формирует статическую графовую структуру зависимостей.


Применение в архитектуре приложений

Eager-загрузка используется в случаях, где структура модулей заранее известна и не требует ленивой подгрузки:

  • реестры компонентов
  • словари маршрутов без code splitting
  • наборы локализаций
  • статические конфигурации приложения
  • утилитарные библиотеки, используемые повсеместно

Особенности разрешения модулей

При использовании eager-режима Vite сохраняет ключи объекта как строковые пути:

{
  './modules/a.js': ...
}

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


Поведение в режиме SSR

В SSR-среде eager-загрузка приводит к немедленному выполнению всех импортов на сервере. Это может быть критично при большом количестве модулей, так как увеличивает время инициализации запроса.

При этом структура данных остаётся синхронной, что упрощает доступ к зависимостям без ожидания асинхронных операций.


Сравнение с ручными импортами

Эквивалент eager-glob можно выразить вручную:

import A from './modules/a.js';
import B from './modules/b.js';

const modules = { A, B };

Однако glob-импорт устраняет необходимость поддерживать список импортов вручную и автоматически масштабируется при добавлении файлов.


Ограничения eager-загрузки

  • отсутствие ленивого разделения кода
  • увеличение начального размера бандла
  • невозможность частичной загрузки по требованию
  • потенциальное дублирование зависимостей при неосторожной архитектуре

Эти свойства делают eager-режим специализированным инструментом, а не универсальной стратегией загрузки.