Skip to content

Splitting Output by Type

Smaller files, better caching, and the ability to import only what you need. Split colors, spacing, and typography into separate outputs so each team or component can consume only the tokens it uses.

Filter tokens by type and write each type to its own file. Each byType() filter targets a single token type:

import { byType } from 'dispersa/filters'
import { nameKebabCase, colorToHex, dimensionToPx } from 'dispersa/transforms'
await dispersa.build({
outputs: [
css({
name: 'colors',
file: 'colors.css',
preset: 'bundle',
filters: [byType('color')],
transforms: [nameKebabCase(), colorToHex()],
}),
css({
name: 'spacing',
file: 'spacing.css',
preset: 'bundle',
filters: [byType('dimension')],
transforms: [nameKebabCase(), dimensionToPx()],
}),
],
})

To include multiple token types in a single output (e.g. all typography-related tokens), you need OR logic. Since multiple filters are AND-combined (a token must pass every filter), you cannot use [byType('fontFamily'), byType('fontWeight')] — no token can be both types simultaneously.

Instead, create a custom filter with OR logic:

import type { Filter } from 'dispersa/filters'
const typographyFilter: Filter = {
filter: (token) => ['fontFamily', 'fontWeight', 'typography'].includes(token.$type),
}

Then use it:

css({
name: 'typography',
file: 'typography.css',
preset: 'bundle',
filters: [typographyFilter],
transforms: [nameKebabCase()],
})

Using byPath() for Namespace-Based Splitting

Section titled “Using byPath() for Namespace-Based Splitting”

Split by token path prefix when your tokens are organized by namespace:

import { byPath } from 'dispersa/filters'
css({
name: 'brand',
file: 'brand.css',
filters: [byPath('color.brand')],
preset: 'bundle',
transforms: [nameKebabCase(), colorToHex()],
})

byPath accepts a string prefix or a RegExp. Use byPath(/^spacing\./) for regex matching.

Combine type and path for fine-grained control. For example, brand colors only:

filters: [byType('color'), byPath('color.brand')],