@kanso-labs/unplugin-style-dictionary 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +20 -0
- package/README.md +187 -0
- package/dist/index.cjs +2 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.ts +6 -0
- package/dist/index.js +167 -0
- package/dist/index.js.map +1 -0
- package/dist/rolldown.cjs +2 -0
- package/dist/rolldown.cjs.map +1 -0
- package/dist/rolldown.d.ts +2 -0
- package/dist/rolldown.js +7 -0
- package/dist/rolldown.js.map +1 -0
- package/dist/rollup.cjs +2 -0
- package/dist/rollup.cjs.map +1 -0
- package/dist/rollup.d.ts +2 -0
- package/dist/rollup.js +7 -0
- package/dist/rollup.js.map +1 -0
- package/dist/types.d.ts +39 -0
- package/dist/vite.cjs +2 -0
- package/dist/vite.cjs.map +1 -0
- package/dist/vite.d.ts +2 -0
- package/dist/vite.js +7 -0
- package/dist/vite.js.map +1 -0
- package/dist/webpack.cjs +2 -0
- package/dist/webpack.cjs.map +1 -0
- package/dist/webpack.d.ts +2 -0
- package/dist/webpack.js +7 -0
- package/dist/webpack.js.map +1 -0
- package/package.json +104 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 Kanso
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
|
6
|
+
this software and associated documentation files (the "Software"), to deal in
|
|
7
|
+
the Software without restriction, including without limitation the rights to
|
|
8
|
+
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
|
9
|
+
the Software, and to permit persons to whom the Software is furnished to do so,
|
|
10
|
+
subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
|
17
|
+
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
|
18
|
+
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
|
19
|
+
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
|
20
|
+
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,187 @@
|
|
|
1
|
+
# unplugin-style-dictionary
|
|
2
|
+
|
|
3
|
+
A lightweight, robust [unplugin](https://unplugin.unjs.io/)-based plugin to compile **Style Dictionary** design tokens ahead of your bundler, with automatic watching, rebuilding, and hot reloading (HMR) under Vite's dev server.
|
|
4
|
+
|
|
5
|
+
Built on unplugin, the same core plugin targets **Vite**, **Rolldown**, **Rollup**, and **Webpack** from a single implementation — useful when a project has more than one build surface (e.g. Storybook/Vitest on Vite, and a package build on Rolldown/tsdown) that both need tokens compiled ahead of them.
|
|
6
|
+
|
|
7
|
+
## Features
|
|
8
|
+
|
|
9
|
+
- **Multi-bundler**: One implementation, four entry points — Vite, Rolldown, Rollup, and Webpack.
|
|
10
|
+
- **Asynchronous builds**: Native support for Style Dictionary v4/v5 async compilation API.
|
|
11
|
+
- **Automatic watching**: Reads the `source` and `include` patterns from your Style Dictionary configurations and automatically watches them. Live rebuild-on-change is fully supported under Vite's dev server; other targets rebuild on change wherever the host bundler itself runs a persistent watch mode.
|
|
12
|
+
- **Config flexibility**: Supports file paths (JSON, JS, MJS, CJS, TS), configuration objects, or functions — including registering custom formats at config-resolution time.
|
|
13
|
+
- **Multi-configuration**: Can run multiple Style Dictionary configurations in parallel (useful for multi-brand or multi-theme projects).
|
|
14
|
+
- **TypeScript Support**: Fully written in TypeScript and exports complete type definitions.
|
|
15
|
+
|
|
16
|
+
## Installation
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
npm install @kanso-labs/unplugin-style-dictionary style-dictionary --save-dev
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
*Note: `style-dictionary` and your bundler (`vite`, `rolldown`, `rollup`, or `webpack`) are peer dependencies, so you can manage their versions independently.*
|
|
23
|
+
|
|
24
|
+
## Usage
|
|
25
|
+
|
|
26
|
+
Import the entry point that matches your bundler.
|
|
27
|
+
|
|
28
|
+
### Vite
|
|
29
|
+
|
|
30
|
+
```typescript
|
|
31
|
+
import StyleDictionary from '@kanso-labs/unplugin-style-dictionary/vite'
|
|
32
|
+
import { defineConfig } from 'vite'
|
|
33
|
+
|
|
34
|
+
export default defineConfig({
|
|
35
|
+
plugins: [
|
|
36
|
+
StyleDictionary({
|
|
37
|
+
// Path to your Style Dictionary config file
|
|
38
|
+
config: 'tokens/config/sd.config.json',
|
|
39
|
+
}),
|
|
40
|
+
],
|
|
41
|
+
})
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
### Rolldown
|
|
45
|
+
|
|
46
|
+
```typescript
|
|
47
|
+
import StyleDictionary from '@kanso-labs/unplugin-style-dictionary/rolldown'
|
|
48
|
+
|
|
49
|
+
export default {
|
|
50
|
+
plugins: [
|
|
51
|
+
StyleDictionary({
|
|
52
|
+
config: 'tokens/config/sd.config.json',
|
|
53
|
+
}),
|
|
54
|
+
],
|
|
55
|
+
}
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
Rolldown (and tools built on it, like [tsdown](https://tsdown.dev/)) is typically run as a one-shot build rather than a long-lived dev server, so under this target the plugin compiles tokens once in `buildStart` rather than watching for changes. That's enough to guarantee generated token files exist before the rest of the build consumes them.
|
|
59
|
+
|
|
60
|
+
### Rollup / Webpack
|
|
61
|
+
|
|
62
|
+
```typescript
|
|
63
|
+
import StyleDictionary from '@kanso-labs/unplugin-style-dictionary/rollup'
|
|
64
|
+
// or: import StyleDictionary from '@kanso-labs/unplugin-style-dictionary/webpack'
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
### Multiple Configurations
|
|
68
|
+
|
|
69
|
+
If you have multiple themes or sub-brands, pass an array of config paths or objects:
|
|
70
|
+
|
|
71
|
+
```typescript
|
|
72
|
+
StyleDictionary({
|
|
73
|
+
config: [
|
|
74
|
+
'tokens/config/sd-base.config.json',
|
|
75
|
+
'tokens/config/sd-theme.config.json'
|
|
76
|
+
]
|
|
77
|
+
})
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
### Config Objects
|
|
81
|
+
|
|
82
|
+
You can pass Style Dictionary configuration objects directly:
|
|
83
|
+
|
|
84
|
+
```typescript
|
|
85
|
+
StyleDictionary({
|
|
86
|
+
config: {
|
|
87
|
+
source: ['tokens/**/*.json'],
|
|
88
|
+
platforms: {
|
|
89
|
+
css: {
|
|
90
|
+
transformGroup: 'css',
|
|
91
|
+
buildPath: 'dist/css/',
|
|
92
|
+
files: [{ destination: 'variables.css', format: 'css/variables' }]
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
})
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
### Custom Formats
|
|
100
|
+
|
|
101
|
+
`config` also accepts a function, which is the pattern to use when you need to register a custom Style Dictionary format (via `StyleDictionary.registerFormat()`, or any other `register*` call) before it's referenced by name in the returned config. The function re-runs on every build — including watch-triggered rebuilds under Vite — so the format is always registered before it's needed; re-registering the same format name on every rebuild is safe (Style Dictionary silently replaces the existing one).
|
|
102
|
+
|
|
103
|
+
```typescript
|
|
104
|
+
// Named `styleDictionaryPlugin` here to avoid colliding with the `StyleDictionary`
|
|
105
|
+
// class imported from the `style-dictionary` package itself, below.
|
|
106
|
+
import styleDictionaryPlugin from '@kanso-labs/unplugin-style-dictionary/vite'
|
|
107
|
+
import StyleDictionary from 'style-dictionary'
|
|
108
|
+
|
|
109
|
+
export default defineConfig({
|
|
110
|
+
plugins: [
|
|
111
|
+
styleDictionaryPlugin({
|
|
112
|
+
config: () => {
|
|
113
|
+
StyleDictionary.registerFormat({
|
|
114
|
+
name: 'custom/my-format',
|
|
115
|
+
format: ({ dictionary }) =>
|
|
116
|
+
dictionary.allTokens
|
|
117
|
+
.map((token) => `${token.name}: ${token.value}`)
|
|
118
|
+
.join('\n'),
|
|
119
|
+
})
|
|
120
|
+
|
|
121
|
+
return {
|
|
122
|
+
source: ['tokens/**/*.json'],
|
|
123
|
+
platforms: {
|
|
124
|
+
custom: {
|
|
125
|
+
transformGroup: 'css',
|
|
126
|
+
buildPath: 'dist/',
|
|
127
|
+
files: [{ destination: 'tokens.txt', format: 'custom/my-format' }],
|
|
128
|
+
},
|
|
129
|
+
},
|
|
130
|
+
}
|
|
131
|
+
},
|
|
132
|
+
}),
|
|
133
|
+
],
|
|
134
|
+
})
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
## Options Reference
|
|
138
|
+
|
|
139
|
+
```typescript
|
|
140
|
+
export interface UnpluginStyleDictionaryOptions {
|
|
141
|
+
/**
|
|
142
|
+
* Style Dictionary configuration(s).
|
|
143
|
+
* Can be:
|
|
144
|
+
* - A file path string (e.g. 'sd.config.json')
|
|
145
|
+
* - An array of file path strings
|
|
146
|
+
* - A Style Dictionary configuration object
|
|
147
|
+
* - An array of Style Dictionary configuration objects
|
|
148
|
+
* - A function that returns a config or array of configs (or resolves to them).
|
|
149
|
+
* Useful for calling `StyleDictionary.registerFormat()` (or other `register*`
|
|
150
|
+
* methods) before returning a config that references the custom format by name.
|
|
151
|
+
*
|
|
152
|
+
* If not provided, it will look for 'sd.config.json' or 'config.json' in the root directory.
|
|
153
|
+
*/
|
|
154
|
+
config?:
|
|
155
|
+
| string
|
|
156
|
+
| string[]
|
|
157
|
+
| Config
|
|
158
|
+
| Config[]
|
|
159
|
+
| (() => Config | Config[] | Promise<Config | Config[]>)
|
|
160
|
+
|
|
161
|
+
/**
|
|
162
|
+
* Additional files or glob patterns to watch.
|
|
163
|
+
* If config files are paths, those paths are watched automatically.
|
|
164
|
+
* By default, the plugin also parses 'source' and 'include' properties in configurations and watches them.
|
|
165
|
+
*/
|
|
166
|
+
watch?: string | string[]
|
|
167
|
+
|
|
168
|
+
/**
|
|
169
|
+
* Disable console logging.
|
|
170
|
+
* @default false
|
|
171
|
+
*/
|
|
172
|
+
silent?: boolean
|
|
173
|
+
}
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
## Migrating from `vite-plugin-style-dictionary`
|
|
177
|
+
|
|
178
|
+
This package was previously published as `@kanso-labs/vite-plugin-style-dictionary`, implemented directly as a Vite plugin. As of this unplugin-based rewrite:
|
|
179
|
+
|
|
180
|
+
- The package is renamed to `@kanso-labs/unplugin-style-dictionary`.
|
|
181
|
+
- The root import no longer resolves to a ready-to-use Vite plugin. Import the bundler-specific entry point instead: `@kanso-labs/unplugin-style-dictionary/vite` (a drop-in replacement for the old default export), `/rolldown`, `/rollup`, or `/webpack`.
|
|
182
|
+
- The exported options type is renamed from `VitePluginStyleDictionaryOptions` to `UnpluginStyleDictionaryOptions`. The shape of the options (`config`, `watch`, `silent`) is unchanged.
|
|
183
|
+
- Behavior under Vite is unchanged: the same `buildStart`-time compilation and dev-server watch/rebuild logic as before.
|
|
184
|
+
|
|
185
|
+
## License
|
|
186
|
+
|
|
187
|
+
MIT
|
package/dist/index.cjs
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
Object.defineProperties(exports,{__esModule:{value:!0},[Symbol.toStringTag]:{value:`Module`}});var e=Object.create,t=Object.defineProperty,n=Object.getOwnPropertyDescriptor,r=Object.getOwnPropertyNames,i=Object.getPrototypeOf,a=Object.prototype.hasOwnProperty,o=(e,i,o,s)=>{if(i&&typeof i==`object`||typeof i==`function`)for(var c=r(i),l=0,u=c.length,d;l<u;l++)d=c[l],!a.call(e,d)&&d!==o&&t(e,d,{get:(e=>i[e]).bind(null,d),enumerable:!(s=n(i,d))||s.enumerable});return e},s=(n,r,a)=>(a=n==null?{}:e(i(n)),o(r||!n||!n.__esModule?t(a,`default`,{value:n,enumerable:!0}):a,n));let c=require("node:fs");c=s(c,1);let l=require("node:path");l=s(l,1);let u=require("node:url"),d=require("node:zlib");d=s(d,1);let f=require("style-dictionary");f=s(f,1);let p=require("unplugin");var m=(e={})=>{let{silent:t=!1}=e,n=process.cwd(),r=(e,n=`info`)=>{if(t)return;let r=`[unplugin-style-dictionary]`;n===`error`?console.error(`\x1b[31m${r} ${e}\x1b[0m`):console.log(n===`success`?`\x1b[32m${r} ${e}\x1b[0m`:`\x1b[36m${r} ${e}\x1b[0m`)},i=async()=>{let t=e.config;if(!t)for(let e of[`sd.config.json`,`config.json`,`sd.config.js`,`sd.config.mjs`]){let r=l.default.resolve(n,e);if(c.default.existsSync(r)){t=e;break}}return t?(typeof t==`function`&&(t=await t()),(Array.isArray(t)?t:[t]).map(e=>{if(typeof e==`string`){let t=l.default.resolve(n,e);return{config:t,dir:l.default.dirname(t),file:t}}else return{config:e,dir:n}})):(r(`No configuration specified and no default config file found. Style Dictionary will not compile.`,`error`),[])},a=async t=>{let i=new Set;for(let e of t){e.file&&i.add(e.file.replace(/\\/g,`/`));let t=null;if(typeof e.config==`string`)try{if(e.config.endsWith(`.json`)){let n=c.default.readFileSync(e.config,`utf-8`);t=JSON.parse(n)}else{let n=await import(`${(0,u.pathToFileURL)(e.config).href}?t=${Date.now()}`);t=n.default||n}}catch(t){r(`Failed to parse config file: ${e.config}. Error: ${t.message}`,`error`)}else t=e.config;if(t){let n=t=>{if(typeof t==`string`){let n=(l.default.isAbsolute(t)?t:l.default.resolve(e.dir,t)).replace(/\\/g,`/`);i.add(n)}};t.source&&(Array.isArray(t.source)?t.source.forEach(n):n(t.source)),t.include&&(Array.isArray(t.include)?t.include.forEach(n):n(t.include))}}if(e.watch){let t=Array.isArray(e.watch)?e.watch:[e.watch];for(let e of t){let t=l.default.isAbsolute(e)?e:l.default.resolve(n,e);i.add(t.replace(/\\/g,`/`))}}return Array.from(i)},o=async(e,i)=>{let a=Date.now();try{i||r(`Compiling design tokens...`,`info`);let o=new Set;for(let r of e){let e=new f.default(r.config);await e.hasInitialized;let a=await e.extend({log:{verbosity:`silent`}});if(await a.buildAllPlatforms(),!i&&!t&&a.platforms)for(let e of Object.keys(a.platforms)){let t=a.platforms[e];if(t&&t.files){let e=t.buildPath||``;for(let r of t.files)if(r&&r.destination){let t=l.default.isAbsolute(e)?e:l.default.resolve(n,e),i=l.default.isAbsolute(r.destination)?r.destination:l.default.resolve(t,r.destination);o.add(i)}}}}let s=Date.now()-a;if(i)r(`Rebuilt design tokens due to change in ${i} (${s}ms)`,`success`);else{if(!t&&o.size>0){let e=[];for(let t of o)if(c.default.existsSync(t)){let r=l.default.relative(n,t).replace(/\\/g,`/`),i=l.default.dirname(r),a=l.default.basename(r),o=i===`.`?`\x1b[32m${a}\x1b[0m`:`\x1b[90m${i}/\x1b[0m\x1b[32m${a}\x1b[0m`;try{let n=`${(c.default.statSync(t).size/1024).toFixed(2)} kB`,i=c.default.readFileSync(t),a=`${(d.default.gzipSync(i).length/1024).toFixed(2)} kB`;e.push({coloredPath:o,gzipSizeStr:a,relativeDisplayPath:r,sizeStr:n})}catch{}}if(e.length>0){let t=Math.max(...e.map(e=>e.relativeDisplayPath.length),0),n=Math.max(...e.map(e=>e.sizeStr.length),0);for(let r of e){let e=` `.repeat(Math.max(2,t-r.relativeDisplayPath.length+2)),i=r.sizeStr.padStart(n);console.log(`${r.coloredPath}${e}\x1b[90m${i} │ gzip: ${r.gzipSizeStr}\x1b[0m`)}}}r(`Compiled successfully! (${s}ms)`,`success`)}}catch(e){let t=Date.now()-a;r(`Compilation failed after ${t}ms: ${e.message}`,`error`)}};return{async buildStart(){let e=await i();if(e.length===0)return;let t=await a(e);for(let e of t)this.addWatchFile(e);await o(e)},name:`unplugin-style-dictionary`,vite:{configResolved(e){n=e.root||process.cwd()},async configureServer(e){let t=await i();if(t.length===0)return;let n=await a(t);e.watcher.add(n),e.watcher.on(`all`,async(t,r)=>{let s=r.replace(/\\/g,`/`);if(n.some(e=>e===s||s.startsWith(e.replace(/\/\*\*/g,``))||e.includes(`*`)&&new RegExp(e.replace(/[.+^${}()|[\]\\]/g,`\\$&`).replace(/\*/g,`.*`)).test(s))){let t=await i();await o(t,l.default.basename(s));let n=await a(t);e.watcher.add(n)}})}},async watchChange(e){let t=await i();if(t.length===0)return;await o(t,l.default.basename(e));let n=await a(t);for(let e of n)this.addWatchFile(e)}}},h=(0,p.createUnplugin)(m);exports.default=h,exports.unplugin=h,exports.unpluginFactory=m;
|
|
2
|
+
//# sourceMappingURL=index.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.cjs","names":[],"sources":["../src/index.ts"],"sourcesContent":["import type { Config } from 'style-dictionary'\nimport type { UnpluginFactory } from 'unplugin'\nimport type { ViteDevServer } from 'vite'\n\nimport fs from 'node:fs'\nimport path from 'node:path'\nimport { pathToFileURL } from 'node:url'\nimport zlib from 'node:zlib'\nimport StyleDictionary from 'style-dictionary'\nimport { createUnplugin } from 'unplugin'\n\nimport type { UnpluginStyleDictionaryOptions } from './types.js'\n\nexport * from './types.js'\n\nexport const unpluginFactory: UnpluginFactory<\n undefined | UnpluginStyleDictionaryOptions,\n false\n> = (options = {}) => {\n const { silent = false } = options\n let root = process.cwd()\n\n // Helper to log if not silent\n const log = (\n message: string,\n type: 'error' | 'info' | 'success' = 'info',\n ) => {\n if (silent) return\n const prefix = '[unplugin-style-dictionary]'\n if (type === 'error') {\n console.error(`\\x1b[31m${prefix} ${message}\\x1b[0m`)\n } else if (type === 'success') {\n console.log(`\\x1b[32m${prefix} ${message}\\x1b[0m`)\n } else {\n console.log(`\\x1b[36m${prefix} ${message}\\x1b[0m`)\n }\n }\n\n // Resolve config file paths / objects\n const resolveConfigs = async (): Promise<\n Array<{ config: Config | string; dir: string; file?: string }>\n > => {\n let rawConfig = options.config\n\n // If config is not defined, look for default configuration files\n if (!rawConfig) {\n const defaults = [\n 'sd.config.json',\n 'config.json',\n 'sd.config.js',\n 'sd.config.mjs',\n ]\n for (const file of defaults) {\n const fullPath = path.resolve(root, file)\n if (fs.existsSync(fullPath)) {\n rawConfig = file\n break\n }\n }\n }\n\n if (!rawConfig) {\n log(\n 'No configuration specified and no default config file found. Style Dictionary will not compile.',\n 'error',\n )\n return []\n }\n\n // Evaluate function if provided\n if (typeof rawConfig === 'function') {\n rawConfig = await rawConfig()\n }\n\n const configs = Array.isArray(rawConfig) ? rawConfig : [rawConfig]\n\n return configs.map((conf) => {\n if (typeof conf === 'string') {\n const fullPath = path.resolve(root, conf)\n return {\n config: fullPath,\n dir: path.dirname(fullPath),\n file: fullPath,\n }\n } else {\n return {\n config: conf,\n dir: root,\n }\n }\n })\n }\n\n // Parse token files to watch\n const getWatchFiles = async (\n resolvedConfigs: Array<{\n config: Config | string\n dir: string\n file?: string\n }>,\n ): Promise<string[]> => {\n const filesToWatch = new Set<string>()\n\n for (const item of resolvedConfigs) {\n if (item.file) {\n filesToWatch.add(item.file.replace(/\\\\/g, '/'))\n }\n\n let configObj: Config | null = null\n\n if (typeof item.config === 'string') {\n try {\n if (item.config.endsWith('.json')) {\n const content = fs.readFileSync(item.config, 'utf-8')\n configObj = JSON.parse(content)\n } else {\n const fileUrl = pathToFileURL(item.config).href\n const module = await import(`${fileUrl}?t=${Date.now()}`)\n configObj = module.default || module\n }\n } catch (err) {\n log(\n `Failed to parse config file: ${item.config}. Error: ${(err as Error).message}`,\n 'error',\n )\n }\n } else {\n configObj = item.config\n }\n\n if (configObj) {\n const addPattern = (pattern: unknown) => {\n if (typeof pattern === 'string') {\n const absolutePattern = path.isAbsolute(pattern)\n ? pattern\n : path.resolve(item.dir, pattern)\n const normalized = absolutePattern.replace(/\\\\/g, '/')\n filesToWatch.add(normalized)\n }\n }\n\n if (configObj.source) {\n if (Array.isArray(configObj.source)) {\n configObj.source.forEach(addPattern)\n } else {\n addPattern(configObj.source)\n }\n }\n\n if (configObj.include) {\n if (Array.isArray(configObj.include)) {\n configObj.include.forEach(addPattern)\n } else {\n addPattern(configObj.include)\n }\n }\n }\n }\n\n // Add manually configured watch files\n if (options.watch) {\n const extraWatches = Array.isArray(options.watch)\n ? options.watch\n : [options.watch]\n for (const pattern of extraWatches) {\n const absolutePattern = path.isAbsolute(pattern)\n ? pattern\n : path.resolve(root, pattern)\n filesToWatch.add(absolutePattern.replace(/\\\\/g, '/'))\n }\n }\n\n return Array.from(filesToWatch)\n }\n\n // Compile design tokens\n const runBuilds = async (\n resolvedConfigs: Array<{ config: Config | string; dir: string }>,\n context?: string,\n ) => {\n const startTime = Date.now()\n try {\n if (!context) {\n log('Compiling design tokens...', 'info')\n }\n\n const generatedFiles = new Set<string>()\n\n for (const item of resolvedConfigs) {\n const sd = new StyleDictionary(item.config)\n await sd.hasInitialized\n const silentSD = await sd.extend({\n log: {\n verbosity: 'silent',\n },\n })\n await silentSD.buildAllPlatforms()\n\n if (!context && !silent && silentSD.platforms) {\n for (const platformName of Object.keys(silentSD.platforms)) {\n const platform = silentSD.platforms[platformName]\n if (platform && platform.files) {\n const buildPath = platform.buildPath || ''\n for (const file of platform.files) {\n if (file && file.destination) {\n const absoluteBuildPath = path.isAbsolute(buildPath)\n ? buildPath\n : path.resolve(root, buildPath)\n const absoluteDestination = path.isAbsolute(file.destination)\n ? file.destination\n : path.resolve(absoluteBuildPath, file.destination)\n generatedFiles.add(absoluteDestination)\n }\n }\n }\n }\n }\n }\n\n const duration = Date.now() - startTime\n\n if (context) {\n log(\n `Rebuilt design tokens due to change in ${context} (${duration}ms)`,\n 'success',\n )\n } else {\n if (!silent && generatedFiles.size > 0) {\n const fileInfos: Array<{\n coloredPath: string\n gzipSizeStr: string\n relativeDisplayPath: string\n sizeStr: string\n }> = []\n\n for (const filePath of generatedFiles) {\n if (fs.existsSync(filePath)) {\n const displayPath = path\n .relative(root, filePath)\n .replace(/\\\\/g, '/')\n const dir = path.dirname(displayPath)\n const base = path.basename(displayPath)\n const coloredPath =\n dir === '.'\n ? `\\x1b[32m${base}\\x1b[0m`\n : `\\x1b[90m${dir}/\\x1b[0m\\x1b[32m${base}\\x1b[0m`\n\n try {\n const stats = fs.statSync(filePath)\n const bytes = stats.size\n const sizeStr = `${(bytes / 1024).toFixed(2)} kB`\n\n const content = fs.readFileSync(filePath)\n const gzipBytes = zlib.gzipSync(content).length\n const gzipSizeStr = `${(gzipBytes / 1024).toFixed(2)} kB`\n\n fileInfos.push({\n coloredPath,\n gzipSizeStr,\n relativeDisplayPath: displayPath,\n sizeStr,\n })\n } catch {\n // Ignore errors reading individual files\n }\n }\n }\n\n if (fileInfos.length > 0) {\n const longestPathLength = Math.max(\n ...fileInfos.map((f) => f.relativeDisplayPath.length),\n 0,\n )\n const longestSizeLength = Math.max(\n ...fileInfos.map((f) => f.sizeStr.length),\n 0,\n )\n\n for (const info of fileInfos) {\n const pathPadding = ' '.repeat(\n Math.max(\n 2,\n longestPathLength - info.relativeDisplayPath.length + 2,\n ),\n )\n const sizePadded = info.sizeStr.padStart(longestSizeLength)\n console.log(\n `${info.coloredPath}${pathPadding}\\x1b[90m${sizePadded} │ gzip: ${info.gzipSizeStr}\\x1b[0m`,\n )\n }\n }\n }\n\n log(`Compiled successfully! (${duration}ms)`, 'success')\n }\n } catch (err) {\n const duration = Date.now() - startTime\n log(\n `Compilation failed after ${duration}ms: ${(err as Error).message}`,\n 'error',\n )\n }\n }\n\n return {\n async buildStart() {\n const resolved = await resolveConfigs()\n if (resolved.length === 0) return\n\n // Register token/config files with the host bundler's watch mode.\n // Works out of the box wherever the host runs a persistent watcher\n // (e.g. `rollup --watch`); Vite's dev server is additionally handled\n // below via the `vite.configureServer` escape hatch, since token\n // sources are plain JSON/JS files outside the module graph and\n // `watchChange` is not reliably invoked by Vite while serving.\n const watchFiles = await getWatchFiles(resolved)\n for (const file of watchFiles) {\n this.addWatchFile(file)\n }\n\n await runBuilds(resolved)\n },\n\n name: 'unplugin-style-dictionary',\n\n vite: {\n configResolved(config) {\n root = config.root || process.cwd()\n },\n\n async configureServer(server: ViteDevServer) {\n const resolved = await resolveConfigs()\n if (resolved.length === 0) return\n\n const filesToWatch = await getWatchFiles(resolved)\n\n // Watch configuration files and token files\n server.watcher.add(filesToWatch)\n\n server.watcher.on('all', async (_event, file) => {\n const normalizedFile = file.replace(/\\\\/g, '/')\n\n // Check if the modified file matches our watched config or token patterns\n const isConfigOrToken = filesToWatch.some((pattern) => {\n // If the pattern is an exact file path\n if (pattern === normalizedFile) return true\n\n // If the pattern is a glob, we check if the file matches it.\n // Note: A simple string match or simple glob matcher can be used here.\n // For simplicity and correctness, since token source paths are usually globs,\n // we can match based on path directory containment or general matching.\n // Let's implement a robust matchesGlob check or check if it's one of the token files.\n // Chokidar triggers on actual files, so we want to check if the changed file matches\n // any of the config files or token files/globs.\n return (\n normalizedFile.startsWith(pattern.replace(/\\/\\*\\*/g, '')) ||\n (pattern.includes('*') &&\n new RegExp(\n pattern\n .replace(/[.+^${}()|[\\]\\\\]/g, '\\\\$&')\n .replace(/\\*/g, '.*'),\n ).test(normalizedFile))\n )\n })\n\n if (isConfigOrToken) {\n // Re-resolve configs to handle added/removed configs or changes to config itself\n const currentResolved = await resolveConfigs()\n await runBuilds(currentResolved, path.basename(normalizedFile))\n\n // Dynamically update the watch list in case the configurations changed\n const newWatches = await getWatchFiles(currentResolved)\n server.watcher.add(newWatches)\n }\n })\n },\n },\n\n async watchChange(id) {\n const resolved = await resolveConfigs()\n if (resolved.length === 0) return\n\n await runBuilds(resolved, path.basename(id))\n\n const watchFiles = await getWatchFiles(resolved)\n for (const file of watchFiles) {\n this.addWatchFile(file)\n }\n },\n }\n}\n\nexport const unplugin = /* #__PURE__ */ createUnplugin(unpluginFactory)\n\nexport default unplugin\n"],"mappings":"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"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import { UnpluginFactory } from 'unplugin';
|
|
2
|
+
import { UnpluginStyleDictionaryOptions } from './types.js';
|
|
3
|
+
export * from './types.js';
|
|
4
|
+
export declare const unpluginFactory: UnpluginFactory<undefined | UnpluginStyleDictionaryOptions, false>;
|
|
5
|
+
export declare const unplugin: import('unplugin').UnpluginInstance<UnpluginStyleDictionaryOptions | undefined, false>;
|
|
6
|
+
export default unplugin;
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
import e from "node:fs";
|
|
2
|
+
import t from "node:path";
|
|
3
|
+
import { pathToFileURL as n } from "node:url";
|
|
4
|
+
import r from "node:zlib";
|
|
5
|
+
import i from "style-dictionary";
|
|
6
|
+
import { createUnplugin as a } from "unplugin";
|
|
7
|
+
//#region src/index.ts
|
|
8
|
+
var o = (a = {}) => {
|
|
9
|
+
let { silent: o = !1 } = a, s = process.cwd(), c = (e, t = "info") => {
|
|
10
|
+
if (o) return;
|
|
11
|
+
let n = "[unplugin-style-dictionary]";
|
|
12
|
+
t === "error" ? console.error(`\x1b[31m${n} ${e}\x1b[0m`) : console.log(t === "success" ? `\x1b[32m${n} ${e}\x1b[0m` : `\x1b[36m${n} ${e}\x1b[0m`);
|
|
13
|
+
}, l = async () => {
|
|
14
|
+
let n = a.config;
|
|
15
|
+
if (!n) for (let r of [
|
|
16
|
+
"sd.config.json",
|
|
17
|
+
"config.json",
|
|
18
|
+
"sd.config.js",
|
|
19
|
+
"sd.config.mjs"
|
|
20
|
+
]) {
|
|
21
|
+
let i = t.resolve(s, r);
|
|
22
|
+
if (e.existsSync(i)) {
|
|
23
|
+
n = r;
|
|
24
|
+
break;
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
return n ? (typeof n == "function" && (n = await n()), (Array.isArray(n) ? n : [n]).map((e) => {
|
|
28
|
+
if (typeof e == "string") {
|
|
29
|
+
let n = t.resolve(s, e);
|
|
30
|
+
return {
|
|
31
|
+
config: n,
|
|
32
|
+
dir: t.dirname(n),
|
|
33
|
+
file: n
|
|
34
|
+
};
|
|
35
|
+
} else return {
|
|
36
|
+
config: e,
|
|
37
|
+
dir: s
|
|
38
|
+
};
|
|
39
|
+
})) : (c("No configuration specified and no default config file found. Style Dictionary will not compile.", "error"), []);
|
|
40
|
+
}, u = async (r) => {
|
|
41
|
+
let i = /* @__PURE__ */ new Set();
|
|
42
|
+
for (let a of r) {
|
|
43
|
+
a.file && i.add(a.file.replace(/\\/g, "/"));
|
|
44
|
+
let r = null;
|
|
45
|
+
if (typeof a.config == "string") try {
|
|
46
|
+
if (a.config.endsWith(".json")) {
|
|
47
|
+
let t = e.readFileSync(a.config, "utf-8");
|
|
48
|
+
r = JSON.parse(t);
|
|
49
|
+
} else {
|
|
50
|
+
let e = await import(`${n(a.config).href}?t=${Date.now()}`);
|
|
51
|
+
r = e.default || e;
|
|
52
|
+
}
|
|
53
|
+
} catch (e) {
|
|
54
|
+
c(`Failed to parse config file: ${a.config}. Error: ${e.message}`, "error");
|
|
55
|
+
}
|
|
56
|
+
else r = a.config;
|
|
57
|
+
if (r) {
|
|
58
|
+
let e = (e) => {
|
|
59
|
+
if (typeof e == "string") {
|
|
60
|
+
let n = (t.isAbsolute(e) ? e : t.resolve(a.dir, e)).replace(/\\/g, "/");
|
|
61
|
+
i.add(n);
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
r.source && (Array.isArray(r.source) ? r.source.forEach(e) : e(r.source)), r.include && (Array.isArray(r.include) ? r.include.forEach(e) : e(r.include));
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
if (a.watch) {
|
|
68
|
+
let e = Array.isArray(a.watch) ? a.watch : [a.watch];
|
|
69
|
+
for (let n of e) {
|
|
70
|
+
let e = t.isAbsolute(n) ? n : t.resolve(s, n);
|
|
71
|
+
i.add(e.replace(/\\/g, "/"));
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
return Array.from(i);
|
|
75
|
+
}, d = async (n, a) => {
|
|
76
|
+
let l = Date.now();
|
|
77
|
+
try {
|
|
78
|
+
a || c("Compiling design tokens...", "info");
|
|
79
|
+
let u = /* @__PURE__ */ new Set();
|
|
80
|
+
for (let e of n) {
|
|
81
|
+
let n = new i(e.config);
|
|
82
|
+
await n.hasInitialized;
|
|
83
|
+
let r = await n.extend({ log: { verbosity: "silent" } });
|
|
84
|
+
if (await r.buildAllPlatforms(), !a && !o && r.platforms) for (let e of Object.keys(r.platforms)) {
|
|
85
|
+
let n = r.platforms[e];
|
|
86
|
+
if (n && n.files) {
|
|
87
|
+
let e = n.buildPath || "";
|
|
88
|
+
for (let r of n.files) if (r && r.destination) {
|
|
89
|
+
let n = t.isAbsolute(e) ? e : t.resolve(s, e), i = t.isAbsolute(r.destination) ? r.destination : t.resolve(n, r.destination);
|
|
90
|
+
u.add(i);
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
let d = Date.now() - l;
|
|
96
|
+
if (a) c(`Rebuilt design tokens due to change in ${a} (${d}ms)`, "success");
|
|
97
|
+
else {
|
|
98
|
+
if (!o && u.size > 0) {
|
|
99
|
+
let n = [];
|
|
100
|
+
for (let i of u) if (e.existsSync(i)) {
|
|
101
|
+
let a = t.relative(s, i).replace(/\\/g, "/"), o = t.dirname(a), c = t.basename(a), l = o === "." ? `\x1b[32m${c}\x1b[0m` : `\x1b[90m${o}/\x1b[0m\x1b[32m${c}\x1b[0m`;
|
|
102
|
+
try {
|
|
103
|
+
let t = `${(e.statSync(i).size / 1024).toFixed(2)} kB`, o = e.readFileSync(i), s = `${(r.gzipSync(o).length / 1024).toFixed(2)} kB`;
|
|
104
|
+
n.push({
|
|
105
|
+
coloredPath: l,
|
|
106
|
+
gzipSizeStr: s,
|
|
107
|
+
relativeDisplayPath: a,
|
|
108
|
+
sizeStr: t
|
|
109
|
+
});
|
|
110
|
+
} catch {}
|
|
111
|
+
}
|
|
112
|
+
if (n.length > 0) {
|
|
113
|
+
let e = Math.max(...n.map((e) => e.relativeDisplayPath.length), 0), t = Math.max(...n.map((e) => e.sizeStr.length), 0);
|
|
114
|
+
for (let r of n) {
|
|
115
|
+
let n = " ".repeat(Math.max(2, e - r.relativeDisplayPath.length + 2)), i = r.sizeStr.padStart(t);
|
|
116
|
+
console.log(`${r.coloredPath}${n}\x1b[90m${i} │ gzip: ${r.gzipSizeStr}\x1b[0m`);
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
c(`Compiled successfully! (${d}ms)`, "success");
|
|
121
|
+
}
|
|
122
|
+
} catch (e) {
|
|
123
|
+
let t = Date.now() - l;
|
|
124
|
+
c(`Compilation failed after ${t}ms: ${e.message}`, "error");
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
return {
|
|
128
|
+
async buildStart() {
|
|
129
|
+
let e = await l();
|
|
130
|
+
if (e.length === 0) return;
|
|
131
|
+
let t = await u(e);
|
|
132
|
+
for (let e of t) this.addWatchFile(e);
|
|
133
|
+
await d(e);
|
|
134
|
+
},
|
|
135
|
+
name: "unplugin-style-dictionary",
|
|
136
|
+
vite: {
|
|
137
|
+
configResolved(e) {
|
|
138
|
+
s = e.root || process.cwd();
|
|
139
|
+
},
|
|
140
|
+
async configureServer(e) {
|
|
141
|
+
let n = await l();
|
|
142
|
+
if (n.length === 0) return;
|
|
143
|
+
let r = await u(n);
|
|
144
|
+
e.watcher.add(r), e.watcher.on("all", async (n, i) => {
|
|
145
|
+
let a = i.replace(/\\/g, "/");
|
|
146
|
+
if (r.some((e) => e === a || a.startsWith(e.replace(/\/\*\*/g, "")) || e.includes("*") && new RegExp(e.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, ".*")).test(a))) {
|
|
147
|
+
let n = await l();
|
|
148
|
+
await d(n, t.basename(a));
|
|
149
|
+
let r = await u(n);
|
|
150
|
+
e.watcher.add(r);
|
|
151
|
+
}
|
|
152
|
+
});
|
|
153
|
+
}
|
|
154
|
+
},
|
|
155
|
+
async watchChange(e) {
|
|
156
|
+
let n = await l();
|
|
157
|
+
if (n.length === 0) return;
|
|
158
|
+
await d(n, t.basename(e));
|
|
159
|
+
let r = await u(n);
|
|
160
|
+
for (let e of r) this.addWatchFile(e);
|
|
161
|
+
}
|
|
162
|
+
};
|
|
163
|
+
}, s = /* #__PURE__ */ a(o);
|
|
164
|
+
//#endregion
|
|
165
|
+
export { s as default, s as unplugin, o as unpluginFactory };
|
|
166
|
+
|
|
167
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["import type { Config } from 'style-dictionary'\nimport type { UnpluginFactory } from 'unplugin'\nimport type { ViteDevServer } from 'vite'\n\nimport fs from 'node:fs'\nimport path from 'node:path'\nimport { pathToFileURL } from 'node:url'\nimport zlib from 'node:zlib'\nimport StyleDictionary from 'style-dictionary'\nimport { createUnplugin } from 'unplugin'\n\nimport type { UnpluginStyleDictionaryOptions } from './types.js'\n\nexport * from './types.js'\n\nexport const unpluginFactory: UnpluginFactory<\n undefined | UnpluginStyleDictionaryOptions,\n false\n> = (options = {}) => {\n const { silent = false } = options\n let root = process.cwd()\n\n // Helper to log if not silent\n const log = (\n message: string,\n type: 'error' | 'info' | 'success' = 'info',\n ) => {\n if (silent) return\n const prefix = '[unplugin-style-dictionary]'\n if (type === 'error') {\n console.error(`\\x1b[31m${prefix} ${message}\\x1b[0m`)\n } else if (type === 'success') {\n console.log(`\\x1b[32m${prefix} ${message}\\x1b[0m`)\n } else {\n console.log(`\\x1b[36m${prefix} ${message}\\x1b[0m`)\n }\n }\n\n // Resolve config file paths / objects\n const resolveConfigs = async (): Promise<\n Array<{ config: Config | string; dir: string; file?: string }>\n > => {\n let rawConfig = options.config\n\n // If config is not defined, look for default configuration files\n if (!rawConfig) {\n const defaults = [\n 'sd.config.json',\n 'config.json',\n 'sd.config.js',\n 'sd.config.mjs',\n ]\n for (const file of defaults) {\n const fullPath = path.resolve(root, file)\n if (fs.existsSync(fullPath)) {\n rawConfig = file\n break\n }\n }\n }\n\n if (!rawConfig) {\n log(\n 'No configuration specified and no default config file found. Style Dictionary will not compile.',\n 'error',\n )\n return []\n }\n\n // Evaluate function if provided\n if (typeof rawConfig === 'function') {\n rawConfig = await rawConfig()\n }\n\n const configs = Array.isArray(rawConfig) ? rawConfig : [rawConfig]\n\n return configs.map((conf) => {\n if (typeof conf === 'string') {\n const fullPath = path.resolve(root, conf)\n return {\n config: fullPath,\n dir: path.dirname(fullPath),\n file: fullPath,\n }\n } else {\n return {\n config: conf,\n dir: root,\n }\n }\n })\n }\n\n // Parse token files to watch\n const getWatchFiles = async (\n resolvedConfigs: Array<{\n config: Config | string\n dir: string\n file?: string\n }>,\n ): Promise<string[]> => {\n const filesToWatch = new Set<string>()\n\n for (const item of resolvedConfigs) {\n if (item.file) {\n filesToWatch.add(item.file.replace(/\\\\/g, '/'))\n }\n\n let configObj: Config | null = null\n\n if (typeof item.config === 'string') {\n try {\n if (item.config.endsWith('.json')) {\n const content = fs.readFileSync(item.config, 'utf-8')\n configObj = JSON.parse(content)\n } else {\n const fileUrl = pathToFileURL(item.config).href\n const module = await import(`${fileUrl}?t=${Date.now()}`)\n configObj = module.default || module\n }\n } catch (err) {\n log(\n `Failed to parse config file: ${item.config}. Error: ${(err as Error).message}`,\n 'error',\n )\n }\n } else {\n configObj = item.config\n }\n\n if (configObj) {\n const addPattern = (pattern: unknown) => {\n if (typeof pattern === 'string') {\n const absolutePattern = path.isAbsolute(pattern)\n ? pattern\n : path.resolve(item.dir, pattern)\n const normalized = absolutePattern.replace(/\\\\/g, '/')\n filesToWatch.add(normalized)\n }\n }\n\n if (configObj.source) {\n if (Array.isArray(configObj.source)) {\n configObj.source.forEach(addPattern)\n } else {\n addPattern(configObj.source)\n }\n }\n\n if (configObj.include) {\n if (Array.isArray(configObj.include)) {\n configObj.include.forEach(addPattern)\n } else {\n addPattern(configObj.include)\n }\n }\n }\n }\n\n // Add manually configured watch files\n if (options.watch) {\n const extraWatches = Array.isArray(options.watch)\n ? options.watch\n : [options.watch]\n for (const pattern of extraWatches) {\n const absolutePattern = path.isAbsolute(pattern)\n ? pattern\n : path.resolve(root, pattern)\n filesToWatch.add(absolutePattern.replace(/\\\\/g, '/'))\n }\n }\n\n return Array.from(filesToWatch)\n }\n\n // Compile design tokens\n const runBuilds = async (\n resolvedConfigs: Array<{ config: Config | string; dir: string }>,\n context?: string,\n ) => {\n const startTime = Date.now()\n try {\n if (!context) {\n log('Compiling design tokens...', 'info')\n }\n\n const generatedFiles = new Set<string>()\n\n for (const item of resolvedConfigs) {\n const sd = new StyleDictionary(item.config)\n await sd.hasInitialized\n const silentSD = await sd.extend({\n log: {\n verbosity: 'silent',\n },\n })\n await silentSD.buildAllPlatforms()\n\n if (!context && !silent && silentSD.platforms) {\n for (const platformName of Object.keys(silentSD.platforms)) {\n const platform = silentSD.platforms[platformName]\n if (platform && platform.files) {\n const buildPath = platform.buildPath || ''\n for (const file of platform.files) {\n if (file && file.destination) {\n const absoluteBuildPath = path.isAbsolute(buildPath)\n ? buildPath\n : path.resolve(root, buildPath)\n const absoluteDestination = path.isAbsolute(file.destination)\n ? file.destination\n : path.resolve(absoluteBuildPath, file.destination)\n generatedFiles.add(absoluteDestination)\n }\n }\n }\n }\n }\n }\n\n const duration = Date.now() - startTime\n\n if (context) {\n log(\n `Rebuilt design tokens due to change in ${context} (${duration}ms)`,\n 'success',\n )\n } else {\n if (!silent && generatedFiles.size > 0) {\n const fileInfos: Array<{\n coloredPath: string\n gzipSizeStr: string\n relativeDisplayPath: string\n sizeStr: string\n }> = []\n\n for (const filePath of generatedFiles) {\n if (fs.existsSync(filePath)) {\n const displayPath = path\n .relative(root, filePath)\n .replace(/\\\\/g, '/')\n const dir = path.dirname(displayPath)\n const base = path.basename(displayPath)\n const coloredPath =\n dir === '.'\n ? `\\x1b[32m${base}\\x1b[0m`\n : `\\x1b[90m${dir}/\\x1b[0m\\x1b[32m${base}\\x1b[0m`\n\n try {\n const stats = fs.statSync(filePath)\n const bytes = stats.size\n const sizeStr = `${(bytes / 1024).toFixed(2)} kB`\n\n const content = fs.readFileSync(filePath)\n const gzipBytes = zlib.gzipSync(content).length\n const gzipSizeStr = `${(gzipBytes / 1024).toFixed(2)} kB`\n\n fileInfos.push({\n coloredPath,\n gzipSizeStr,\n relativeDisplayPath: displayPath,\n sizeStr,\n })\n } catch {\n // Ignore errors reading individual files\n }\n }\n }\n\n if (fileInfos.length > 0) {\n const longestPathLength = Math.max(\n ...fileInfos.map((f) => f.relativeDisplayPath.length),\n 0,\n )\n const longestSizeLength = Math.max(\n ...fileInfos.map((f) => f.sizeStr.length),\n 0,\n )\n\n for (const info of fileInfos) {\n const pathPadding = ' '.repeat(\n Math.max(\n 2,\n longestPathLength - info.relativeDisplayPath.length + 2,\n ),\n )\n const sizePadded = info.sizeStr.padStart(longestSizeLength)\n console.log(\n `${info.coloredPath}${pathPadding}\\x1b[90m${sizePadded} │ gzip: ${info.gzipSizeStr}\\x1b[0m`,\n )\n }\n }\n }\n\n log(`Compiled successfully! (${duration}ms)`, 'success')\n }\n } catch (err) {\n const duration = Date.now() - startTime\n log(\n `Compilation failed after ${duration}ms: ${(err as Error).message}`,\n 'error',\n )\n }\n }\n\n return {\n async buildStart() {\n const resolved = await resolveConfigs()\n if (resolved.length === 0) return\n\n // Register token/config files with the host bundler's watch mode.\n // Works out of the box wherever the host runs a persistent watcher\n // (e.g. `rollup --watch`); Vite's dev server is additionally handled\n // below via the `vite.configureServer` escape hatch, since token\n // sources are plain JSON/JS files outside the module graph and\n // `watchChange` is not reliably invoked by Vite while serving.\n const watchFiles = await getWatchFiles(resolved)\n for (const file of watchFiles) {\n this.addWatchFile(file)\n }\n\n await runBuilds(resolved)\n },\n\n name: 'unplugin-style-dictionary',\n\n vite: {\n configResolved(config) {\n root = config.root || process.cwd()\n },\n\n async configureServer(server: ViteDevServer) {\n const resolved = await resolveConfigs()\n if (resolved.length === 0) return\n\n const filesToWatch = await getWatchFiles(resolved)\n\n // Watch configuration files and token files\n server.watcher.add(filesToWatch)\n\n server.watcher.on('all', async (_event, file) => {\n const normalizedFile = file.replace(/\\\\/g, '/')\n\n // Check if the modified file matches our watched config or token patterns\n const isConfigOrToken = filesToWatch.some((pattern) => {\n // If the pattern is an exact file path\n if (pattern === normalizedFile) return true\n\n // If the pattern is a glob, we check if the file matches it.\n // Note: A simple string match or simple glob matcher can be used here.\n // For simplicity and correctness, since token source paths are usually globs,\n // we can match based on path directory containment or general matching.\n // Let's implement a robust matchesGlob check or check if it's one of the token files.\n // Chokidar triggers on actual files, so we want to check if the changed file matches\n // any of the config files or token files/globs.\n return (\n normalizedFile.startsWith(pattern.replace(/\\/\\*\\*/g, '')) ||\n (pattern.includes('*') &&\n new RegExp(\n pattern\n .replace(/[.+^${}()|[\\]\\\\]/g, '\\\\$&')\n .replace(/\\*/g, '.*'),\n ).test(normalizedFile))\n )\n })\n\n if (isConfigOrToken) {\n // Re-resolve configs to handle added/removed configs or changes to config itself\n const currentResolved = await resolveConfigs()\n await runBuilds(currentResolved, path.basename(normalizedFile))\n\n // Dynamically update the watch list in case the configurations changed\n const newWatches = await getWatchFiles(currentResolved)\n server.watcher.add(newWatches)\n }\n })\n },\n },\n\n async watchChange(id) {\n const resolved = await resolveConfigs()\n if (resolved.length === 0) return\n\n await runBuilds(resolved, path.basename(id))\n\n const watchFiles = await getWatchFiles(resolved)\n for (const file of watchFiles) {\n this.addWatchFile(file)\n }\n },\n }\n}\n\nexport const unplugin = /* #__PURE__ */ createUnplugin(unpluginFactory)\n\nexport default unplugin\n"],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rolldown.cjs","names":[],"sources":["../src/rolldown.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.rolldown\n"],"mappings":"+FAEA,IAAA,uBAAe,CAAA,CAAA,QAAS"}
|
package/dist/rolldown.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rolldown.js","names":[],"sources":["../src/rolldown.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.rolldown\n"],"mappings":";;AAEA,IAAA,IAAe,EAAS"}
|
package/dist/rollup.cjs
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rollup.cjs","names":[],"sources":["../src/rollup.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.rollup\n"],"mappings":"+FAEA,IAAA,uBAAe,CAAA,CAAA,QAAS"}
|
package/dist/rollup.d.ts
ADDED
package/dist/rollup.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rollup.js","names":[],"sources":["../src/rollup.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.rollup\n"],"mappings":";;AAEA,IAAA,IAAe,EAAS"}
|
package/dist/types.d.ts
ADDED
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { Config } from 'style-dictionary';
|
|
2
|
+
/**
|
|
3
|
+
* Options for the Style Dictionary unplugin factory, shared across all bundler
|
|
4
|
+
* targets (Vite, Rolldown, Rollup, Webpack).
|
|
5
|
+
*
|
|
6
|
+
* Live rebuild-on-change is driven by the host bundler's watch mode. Vite's dev
|
|
7
|
+
* server is handled explicitly and is the best-supported case. Other targets
|
|
8
|
+
* rebuild on change only when the host bundler itself runs a persistent watch
|
|
9
|
+
* mode (e.g. `rollup --watch`), since token source files sit outside the module
|
|
10
|
+
* graph. A one-shot build (e.g. `tsdown`/`rolldown build` without `--watch`)
|
|
11
|
+
* only builds once, in `buildStart`.
|
|
12
|
+
*/
|
|
13
|
+
export interface UnpluginStyleDictionaryOptions {
|
|
14
|
+
/**
|
|
15
|
+
* Style Dictionary configuration(s).
|
|
16
|
+
* Can be:
|
|
17
|
+
* - A file path string (e.g. 'sd.config.json')
|
|
18
|
+
* - An array of file path strings
|
|
19
|
+
* - A Style Dictionary configuration object
|
|
20
|
+
* - An array of Style Dictionary configuration objects
|
|
21
|
+
* - A function that returns a config or array of configs (or resolves to them).
|
|
22
|
+
* Useful for calling `StyleDictionary.registerFormat()` (or other `register*`
|
|
23
|
+
* methods) before returning a config that references the custom format by name.
|
|
24
|
+
*
|
|
25
|
+
* If not provided, it will look for 'sd.config.json' or 'config.json' in the root directory.
|
|
26
|
+
*/
|
|
27
|
+
config?: (() => Config | Config[] | Promise<Config | Config[]>) | Config | Config[] | string | string[];
|
|
28
|
+
/**
|
|
29
|
+
* Disable console logging.
|
|
30
|
+
* @default false
|
|
31
|
+
*/
|
|
32
|
+
silent?: boolean;
|
|
33
|
+
/**
|
|
34
|
+
* Additional files or glob patterns to watch.
|
|
35
|
+
* If config files are paths, those paths are watched automatically.
|
|
36
|
+
* By default, the plugin also parses 'source' and 'include' properties in configurations and watches them.
|
|
37
|
+
*/
|
|
38
|
+
watch?: string | string[];
|
|
39
|
+
}
|
package/dist/vite.cjs
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"vite.cjs","names":[],"sources":["../src/vite.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.vite\n"],"mappings":"+FAEA,IAAA,uBAAe,CAAA,CAAA,QAAS"}
|
package/dist/vite.d.ts
ADDED
package/dist/vite.js
ADDED
package/dist/vite.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"vite.js","names":[],"sources":["../src/vite.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.vite\n"],"mappings":";;AAEA,IAAA,IAAe,EAAS"}
|
package/dist/webpack.cjs
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"webpack.cjs","names":[],"sources":["../src/webpack.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.webpack\n"],"mappings":"+FAEA,IAAA,uBAAe,CAAA,CAAA,QAAS"}
|
package/dist/webpack.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"webpack.js","names":[],"sources":["../src/webpack.ts"],"sourcesContent":["import { unplugin } from './index.js'\n\nexport default unplugin.webpack\n"],"mappings":";;AAEA,IAAA,IAAe,EAAS"}
|
package/package.json
ADDED
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@kanso-labs/unplugin-style-dictionary",
|
|
3
|
+
"version": "0.2.0",
|
|
4
|
+
"description": "Compile Style Dictionary design tokens ahead of your bundler (Vite, Rolldown, Rollup, or Webpack) from a single unplugin-based plugin, with automatic watching and rebuilding under Vite",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"unplugin",
|
|
7
|
+
"vite",
|
|
8
|
+
"rolldown",
|
|
9
|
+
"rollup",
|
|
10
|
+
"webpack",
|
|
11
|
+
"style-dictionary",
|
|
12
|
+
"design-tokens",
|
|
13
|
+
"tokens"
|
|
14
|
+
],
|
|
15
|
+
"license": "MIT",
|
|
16
|
+
"files": [
|
|
17
|
+
"dist"
|
|
18
|
+
],
|
|
19
|
+
"exports": {
|
|
20
|
+
".": {
|
|
21
|
+
"types": "./dist/index.d.ts",
|
|
22
|
+
"import": "./dist/index.js",
|
|
23
|
+
"require": "./dist/index.cjs"
|
|
24
|
+
},
|
|
25
|
+
"./vite": {
|
|
26
|
+
"types": "./dist/vite.d.ts",
|
|
27
|
+
"import": "./dist/vite.js",
|
|
28
|
+
"require": "./dist/vite.cjs"
|
|
29
|
+
},
|
|
30
|
+
"./rolldown": {
|
|
31
|
+
"types": "./dist/rolldown.d.ts",
|
|
32
|
+
"import": "./dist/rolldown.js",
|
|
33
|
+
"require": "./dist/rolldown.cjs"
|
|
34
|
+
},
|
|
35
|
+
"./rollup": {
|
|
36
|
+
"types": "./dist/rollup.d.ts",
|
|
37
|
+
"import": "./dist/rollup.js",
|
|
38
|
+
"require": "./dist/rollup.cjs"
|
|
39
|
+
},
|
|
40
|
+
"./webpack": {
|
|
41
|
+
"types": "./dist/webpack.d.ts",
|
|
42
|
+
"import": "./dist/webpack.js",
|
|
43
|
+
"require": "./dist/webpack.cjs"
|
|
44
|
+
},
|
|
45
|
+
"./package.json": "./package.json"
|
|
46
|
+
},
|
|
47
|
+
"main": "./dist/index.cjs",
|
|
48
|
+
"module": "./dist/index.js",
|
|
49
|
+
"types": "./dist/index.d.ts",
|
|
50
|
+
"type": "module",
|
|
51
|
+
"scripts": {
|
|
52
|
+
"build": "tsc -b && vite build",
|
|
53
|
+
"clean": "rimraf dist",
|
|
54
|
+
"lint": "eslint .",
|
|
55
|
+
"test": "vitest run",
|
|
56
|
+
"prepare": "husky"
|
|
57
|
+
},
|
|
58
|
+
"peerDependencies": {
|
|
59
|
+
"rolldown": "*",
|
|
60
|
+
"rollup": "*",
|
|
61
|
+
"style-dictionary": "^5.0.0",
|
|
62
|
+
"vite": "^6.0.0 || ^7.0.0 || ^8.0.0",
|
|
63
|
+
"webpack": "*"
|
|
64
|
+
},
|
|
65
|
+
"peerDependenciesMeta": {
|
|
66
|
+
"rolldown": {
|
|
67
|
+
"optional": true
|
|
68
|
+
},
|
|
69
|
+
"rollup": {
|
|
70
|
+
"optional": true
|
|
71
|
+
},
|
|
72
|
+
"vite": {
|
|
73
|
+
"optional": true
|
|
74
|
+
},
|
|
75
|
+
"webpack": {
|
|
76
|
+
"optional": true
|
|
77
|
+
}
|
|
78
|
+
},
|
|
79
|
+
"devDependencies": {
|
|
80
|
+
"@commitlint/cli": "21.2.1",
|
|
81
|
+
"@commitlint/config-conventional": "21.2.0",
|
|
82
|
+
"@eslint/js": "10.0.1",
|
|
83
|
+
"@types/node": "25.9.1",
|
|
84
|
+
"eslint": "10.5.0",
|
|
85
|
+
"eslint-config-prettier": "10.1.8",
|
|
86
|
+
"eslint-plugin-perfectionist": "5.9.1",
|
|
87
|
+
"eslint-plugin-prettier": "5.5.6",
|
|
88
|
+
"globals": "17.6.0",
|
|
89
|
+
"husky": "9.1.7",
|
|
90
|
+
"prettier": "3.8.3",
|
|
91
|
+
"rimraf": "6.1.3",
|
|
92
|
+
"rollup": "^4.62.2",
|
|
93
|
+
"style-dictionary": "5.4.1",
|
|
94
|
+
"typescript": "6.0.3",
|
|
95
|
+
"typescript-eslint": "8.61.1",
|
|
96
|
+
"vite": "8.1.5",
|
|
97
|
+
"vite-plugin-dts": "5.0.1",
|
|
98
|
+
"vitest": "4.1.10",
|
|
99
|
+
"webpack": "^5.108.4"
|
|
100
|
+
},
|
|
101
|
+
"dependencies": {
|
|
102
|
+
"unplugin": "^3.3.0"
|
|
103
|
+
}
|
|
104
|
+
}
|