Allow resolve config to take in optional paths alongside configs
This commit is contained in:
parent
f876304557
commit
20f001cb3c
3 changed files with 90 additions and 67 deletions
|
|
@ -8,27 +8,33 @@ test('top level theme keys are replaced', ({ expect }) => {
|
|||
|
||||
let config = resolveConfig(design, [
|
||||
{
|
||||
theme: {
|
||||
colors: {
|
||||
red: 'red',
|
||||
},
|
||||
config: {
|
||||
theme: {
|
||||
colors: {
|
||||
red: 'red',
|
||||
},
|
||||
|
||||
fontFamily: {
|
||||
sans: 'SF Pro Display',
|
||||
fontFamily: {
|
||||
sans: 'SF Pro Display',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
theme: {
|
||||
colors: {
|
||||
green: 'green',
|
||||
config: {
|
||||
theme: {
|
||||
colors: {
|
||||
green: 'green',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
theme: {
|
||||
colors: {
|
||||
blue: 'blue',
|
||||
config: {
|
||||
theme: {
|
||||
colors: {
|
||||
blue: 'blue',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
|
@ -51,21 +57,25 @@ test('theme can be extended', ({ expect }) => {
|
|||
|
||||
let config = resolveConfig(design, [
|
||||
{
|
||||
theme: {
|
||||
colors: {
|
||||
red: 'red',
|
||||
},
|
||||
config: {
|
||||
theme: {
|
||||
colors: {
|
||||
red: 'red',
|
||||
},
|
||||
|
||||
fontFamily: {
|
||||
sans: 'SF Pro Display',
|
||||
fontFamily: {
|
||||
sans: 'SF Pro Display',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
theme: {
|
||||
extend: {
|
||||
colors: {
|
||||
blue: 'blue',
|
||||
config: {
|
||||
theme: {
|
||||
extend: {
|
||||
colors: {
|
||||
blue: 'blue',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
|
@ -92,31 +102,37 @@ test('theme keys can reference other theme keys using the theme function regardl
|
|||
|
||||
let config = resolveConfig(design, [
|
||||
{
|
||||
theme: {
|
||||
colors: {
|
||||
red: 'red',
|
||||
},
|
||||
placeholderColor: {
|
||||
green: 'green',
|
||||
config: {
|
||||
theme: {
|
||||
colors: {
|
||||
red: 'red',
|
||||
},
|
||||
placeholderColor: {
|
||||
green: 'green',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
theme: {
|
||||
extend: {
|
||||
colors: ({ theme }) => ({
|
||||
...theme('placeholderColor'),
|
||||
blue: 'blue',
|
||||
}),
|
||||
config: {
|
||||
theme: {
|
||||
extend: {
|
||||
colors: ({ theme }) => ({
|
||||
...theme('placeholderColor'),
|
||||
blue: 'blue',
|
||||
}),
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
theme: {
|
||||
extend: {
|
||||
caretColor: ({ theme }) => theme('accentColor'),
|
||||
accentColor: ({ theme }) => theme('backgroundColor'),
|
||||
backgroundColor: ({ theme }) => theme('colors'),
|
||||
config: {
|
||||
theme: {
|
||||
extend: {
|
||||
caretColor: ({ theme }) => theme('accentColor'),
|
||||
accentColor: ({ theme }) => theme('backgroundColor'),
|
||||
backgroundColor: ({ theme }) => theme('colors'),
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
|
@ -156,23 +172,25 @@ test('theme keys can read from the CSS theme', ({ expect }) => {
|
|||
|
||||
let config = resolveConfig(design, [
|
||||
{
|
||||
theme: {
|
||||
colors: ({ theme }) => ({
|
||||
// Reads from the --color-* namespace
|
||||
...theme('color'),
|
||||
red: 'red',
|
||||
}),
|
||||
accentColor: ({ theme }) => ({
|
||||
// Reads from the --color-* namespace through `colors`
|
||||
...theme('colors'),
|
||||
}),
|
||||
placeholderColor: ({ theme }) => ({
|
||||
// Reads from the --color-* namespace through `colors`
|
||||
primary: theme('colors.green'),
|
||||
config: {
|
||||
theme: {
|
||||
colors: ({ theme }) => ({
|
||||
// Reads from the --color-* namespace
|
||||
...theme('color'),
|
||||
red: 'red',
|
||||
}),
|
||||
accentColor: ({ theme }) => ({
|
||||
// Reads from the --color-* namespace through `colors`
|
||||
...theme('colors'),
|
||||
}),
|
||||
placeholderColor: ({ theme }) => ({
|
||||
// Reads from the --color-* namespace through `colors`
|
||||
primary: theme('colors.green'),
|
||||
|
||||
// Reads from the --color-* namespace directly
|
||||
secondary: theme('color.green'),
|
||||
}),
|
||||
// Reads from the --color-* namespace directly
|
||||
secondary: theme('color.green'),
|
||||
}),
|
||||
},
|
||||
},
|
||||
},
|
||||
])
|
||||
|
|
|
|||
|
|
@ -9,6 +9,11 @@ import {
|
|||
type UserConfig,
|
||||
} from './types'
|
||||
|
||||
export interface ConfigFile {
|
||||
path?: string
|
||||
config: UserConfig
|
||||
}
|
||||
|
||||
interface ResolutionContext {
|
||||
design: DesignSystem
|
||||
configs: UserConfig[]
|
||||
|
|
@ -23,7 +28,7 @@ let minimal: ResolvedConfig = {
|
|||
plugins: [],
|
||||
}
|
||||
|
||||
export function resolveConfig(design: DesignSystem, configs: UserConfig[]): ResolvedConfig {
|
||||
export function resolveConfig(design: DesignSystem, files: ConfigFile[]): ResolvedConfig {
|
||||
let ctx: ResolutionContext = {
|
||||
design,
|
||||
configs: [],
|
||||
|
|
@ -35,8 +40,8 @@ export function resolveConfig(design: DesignSystem, configs: UserConfig[]): Reso
|
|||
result: structuredClone(minimal),
|
||||
}
|
||||
|
||||
for (let config of configs) {
|
||||
resolveInternal(ctx, config)
|
||||
for (let file of files) {
|
||||
resolveInternal(ctx, file)
|
||||
}
|
||||
|
||||
// Merge themes
|
||||
|
|
@ -80,11 +85,11 @@ export interface PluginUtils {
|
|||
theme(keypath: string, defaultValue?: any): any
|
||||
}
|
||||
|
||||
function resolveInternal(ctx: ResolutionContext, user: UserConfig): void {
|
||||
function resolveInternal(ctx: ResolutionContext, { config, path }: ConfigFile): void {
|
||||
let plugins: PluginWithConfig[] = []
|
||||
|
||||
// Normalize plugins so they share the same shape
|
||||
for (let plugin of user.plugins ?? []) {
|
||||
for (let plugin of config.plugins ?? []) {
|
||||
if ('__isOptionsFunction' in plugin) {
|
||||
// Happens with `plugin.withOptions()` when no options were passed:
|
||||
// e.g. `require("my-plugin")` instead of `require("my-plugin")(options)`
|
||||
|
|
@ -103,12 +108,12 @@ function resolveInternal(ctx: ResolutionContext, user: UserConfig): void {
|
|||
}
|
||||
|
||||
// Apply configs from presets
|
||||
if (Array.isArray(user.presets) && user.presets.length === 0) {
|
||||
if (Array.isArray(config.presets) && config.presets.length === 0) {
|
||||
throw new Error('The empty preset `[]` is not supported')
|
||||
}
|
||||
|
||||
for (let preset of user.presets ?? []) {
|
||||
resolveInternal(ctx, preset)
|
||||
for (let preset of config.presets ?? []) {
|
||||
resolveInternal(ctx, { path, config: preset })
|
||||
}
|
||||
|
||||
// Apply configs from plugins
|
||||
|
|
@ -116,12 +121,12 @@ function resolveInternal(ctx: ResolutionContext, user: UserConfig): void {
|
|||
ctx.plugins.push(plugin)
|
||||
|
||||
if (plugin.config) {
|
||||
resolveInternal(ctx, plugin.config)
|
||||
resolveInternal(ctx, { path, config: plugin.config })
|
||||
}
|
||||
}
|
||||
|
||||
// Then apply the "user" config
|
||||
ctx.configs.push(user)
|
||||
ctx.configs.push(config)
|
||||
}
|
||||
|
||||
function mergeTheme(ctx: ResolutionContext) {
|
||||
|
|
|
|||
|
|
@ -332,8 +332,8 @@ export function registerPlugins(
|
|||
ast: AstNode[],
|
||||
) {
|
||||
let resolvedConfig = resolveConfig(designSystem, [
|
||||
createCompatConfig(designSystem.theme),
|
||||
{ plugins },
|
||||
{ config: createCompatConfig(designSystem.theme) },
|
||||
{ config: { plugins } },
|
||||
])
|
||||
|
||||
let pluginApi = buildPluginApi(designSystem, ast, resolvedConfig)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue