Loader global-css

Механизм загрузчиков в esbuild опирается на правило сопоставления расширений файлов с конкретными стратегиями обработки. Каждый тип ресурса — JavaScript, TypeScript, JSON, CSS, изображения — получает собственный pipeline трансформации, определяемый через параметр loader. Для CSS это особенно важно, поскольку поведение отличается от привычной модели JavaScript-модулей и напрямую влияет на глобальность стилей в приложении.

Для файлов .css используется встроенный загрузчик css, который изменяет стандартную семантику импорта:

import './styles.css'

Такой импорт не приводит к получению объекта в JavaScript-коде. Вместо этого esbuild рассматривает CSS как побочный эффект, который должен быть включён в итоговую сборку.

Базовая настройка:

import * as esbuild from 'esbuild'

esbuild.build({
  entryPoints: ['src/index.js'],
  bundle: true,
  outfile: 'dist/app.js',
  loader: {
    '.css': 'css'
  }
})

При такой конфигурации CSS становится частью графа зависимостей и перестаёт быть внешним ресурсом.

Глобальный CSS как модель поведения

Понятие глобального CSS в контексте esbuild означает отсутствие изоляции стилей между модулями. Любой импортированный файл .css влияет на общий DOM без ограничений области видимости.

Ключевая особенность заключается в том, что esbuild не реализует автоматическую инкапсуляцию классов. Все селекторы остаются в исходном виде:

.button {
  background: black;
  color: white;
}

После сборки этот стиль применяется ко всем элементам .button в документе без привязки к конкретному модулю.

Поведение импортов CSS в связке с JavaScript

При использовании CSS внутри JavaScript-модулей esbuild превращает импорт в побочный эффект. В браузерной сборке это реализуется через генерацию кода, который динамически добавляет <style> в документ:

// псевдогенерируемый результат
var css = "body { margin: 0; }";
var style = document.createElement("style");
style.textContent = css;
document.head.appendChild(style);

Такой подход делает CSS глобально применимым без необходимости отдельного подключения через <link>.

Отличие глобального CSS от CSS Modules

Esbuild по умолчанию не включает механизм CSS Modules. Это означает, что отсутствует переименование классов и локализация области видимости.

Глобальный CSS:

.title {
  font-size: 20px;
}

CSS Modules (не встроены в esbuild без плагинов):

.title {
  font-size: 20px;
}

В модульной системе класс .title трансформируется в уникальный идентификатор, например:

.title_ab12x {
  font-size: 20px;
}

и доступ осуществляется через импорт:

import styles from './styles.module.css'
console.log(styles.title)

В esbuild для этого используются сторонние плагины, поскольку базовый loader css ориентирован именно на глобальное поведение.

Конфигурация глобального CSS в типичных сборках

Наиболее распространённая конфигурация предполагает единый глобальный слой стилей:

esbuild.build({
  entryPoints: ['src/main.js'],
  bundle: true,
  outdir: 'dist',
  loader: {
    '.css': 'css'
  },
  splitting: true,
  format: 'esm'
})

При этом все CSS-файлы, импортируемые из разных частей приложения, объединяются в общий набор стилей.

Порядок подключения и каскадность

Глобальный CSS в esbuild подчиняется стандартным правилам каскада. Порядок импорта определяет итоговую приоритетность правил:

import './reset.css'
import './theme.css'
import './components/button.css'

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

Влияние tree shaking и side effects

CSS в esbuild считается ресурсом с побочными эффектами. Это означает, что даже если файл импортирован косвенно, он не удаляется из сборки:

import './global.css'

Удаление такого импорта невозможно без явного анализа side effects, поскольку визуальное состояние приложения зависит от его выполнения.

Интеграция глобальных стилей в архитектуру приложения

Глобальный CSS часто используется в базовых слоях приложения:

  • reset и normalize стили
  • типографика
  • дизайн-токены
  • переменные CSS
  • базовые компоненты без изоляции

Пример структуры:

src/
  styles/
    reset.css
    variables.css
    global.css
  components/
    header/
      header.js
      header.css

Импорт глобального слоя обычно выполняется в точке входа:

import './styles/reset.css'
import './styles/variables.css'
import './styles/global.css'
import './app.js'

Особенности работы с переменными и :root

Глобальный CSS часто опирается на использование CSS-переменных:

:root {
  --primary-color: #3366ff;
  --font-size-base: 16px;
}

Такой подход хорошо сочетается с esbuild, поскольку стили не изолируются и переменные доступны во всём DOM без дополнительных механизмов проброса.

Ограничения модели loader: css

Несмотря на простоту, загрузчик css в esbuild имеет ряд ограничений:

  • отсутствие встроенной поддержки CSS-in-JS трансформаций
  • отсутствие нативной поддержки CSS Modules
  • отсутствие постобработки (autoprefixer не включён по умолчанию)
  • минимальная семантика анализа классов и селекторов

Для расширения функциональности подключаются плагины:

  • обработка PostCSS
  • поддержка SCSS/Sass
  • модульная система классов
  • инлайнинг ресурсов

Глобальные стили и production-сборка

В production-режиме esbuild оптимизирует CSS следующим образом:

  • удаление дубликатов правил при объединении
  • минимизация пробелов и комментариев
  • объединение файлов в единый CSS-бандл при необходимости

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

Поведение при code splitting

При использовании code splitting CSS может быть разбит по чанкам, соответствующим точкам входа:

esbuild.build({
  entryPoints: ['src/pageA.js', 'src/pageB.js'],
  bundle: true,
  splitting: true,
  format: 'esm',
  outdir: 'dist',
  loader: {
    '.css': 'css'
  }
})

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

Использование глобального CSS как базового слоя поверх модульной архитектуры

В приложениях с компонентной структурой глобальный CSS обычно выполняет роль нижнего слоя:

  • базовые правила HTML
  • общая сетка
  • переменные темы
  • стили сторонних библиотек

Поверх него могут накладываться локальные стили компонентов, даже если они не изолированы системой модулей. В такой модели важно учитывать приоритет и порядок подключения, поскольку конфликт селекторов разрешается исключительно каскадом, а не системой именования.