Three types, one pipeline
Underlith organizes tokens into three distinct types. Each type has a single responsibility —
and together they form the pipeline from raw values to your publishable brand package.
When you run underlith brand init, Underlith separates brand tokens from base tokens and scaffolds them into a publishable @your-org/tokens package. Semantic aliases travel with the brand layer.
Base tokens
Framework primitives. Raw values that define the scale of your system. These live in the Underlith package and are shared across all consumers.
Spacing spacing.css
The spacing scale used across the system. Replaces arbitrary values like 8px or 12px with a consistent, named scale.
--ul-space-1
--ul-space-2
--ul-space-3
--ul-space-4
--ul-space-5Typography typography.css
Typographic scales as tokens. Describes intent — not headings or text styles.
--ul-font-size-sm
--ul-font-size-md
--ul-font-size-lg
--ul-line-height-tight
--ul-font-weight-regularRadius & Borders radius-and-borders.css
Shape-related decisions. Ensures consistent geometry across all consumers.
--ul-radius-sm
--ul-radius-md
--ul-radius-lg
--ul-border-width-hairlineElevation elevation.css
Depth tokens. Relative depth, not specific components.
--ul-elevation-1
--ul-elevation-2
--ul-elevation-3Opacity opacity.css
Named transparency levels. Avoids arbitrary alpha values.
--ul-opacity-disabled
--ul-opacity-muted
--ul-opacity-overlayBreakpoints breakpoints.css
Responsive thresholds as tokens. Defines when layout decisions change.
--ul-breakpoint-sm
--ul-breakpoint-md
--ul-breakpoint-lgMotion motion.css
Durations, easings, delays, and composite motion tokens. Use individual tokens for fine control, or composite tokens for common effects.
Durations
--ul-duration-nano
--ul-duration-micro
--ul-duration-fast
--ul-duration-base
--ul-duration-moderate
--ul-duration-slow
--ul-duration-glacial
--ul-duration-epicEasing
--ul-ease-linear
--ul-ease-enter
--ul-ease-enter-back
--ul-ease-enter-spring
--ul-ease-exit
--ul-ease-exit-sharp
--ul-ease-inout
--ul-ease-inout-soft
--ul-ease-inout-strong
--ul-ease-bounce
--ul-ease-bounce-strong
--ul-ease-elastic
--ul-ease-anticipateComposite motion tokens
--ul-motion-drop-bounce
--ul-motion-fade-up
--ul-motion-fade-in
--ul-motion-scale-pop
--ul-motion-glow-breath
--ul-motion-pulse
--ul-motion-float
--ul-motion-shimmer
--ul-motion-skeletonBrand tokens
Your org's identity decisions. Colors, brand palette, identity values.
These are the tokens that underlith brand init extracts and packages
into your publishable @your-org/tokens.
Colors colors.css
Raw color values. Value-based, without semantic context. Your brand palette lives here.
--ul-color-brand-300
--ul-color-brand-500
--ul-color-neutral-0
--ul-color-neutral-900Semantic aliases
The most important layer. Maps raw tokens to intent — what something means, not what it looks like. Semantic aliases are what components consume. When your brand evolves, you update the alias. Components never change.
Semantic aliases semantic-aliases.css
/* Text */
--ul-color-text
--ul-color-text-secondary
--ul-color-text-inverse
/* Surfaces */
--ul-color-bg-surface
--ul-color-bg-elevated
/* Borders */
--ul-color-border-subtle
--ul-color-border-strong
/* Interactive */
--ul-color-brand-primary
--ul-color-brand-primary-hover
Semantic aliases travel with your brand package. When you publish @your-org/tokens,
any project that installs it gets the complete alias map — and can safely use
var(--ul-color-text) without ever knowing what the underlying value is.