Review README.md and CONTRIBUTING.md for all relevant repository information.
- Use
npm installto install dependencies. - Use
npm run devto start the local development server (runsprebuildautomatically). - Use
npm run buildto produce a production build (also runsprebuildautomatically). - Do not edit files in
build/; it is compiled output. - The
scripts/prebuild.jsscript must run before the dev server or build — it is wired intopredev/prebuildhooks, so callingnpm run devornpm run buildis sufficient.
- TypeScript (config files and scripts), MDX/Markdown (content).
- Prettier is configured via
@harperfast/code-guidelines/prettier(seepackage.json). - Required before every commit/PR: run
npm run format:write, then confirmnpm run format:checkis clean. This is a hard gate, not advisory — CI fails any unformatted PR (see CI). - Formatting applies to every file in the repo, not just content. Prettier runs against the whole tree (
prettier .) —.ts,.md,.mdx,.json, and files underplans/,scripts/, etc. Do not assume a directory is exempt because it is not user-facing docs. - The lint script is a no-op (
echo 0); do not expectnpm run lintto catch issues.
Prefer plain ASCII characters in Markdown unless a typographic character is genuinely needed for meaning. This keeps content searchable, easy to type, and consistent with the rest of the docs.
-
Separators between fields — use a regular hyphen with spaces (
-), not bullet characters (•,·) or HTML entities ( ). ForType:/Default:reference blocks, put each on its own line separated by a blank line (the established pattern inreference/logging/configuration.md,reference/http/configuration.md, etc.):### `some.option` Type: `boolean` Default: `false` Description text here.
-
Type annotations — use the form
`<type>` (<modifier>)when a hint is useful, e.g.`string` (duration),`number` (ratio). Do not invent compound type names like`duration string`. -
Hyphens vs. dashes — em dashes (
—) are fine for parenthetical asides and match existing prose; do not use them as field separators. Do not use en dashes (–) except for numeric ranges like9229–9231. -
No HTML entities for whitespace — let Markdown / Prettier handle spacing; never reach for
to force layout. -
Lists — use
-for bullets (Prettier's default) and avoid mixing with*or•. -
Emoji — only when the user explicitly requests it.
- Content lives in four directories:
learn/,reference/,release-notes/, andfabric/. - Sidebar configs:
sidebarsLearn.ts,sidebarsReference.ts,sidebarsReleaseNotes.ts,sidebarsFabric.ts. - Reference is versioned; current version is v5 (
reference/). Archived v4 content is inreference_versioned_docs/version-v4/. - Do not modify
reference_versioned_docs/for current (v5) work; editreference/instead. - The
<VersionBadge>component is globally registered — no import needed in.md/.mdxfiles. - The
<EngineBadge>component (also global) tags storage-engine support inline:<EngineBadge engines="RocksDB" />or<EngineBadge engines="RocksDB, LMDB" />. - See the complete repository organization in
CONTRIBUTING.md
- Tag minor-version availability inline:
<VersionBadge version="vX.Y.0" />for new surface,<VersionBadge type="changed" version="vX.Y.0" />for behavior changes to existing surface. - Derive the version from the core release the change ships in, stripping prerelease suffixes (
5.1.0-beta.1→v5.1.0). - Determine that release from the core repo's git tags, not from the feature branch's
package.json. A branch reading5.2.0-beta.3says which release was open when the branch started, not which one the change lands in — if a release is cut before the feature merges, the badge is silently wrong. Checkgit tag --sort=-creatordatefor the newest release, andgit tag --contains <merge-commit>for whether the change is in one; a merged-but-untagged feature ships in the next version, which may be a minor bump. Re-check on every refresh pass of a long-lived docs PR, because a release cut between passes invalidates a badge that was correct when written. - Fetch tags and confirm the tag object before trusting the answer.
git tag --containsis only as good as the local tag it compares against: a stale or divergent tag of the same name gives a confidently wrong answer in either direction. Rungit fetch --tags, then checkgit rev-parse <tag>againstgit ls-remote --tags origin <tag>. When a badge is disputed, the decisive check is not--containsat all but whether the feature's files exist at the tag —git ls-tree -r --name-only <tag> | grep <path>, orgit show <tag>:<file>— since that cannot be confounded by ancestry or by which tag your clone happens to hold. - A patch release may or may not be cut from
main, so ancestry is not a reliable test. Roughly a third come offmainand the rest off a release branch such asv5.2, which carries selective cherry-picks. When a tag is cut from a release branch,git tag --contains <main-merge-sha>returns nothing for it by design —v5.2.5's commit is not an ancestor ofmainat all. So an empty--containsdoes not mean "unreleased", and a newer patch tag existing is not evidence against a next-minor badge. It tells you nothing either way until you know which kind of cut that tag was. - Cherry-picks defeat ancestry checks entirely, so test for the feature's files instead. A back-port creates a new commit SHA, so
git branch -r --contains <original-sha>andgit tag --containsboth stay empty even when the feature is present on the release branch — which would wrongly badge a back-ported feature as next-minor. Ask whether the code is there, not whether the commit is:git show <tag>:<path/to/feature/file>orgit ls-tree -r --name-only <tag> | grep <path>. When you need the commit rather than the file,git log --oneline --cherry-mark --left-right <tag>...mainmarks patch-equivalent commits with=;git cherry <tag> mainis the equivalent shorthand. Do not use--cherry-pickfor this — it omits equivalent commits from both sides, so a back-port is exactly what disappears from the output. - Compare commits, not tag objects. An annotated tag's own SHA differs from the commit it points at, so two people can cite
v5.2.5as different hashes and both be right. Use<tag>^{commit}. - Each minor release gets a file under
release-notes/<major-codename>/(e.g.release-notes/v5-lincoln/5.1.md); the sidebar picks it up automatically. - Absolute links from
release-notes/(orlearn/) into current reference docs use the versioned path/reference/v5/...— the reference plugin maps the current version to thev5URL path. - When documenting a change from a core/pro PR, cross-link the feature PR and the docs PR in both descriptions.
- There is no automated test suite. Verification is done by running the dev server or build.
npm run buildis the best end-to-end check — it will fail on broken links, missing imports, or MDX errors.npm run typecheckchecks TypeScript config files only.- Known issue:
npm run serve(post-build preview) 404s on paths like/docs/4.Xlocally due to an upstreamserve-handlerbug. This is not a real breakage — see CONTRIBUTING.md for details. - Run the commands a page documents before shipping them, against a throwaway Harper of the version the page targets. In a scratch directory,
npm install harper@<version>, then run that copy'snpx harper installandnpx harper startfrom the scratch directory — not a globalharper, which may be another version — withHOME,ROOTPATH,TC_AGREEMENT=yes,HDB_ADMIN_USERNAME,HDB_ADMIN_PASSWORD,OPERATIONSAPI_NETWORK_PORTandHTTP_PORTset to scratch values, and point the CLI at it withHARPER_CLI_TARGET.- Set
HOMEto a scratch directory on every command. Without it,harper installfinds the contributor's own~/.harperdb/hdb_boot_properties.fileand inspects that install, andharper loginwrites their~/.harperdb/credentials.json. - Harper core alone has no replication, so anything that replicates fails with
Replication not implemented, includingreplicated=true, and the job arestart=rollingdeploy starts when it only restarts (before v5.4.0, or when the deploy'scertificationisunavailable). Those paths need Harper Pro.
- Set
- CI runs
npm run buildandnpm run format:checkon pull requests. - If CI fails on formatting, run
npm run format:writelocally and commit the result.
- Issues are filed via the issue forms (blank issues are disabled). Each form sets an issue type: Bug (documented content is wrong/broken, or a site defect), Feature (new or expanded docs/site capability), or Task (smaller edits/cleanup, usually applied during triage).
- Area labels:
content(documentation text/examples) vsplatform(the docs site itself — build, search, navigation, styling). These are the only area labels; there are no per-subsystem labels. - Kind is captured by the issue type, not labels — do not reintroduce
bug/enhancementlabels. - Milestones:
v5.xrelease milestones, named to match theharper/harper-prorepos. Tag an issue with the milestone of the release whose docs it must ship with, so docs work is tracked per release. Do not delete the empty release milestones — they are the canonical per-release buckets. - See
CONTRIBUTING.md(Reporting Issues) for the contributor-facing version.