Repository navigation
Development Guide
Applies to the current
mainimplementation. Last source review: 2026-07-15.
This guide describes the repository's current npm-based workflow and the architectural boundaries expected of contributions.
- Node.js 24.11 or newer;
.nvmrctracks the Node 24 line. - npm, using the committed
package-lock.json. - Git.
- Optional for native download-engine work:
par2,unrar, and7zzonPATH. - Docker with the Compose plugin for production-image and container testing.
git clone https://github.com/TannerMidd/Nooklet.git
cd Nooklet
npm ci
cp .env.example .envPowerShell:
git clone https://github.com/TannerMidd/Nooklet.git
Set-Location Nooklet
npm ci
Copy-Item .env.example .envSet an independent AUTH_SECRET of at least 32 characters. Use a separate BOOTSTRAP_TOKEN when testing first-admin setup. Never commit .env, databases, local paths, queue payloads, or credentials.
Start the development server:
npm run devThe default development URL is http://localhost:42021.
| Command | Purpose |
|---|---|
npm run dev |
Start the Next.js development server on port 42021 |
npm run typecheck |
Run TypeScript without emitting output |
npm run lint |
Run ESLint across the repository |
npm test |
Run Vitest in the Node environment |
npm run build |
Build and sanitize the standalone production bundle |
npm run check |
Typecheck, lint, test, and build |
npm run db:generate |
Generate a Drizzle migration after a schema change |
npm run db:backup |
Create and verify a SQLite backup using .env
|
npm run account:recover -- --email ... |
Recover a locked-out account locally |
Source: package.json.
src/app/ routes, layouts, server actions, and API boundaries
src/components/ shared and feature UI
src/config/ navigation and project-level presentation configuration
src/lib/ database, framework, security, and integration foundations
src/modules/ domain commands, queries, repositories, adapters, and workflows
drizzle/ generated SQL migrations and snapshots
docs/ ADRs, behavior requirements, architecture notes, and Wiki source
scripts/ backup, recovery, and standalone-build utilities
See Architecture for current module ownership.
- Keep route handlers and server actions thin: authenticate, parse, authorize, delegate, and shape a user-safe result.
- Put multi-step behavior in the owning domain workflow rather than a screen component.
- Do not call raw vendor adapters from UI code.
- Prefer typed, task-shaped commands and queries over generic setting or proxy endpoints.
- Keep credentials server-side, encrypted at rest, masked in summaries, and absent from audit payloads.
- Validate environment, action, route, adapter input, and adapter output boundaries.
- Preserve normalized persistence and add indexes for new query predicates.
- Keep the supported one-container topology in mind; do not introduce an external runtime dependency without an explicit architecture decision.
The decision basis is ADR-0001, but current implementation should be checked because some older examples in that ADR have drifted. See Architecture Decisions.
For a new or materially changed workflow:
- Define validated input and explicit output/error types.
- Keep orchestration separate from adapter and persistence details when the flow has multiple phases.
- Authorize at the server boundary and enforce ownership again in repository/workflow queries.
- Add a wiring or behavior test that exercises phase ordering and failure propagation.
- Persist user-visible failure state when work continues asynchronously.
- Add audit or notification behavior for security-sensitive and operationally important outcomes.
- Update the behavior matrix and relevant Wiki pages when user-observable behavior changes.
Follow the closest existing module pattern rather than creating empty template directories.
- Change
src/lib/database/schema.ts. - Generate one logical migration with
npm run db:generate. - Inspect generated SQL and Drizzle metadata before committing.
- Add repository/query tests that read and write the new shape.
- Consider upgrade and rollback behavior for existing SQLite files.
- Keep migration and consumer commits separately reviewable when practical.
Never edit an already-published migration to represent a new logical change.
Ask these questions for every boundary change:
- Can a user read or mutate another user's row?
- Can a URL reach loopback, private, link-local, metadata, or redirected targets?
- Can a supplied path escape an approved root through
.., a symlink, or platform-specific syntax? - Can an error, log, audit payload, or browser response reveal a secret or protected download URL?
- Is a high-risk operation rate-limited?
- Does a background failure remain visible and retry safely?
Use the existing helpers under src/lib/security rather than implementing one-off checks.
git status --short
git diff --check
npm run typecheck
npm run lint
npm test
npm run buildRun the smallest relevant validation during iteration and the full proportional suite before handoff. Review the complete diff for secrets, generated noise, debug output, dead code, stale names, and unrelated changes. Use focused Conventional Commit subjects such as fix(downloads): ... or docs(wiki): ....
Implementation is not complete when operator behavior changes but the relevant documentation remains stale. Use Documentation Policy to identify the canonical page and source links to update.
Related: Testing and CI | Architecture | Security Model
Nooklet repository · Features · User guide · Engineering dossier · Issues · Private security advisory
Documentation last reviewed against main: August 19, 2026.
Nooklet
Start here
- Getting started
- Guided Docker setup
- Docker installation
- Native installation (advanced)
- First-time setup
Configure
Use Nooklet
- Discover and recommendations
- Library and requests
- YouTube monitoring
- Downloads and import
- Watch history
- Automation and notifications
Operate
- Health and diagnostics
- Backup, restore, upgrades
- Accounts and users
- Troubleshooting
- Multi-instance boundaries
Engineering