Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
Expand Up @@ -670,6 +670,15 @@ Two pieces make the current arrangement, and they have to stay in step:
`main`. Deploy hooks are unaffected by `deploymentEnabled: false` — that setting gates the Git
integration, not the hook.

**Vercel installs from `apps/docs`, and CI does not.** An `npm install` run inside a workspace
brings only what that workspace depends on, directly or through another workspace it names. CI
runs `npm ci` at the root, which brings everything, so a package the docs build needs and
`apps/docs` never declared is present in CI and missing on Vercel. The first deploy of the web
collection failed this way, on `tailwind-variants`, with every check green. The docs app
therefore depends on `panelui-web` by name, because its pages import that source by path, and a
contract test holds it there. To see what Vercel will see, clone the repository fresh, then
`cd apps/docs && npm install && npm run build`.

**A documentation change that is not part of a release does not reach panelui.dev on its own.**
New previews, a corrected props table and a typo fix all sit on `main` until the next release. To
publish them now, run the **Deploy docs** workflow by hand from the Actions tab — that is what the
Expand Down
1 change: 1 addition & 0 deletions apps/docs/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@
"lucide-react": "^1.25.0",
"next": "^16.3.0",
"next-themes": "^0.4.6",
"panelui-web": "*",
"react": "^19.2.3",
"react-day-picker": "^10.0.1",
"react-dom": "^19.2.3",
Expand Down
36 changes: 36 additions & 0 deletions apps/docs/test/web-registry.test.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -114,3 +114,39 @@ test('every component has a thumb for the index, and the index shows the gallery
}
assert.match(read('content/docs/web/components/index.mdx'), /<WebComponentGallery \/>/);
});

/*
* The site is built on Vercel from `apps/docs`, and an install run from there
* brings only what the docs app depends on, directly or through a workspace
* it names. The pages import the web components' source by path, so that
* source's own imports have to arrive the same way. CI installs every
* workspace from the root and cannot see one that is missing: the first
* deploy of the web collection failed on exactly this, with every check green.
*/
test('the docs app can install what the web components import', () => {
const web = path.resolve(docs, '../../packages/web');
const webPackage = JSON.parse(fs.readFileSync(path.join(web, 'package.json'), 'utf8'));
const docsPackage = JSON.parse(read('package.json'));

assert.ok(
docsPackage.dependencies?.['panelui-web'],
'apps/docs must depend on panelui-web: its pages import that source, and Vercel installs from apps/docs'
);

// And the package says everything its source reaches for, so naming the package is enough.
const declared = new Set([
...Object.keys(webPackage.dependencies ?? {}),
...Object.keys(webPackage.peerDependencies ?? {}),
]);
const sources = fs
.readdirSync(path.join(web, 'src'), { recursive: true })
.filter((file) => /\.tsx?$/.test(String(file)));
for (const file of sources) {
const source = fs.readFileSync(path.join(web, 'src', String(file)), 'utf8');
for (const [, specifier] of source.matchAll(/from\s+['"]([^'".][^'"]*)['"]/g)) {
// `@scope/name/sub/path` and `name/sub/path` both belong to the package before the sub path.
const name = specifier.startsWith('@') ? specifier.split('/').slice(0, 2).join('/') : specifier.split('/')[0];
assert.ok(declared.has(name), `${file} imports ${specifier}, which packages/web/package.json does not declare`);
}
}
});
1 change: 1 addition & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading