Встроенная поддержка CSS

Общая модель обработки CSS

Vite рассматривает CSS как полноценный модуль первого класса. Любой импорт стилей внутри JavaScript или TypeScript файлов включается в граф зависимостей и обрабатывается через единый пайплайн трансформации.

import './styles/main.css'

При таком импорте файл не просто добавляется в сборку, а проходит несколько этапов обработки:

  • анализ зависимостей внутри CSS (@import, url())
  • трансформация через PostCSS (если настроен)
  • разрешение путей и ассетов
  • инъекция в DOM в dev-режиме
  • выделение в отдельный файл в production-сборке

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


Импорт CSS как модулей

CSS можно импортировать напрямую в JavaScript-модулях. Это создаёт явную связь между компонентом и стилями.

import './button.css'

Поддерживаются также динамические зависимости:

if (theme === 'dark') {
  import('./themes/dark.css')
}

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


Обработка @import и url()

Vite автоматически разбирает CSS и обрабатывает встроенные директивы.

@import

@import './reset.css';

Такие импорты:

  • инлайнются в основной CSS в dev-режиме
  • оптимизируются в production (снижается количество запросов)
  • участвуют в графе зависимостей

url()

.background {
  background-image: url('./image.png');
}

Пути внутри url():

  • резолвятся относительно файла
  • могут быть заменены на хешированные ассеты
  • при необходимости инлайнются в base64 (если включено ограничение размера)

CSS и обработка ассетов

Vite автоматически управляет ресурсами, на которые ссылается CSS.

.icon {
  background: url('/icons/arrow.svg');
}

Поведение зависит от режима:

  • development: путь остаётся логическим, обслуживается dev server
  • production: файл копируется в dist/assets и получает хеш

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

  • ?url — вернуть путь к файлу
  • ?raw — импортировать содержимое как строку
  • ?inline — инлайн содержимого
import logoUrl from './logo.svg?url'
import logoRaw from './logo.svg?raw'

CSS Modules

Vite имеет встроенную поддержку CSS Modules без дополнительной конфигурации.

/* button.module.css */
.button {
  color: white;
  background: black;
}
import styles from './button.module.css'

console.log(styles.button)

Особенности реализации:

  • локальная область видимости классов
  • автоматическая генерация уникальных имён
  • поддержка композиции (composes)
  • типизация через d.ts при использовании TypeScript

Пример с несколькими классами:

.container {
  padding: 10px;
}

.primary {
  color: blue;
}
<div className={`${styles.container} ${styles.primary}`} />

Глобальные стили и изоляция

Обычные CSS-файлы считаются глобальными по умолчанию.

body {
  margin: 0;
}

Такой стиль применяется ко всему приложению.

CSS Modules являются единственным встроенным механизмом изоляции, без необходимости ручного namespace-подхода.


Поддержка препроцессоров

Vite поддерживает основные CSS-препроцессоры без дополнительной настройки:

  • Sass / SCSS
  • Less
  • Stylus

Пример SCSS:

$primary: #42b883;

.button {
  background: $primary;

  &:hover {
    opacity: 0.8;
  }
}

Установка зависимости достаточна для активации поддержки:

npm install sass

Дополнительная конфигурация:

// vite.config.js
export default {
  css: {
    preprocessorOptions: {
      scss: {
        additionalData: `@import "./src/styles/variables.scss";`
      }
    }
  }
}

Это позволяет автоматически подключать переменные и миксины ко всем файлам.


PostCSS интеграция

Vite автоматически использует PostCSS, если найден конфигурационный файл.

Поддерживаются:

  • postcss.config.js
  • postcss.config.cjs
  • postcss.config.mjs

Пример конфигурации:

export default {
  plugins: [
    require('autoprefixer'),
    require('postcss-nested')
  ]
}

PostCSS применяется ко всем CSS-файлам после базового разбора Vite.


Горячая замена CSS (HMR)

Vite реализует мгновенное обновление CSS без перезагрузки страницы.

При изменении файла:

  • старый <style> удаляется из DOM
  • новый вставляется мгновенно
  • состояние приложения не теряется

Особенности:

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

Даже изменения в импортированных SCSS или CSS Modules корректно триггерят обновления.


Разделение CSS в production

В production-сборке Vite извлекает CSS в отдельные файлы.

dist/assets/index.abc123.css
dist/assets/index.abc123.js

Это обеспечивает:

  • параллельную загрузку JS и CSS
  • кэширование по хешу
  • уменьшение времени первого рендера

Если используется code splitting:

import('./admin.css')

Vite создаёт отдельный CSS-чанк, связанный с соответствующим JS-модулем.


Оптимизация CSS

На этапе сборки выполняются оптимизации:

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

В новых версиях Vite может использоваться Lightning CSS для ускоренной обработки и более агрессивной оптимизации.


Поддержка scoped и компонентного подхода

Хотя Vite не навязывает framework-специфичную модель, он корректно работает с scoped-стилями через плагины (Vue, Svelte).

Пример для Vue:

<style scoped>
.button {
  color: red;
}
</style>

Vite обрабатывает такие стили через соответствующий плагин фреймворка, сохраняя совместимость с HMR и модульной системой.


Интеграция с node_modules CSS

CSS из зависимостей обрабатывается так же, как локальный код:

import 'normalize.css'

Особенности:

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

Управление поведением через конфигурацию

Основные параметры CSS в Vite:

export default {
  css: {
    modules: {
      localsConvention: 'camelCaseOnly',
      scopeBehaviour: 'local'
    },
    devSourcemap: true,
    preprocessorOptions: {
      less: {},
      scss: {}
    }
  }
}

Ключевые возможности:

  • настройка CSS Modules
  • управление sourcemap в dev-режиме
  • конфигурация препроцессоров
  • контроль поведения импортов

CSS как часть модульной системы Vite

CSS в Vite не является вторичным форматом. Он участвует в тех же механизмах, что и Jav * aScript:

  • входит в dependency graph
  • поддерживает HMR
  • участвует в code splitting
  • обрабатывается плагинной системой
  • оптимизируется на этапе build

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