Replace this description with a short summary of what this package does.
npm install my-packageimport { hello } from 'my-package'
hello('world') // => 'Hello, world!'The full API reference is generated from the source by TypeDoc and published to this project's GitHub Pages site.
| Tool | Role |
|---|---|
| tsdown | Build — ESM bundle + .d.ts declarations |
| TypeScript | Language |
| Biome | Linter & formatter |
| Vitest + coverage-v8 | Testing & coverage |
| publint + are-the-types-wrong | Package shape & types-resolution validation |
| TypeDoc | API reference generation |
| VitePress | Documentation site |
| Husky + lint-staged | Git hooks (pre-commit, pre-push) |
| commitlint | Commit message linting |
| semantic-release | Automated versioning, changelog & npm publish |
| GitHub Actions + Pages | CI, npm releases, docs hosting |
- Node.js ≥ 24 (pinned in
.nvmrc— runnvm useif you have nvm) - npm (ships with Node)
src/
index.ts # package entry — the public API
tests/ # Vitest tests
docs/ # VitePress site (+ protocols.md; generated api/ is gitignored)
dist/ # build output (gitignored)
| Script | Description |
|---|---|
npm run build |
Bundle to dist/ (ESM + .d.ts) with tsdown |
npm run check |
Lint + type-check — the everyday "is it OK?" command |
npm run fix |
Auto-fix everything fixable (Biome) |
npm run biome:check / biome:fix |
Biome lint/format only |
npm run verify |
Type-check only (tsc, no output) |
npm test |
Run tests in watch mode (Vitest) |
npm run coverage |
One-shot test run with a coverage report |
npm run check:package |
Validate the packed tarball with publint + attw |
npm run docs:dev |
Generate the API reference and start the docs dev server |
npm run docs:build |
Generate the API reference and build the docs site |
npm run docs:preview |
Preview the built docs site |
npm run docs:api |
Generate the API markdown only |
Biome handles linting and formatting in one tool, using the library preset (@side-xp/biome-config/biome.lib.json). The pre-commit hook runs lint-staged, which auto-formats staged files. npm run check additionally surfaces type errors.
Tests live in src/tests/ and run in the node environment. The pre-push hook runs the suite (vitest run) so failing tests can't be pushed. Coverage is report-only — npm run coverage prints the numbers and the CI posts a summary table on pull requests, but it never fails the build. (To test against the DOM, or to enforce coverage thresholds, see docs/protocols.md.)
@ is aliased to ./src for internal imports (source and tests):
import { hello } from '@/index'npm run build produces an ESM bundle plus type declarations in dist/. Only dist/ is published (see files in package.json). The prepack (build) and prepublishOnly (check:package) lifecycle scripts run automatically on publish, so a package that doesn't build or has a broken shape can never be released.
TypeDoc generates Markdown API docs from the source's TSDoc comments, and VitePress renders them into a site alongside hand-written guides. The generated docs/api/ is gitignored and rebuilt on every docs:* run and in CI.
This project enforces Conventional Commits via commitlint. The commit-msg hook rejects messages that don't follow:
<type>(<optional scope>): <short description>
Common types: feat, fix, chore, docs, test, refactor, perf, ci, build.
Why this matters:
semantic-releasereads the commit history to choose the next version. Afeatis a minor bump, afixis a patch, and aBREAKING CHANGE:footer is a major bump.
The GitHub Actions workflow (.github/workflows/ci.yml) has three jobs:
check— runs on every push to an integration branch and on every pull request: lint + types, tests (with a coverage comment on PRs), build, and package validation (publint + attw).release— on push tomain/masteraftercheckpasses:semantic-releasebumps the version, updates the changelog, publishes to npm, and cuts a GitHub Release.deploy-docs— afterrelease: builds the VitePress site and deploys it to GitHub Pages.