Monorepo workflow
Watch panda lib in the package. Never put a manifest package in include.
The design system and the app are workspace packages. Run panda lib --watch in the library. The app points at it with
designSystem.
my-design-system/
├── packages/
│ ├── ds/
│ └── app/
├── package.json
└── pnpm-workspace.yamlpnpm-workspace.yaml
packages:
- 'packages/*'packages/app/package.json
{
"dependencies": {
"@acme/ds": "workspace:*"
}
}packages/app/panda.config.ts
export default defineConfig({
designSystem: '@acme/ds',
include: ['src/**/*.{ts,tsx}']
})Do not include the library source
A package that already ran panda lib has a manifest (dist/panda/lib.json). It belongs in designSystem, not
include.
packages/app/panda.config.ts
export default defineConfig({
designSystem: '@acme/ds',
// ❌ errors: design_system_in_include
include: ['src/**/*.{ts,tsx}', '@acme/ds']
})A path glob into the package does not error. It re-extracts source the manifest already covers, so remove it too:
packages/app/panda.config.ts
export default defineConfig({
designSystem: '@acme/ds',
include: [
'src/**/*.{ts,tsx}',
// ⚠️ no error, but wasted work: buildinfo.json already has these styles
'./node_modules/@acme/ds/src/**/*.{ts,tsx}'
]
})The app replays the styles recorded in buildinfo.json. It does not re-scan the library source.
Watch the library
packages/ds/package.json
{
"scripts": {
"watch": "panda codegen && panda lib --watch"
}
}pnpm --filter @acme/ds watch
pnpm --filter @acme/app devpanda lib --watch rewrites dist/panda/ when tokens, recipes, or components change. It does not rerun
panda codegen. If a change updates generated styled-system files, run panda codegen again, or keep a second
codegen watcher.
Panda watches the app's include plus the library's manifest and build-info paths. Editing library source updates JS
through your bundler. CSS can lag until panda lib finishes. That is a known limit.
When CSS does not update
- Confirm the library watcher is running and
dist/panda/buildinfo.jsonis rewriting. - Confirm the app lists
designSystem: '@acme/ds', not the library ininclude. - Run the app with
--log-level debugand save again. - If Panda rewrote CSS but the browser did not, the bundler is not watching the workspace package. Vite often skips
node_modules(including workspace links).
packages/app/vite.config.ts
export default defineConfig({
server: {
watch: {
ignored: ['!**/node_modules/@acme/ds/**']
}
}
})Exact Vite / webpack flags depend on the app. The symptom is the same: files on disk are new, the dev server is not.
Build order
Start the library watcher first. The app's first panda codegen needs dist/panda/ (or a workspace:* source export)
to resolve.
package.json
{
"scripts": {
"dev": "pnpm --filter @acme/ds watch & pnpm --filter @acme/app dev"
}
}