nestjs-boost 0.0.0-stage → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (87) hide show
  1. package/CHANGELOG.md +68 -0
  2. package/LICENSE +21 -0
  3. package/NOTICE.md +6 -0
  4. package/README.md +168 -2
  5. package/bin/nestjs-boost.mjs +148 -0
  6. package/guidelines/core.md +64 -0
  7. package/lib/agents.mjs +137 -0
  8. package/lib/installer.mjs +450 -0
  9. package/lib/prompt.mjs +131 -0
  10. package/lib/setup.mjs +60 -0
  11. package/manifest.json +676 -0
  12. package/package.json +67 -6
  13. package/scripts/postinstall.mjs +49 -0
  14. package/skills/nestjs-ai/SKILL.md +145 -0
  15. package/skills/nestjs-ai/references/ai-reference.md +143 -0
  16. package/skills/nestjs-architecture/SKILL.md +83 -0
  17. package/skills/nestjs-architecture/references/dynamic-modules.md +92 -0
  18. package/skills/nestjs-architecture/references/scopes-lifecycle.md +98 -0
  19. package/skills/nestjs-architecture/references/troubleshooting.md +77 -0
  20. package/skills/nestjs-authentication/SKILL.md +115 -0
  21. package/skills/nestjs-authentication/references/flows.md +180 -0
  22. package/skills/nestjs-authorization/SKILL.md +104 -0
  23. package/skills/nestjs-caching/SKILL.md +109 -0
  24. package/skills/nestjs-cli-tooling/SKILL.md +94 -0
  25. package/skills/nestjs-cli-tooling/references/nest-cli-json.md +91 -0
  26. package/skills/nestjs-configuration/SKILL.md +109 -0
  27. package/skills/nestjs-cqrs/SKILL.md +124 -0
  28. package/skills/nestjs-database-drizzle/SKILL.md +117 -0
  29. package/skills/nestjs-database-mikro-orm/SKILL.md +109 -0
  30. package/skills/nestjs-database-mongoose/SKILL.md +124 -0
  31. package/skills/nestjs-database-prisma/SKILL.md +126 -0
  32. package/skills/nestjs-database-sequelize/SKILL.md +88 -0
  33. package/skills/nestjs-database-typeorm/SKILL.md +110 -0
  34. package/skills/nestjs-deployment/SKILL.md +133 -0
  35. package/skills/nestjs-deployment/references/serverless-and-systemd.md +133 -0
  36. package/skills/nestjs-events/SKILL.md +78 -0
  37. package/skills/nestjs-file-storage/SKILL.md +111 -0
  38. package/skills/nestjs-file-storage/references/storage-reference.md +82 -0
  39. package/skills/nestjs-graphql/SKILL.md +119 -0
  40. package/skills/nestjs-graphql/references/federation.md +110 -0
  41. package/skills/nestjs-graphql/references/schema-features.md +133 -0
  42. package/skills/nestjs-health-checks/SKILL.md +114 -0
  43. package/skills/nestjs-http-client/SKILL.md +118 -0
  44. package/skills/nestjs-http-client/references/http-client-reference.md +116 -0
  45. package/skills/nestjs-http-platform/SKILL.md +104 -0
  46. package/skills/nestjs-http-platform/references/adapters.md +88 -0
  47. package/skills/nestjs-http-web-features/SKILL.md +113 -0
  48. package/skills/nestjs-http-web-features/references/uploads-streaming.md +108 -0
  49. package/skills/nestjs-i18n/SKILL.md +113 -0
  50. package/skills/nestjs-idempotency/SKILL.md +112 -0
  51. package/skills/nestjs-locks/SKILL.md +108 -0
  52. package/skills/nestjs-logging/SKILL.md +123 -0
  53. package/skills/nestjs-mail/SKILL.md +125 -0
  54. package/skills/nestjs-mail/references/mail-reference.md +90 -0
  55. package/skills/nestjs-mcp-server/SKILL.md +152 -0
  56. package/skills/nestjs-mcp-server/references/mcp-reference.md +146 -0
  57. package/skills/nestjs-microservices/SKILL.md +108 -0
  58. package/skills/nestjs-microservices/references/transports.md +117 -0
  59. package/skills/nestjs-observability/SKILL.md +108 -0
  60. package/skills/nestjs-observability/references/apm-and-otel.md +106 -0
  61. package/skills/nestjs-openapi/SKILL.md +90 -0
  62. package/skills/nestjs-openapi/references/swagger-reference.md +180 -0
  63. package/skills/nestjs-outbox/SKILL.md +119 -0
  64. package/skills/nestjs-outbox/references/outbox-reference.md +74 -0
  65. package/skills/nestjs-passport-auth/SKILL.md +125 -0
  66. package/skills/nestjs-queues/SKILL.md +118 -0
  67. package/skills/nestjs-queues/references/bull-legacy.md +75 -0
  68. package/skills/nestjs-request-pipeline/SKILL.md +146 -0
  69. package/skills/nestjs-request-pipeline/references/filters-interceptors.md +114 -0
  70. package/skills/nestjs-request-pipeline/references/pipes-decorators.md +80 -0
  71. package/skills/nestjs-resilience/SKILL.md +116 -0
  72. package/skills/nestjs-resilience/references/resilience-reference.md +74 -0
  73. package/skills/nestjs-scheduling/SKILL.md +100 -0
  74. package/skills/nestjs-security-hardening/SKILL.md +99 -0
  75. package/skills/nestjs-security-hardening/references/throttler-advanced.md +78 -0
  76. package/skills/nestjs-standalone-apps/SKILL.md +78 -0
  77. package/skills/nestjs-testing/SKILL.md +118 -0
  78. package/skills/nestjs-testing/references/advanced-testing.md +62 -0
  79. package/skills/nestjs-upgrading/SKILL.md +82 -0
  80. package/skills/nestjs-upgrading/references/esm-switch.md +114 -0
  81. package/skills/nestjs-validation-serialization/SKILL.md +124 -0
  82. package/skills/nestjs-validation-serialization/references/validation-options.md +84 -0
  83. package/skills/nestjs-webhooks/SKILL.md +116 -0
  84. package/skills/nestjs-webhooks/references/webhooks-reference.md +132 -0
  85. package/skills/nestjs-websockets/SKILL.md +108 -0
  86. package/skills/nestjs-workflows/SKILL.md +123 -0
  87. package/skills/nestjs-workflows/references/workflows-reference.md +85 -0
package/CHANGELOG.md ADDED
@@ -0,0 +1,68 @@
1
+ # Changelog
2
+
3
+ ## 1.2.0 — 2026-11-08
4
+
5
+ First release after the package was republished (versions 1.0.0 and 1.1.0 can't be reused on npm). It includes everything below.
6
+
7
+ ### Repository security
8
+ - `SECURITY.md` with private vulnerability reporting, CodeQL code scanning (JavaScript and workflows), Dependabot updates for the pinned Actions, `CODEOWNERS`, and LF line endings via `.gitattributes`.
9
+
10
+ ### Added
11
+ - **Interactive setup.** `npx nestjs-boost install` asks which AI coding agents you use (detected ones pre-selected), shows the plan (skills, folders, which agents read each folder, instructions files, change counts) and installs after you confirm. The choice is saved in the lock file and reused by later runs and `npm install`.
12
+ - **Seven more agents:** Gemini CLI, Windsurf, Cline, Roo Code, Kiro, JetBrains Junie and OpenCode, alongside Claude Code, OpenAI Codex, GitHub Copilot and Cursor. Each installs into the skills folder its own docs specify, with the guidelines block in its instructions file (`CLAUDE.md`, `AGENTS.md`, `GEMINI.md` or `.github/copilot-instructions.md`).
13
+ - **Shared folders without duplicates:** with several agents selected, each skill is installed once into the folders that cover all of them (for example Claude Code + Cursor + Copilot share `.claude/skills/`).
14
+ - `nestjs-boost agents` lists the supported agents and their folders. `-y` / `--yes` skips all questions.
15
+ - Agent registry in `lib/agents.mjs`: adding an agent is one entry (see CONTRIBUTING.md).
16
+
17
+ ### Changed
18
+ - **Install paths for Cursor and Copilot on their own:** selected alone (or without an agent that shares a folder with them), Cursor now uses `.cursor/skills/` and Copilot `.github/skills/`, their native folders, instead of `.agents/skills/`. The next sync moves the skills there and removes the old copies unless you edited them. With Claude Code or Codex also selected, nothing moves.
19
+ - Deselecting an agent now also removes the guidelines block from its instructions file (and the file, if nestjs-boost created it and nothing else is left).
20
+ - Install output groups skill changes per folder.
21
+ - `install` never prompts in CI, with piped output, with `--yes`/`--agents`, or when `agents` is set in config, so scripted runs behave as before.
22
+
23
+ ### Security
24
+ - **Lock file entries are validated.** Only skill folders under `.claude/skills/` / `.agents/skills/` and the known guideline files are honoured. Before this, a crafted `.ai/nestjs-boost.lock.json` could make `install` (and so `npm install`) delete any project folder whose hash it listed, and `uninstall --force` could target the project root.
25
+ - **Symbolic links are never followed.** Writes and deletes refuse a link anywhere on the path. Links inside skill folders, `.ai/skills/` and `.ai/guidelines/` are skipped when hashing, copying or reading, so link loops and device files can't hang an install.
26
+ - **Postinstall is opt-in and refresh-only.** It syncs only when the project has a lock file or a `"nestjs-boost"` config key, only when `nestjs-boost` is a direct dependency, and never under `npx`. Installing the package no longer adds agent instructions on its own; run `npx nestjs-boost install` once.
27
+ - Block markers are stripped from project-supplied guideline text and skill descriptions, so they can't shift the managed block over user content.
28
+ - Custom skill names in `.ai/skills/` must be lowercase-with-hyphens.
29
+ - `scripts/validate.mjs` now runs on Windows. Before, it exited 0 without validating, which skipped the `npm test` / `prepublishOnly` gate there.
30
+ - Release workflow: actions pinned to commit SHAs, npm pinned instead of `@latest`, publish job runs in an `npm-publish` environment, and the tag must match `package.json` and `manifest.json`.
31
+ - `nestjs-openapi`: the Fastify helmet CSP example for Swagger UI now applies only when docs are enabled and no longer allows bare `https:` scripts.
32
+
33
+ ### Fixed
34
+ - `manifest.json` version now follows `package.json` (it was `0.1.0`), and the validator checks they match.
35
+
36
+ ## 0.2.0 — 2026-11-06
37
+
38
+ ### npm package
39
+ - `npm install -D nestjs-boost` installs the matching skills through a `postinstall` hook. The hook never fails an install, skips in CI (`NESTJS_BOOST_CI=1` opts in) and with `NESTJS_BOOST_SKIP=1`, and re-syncs on every install.
40
+ - Hash-protected sync: skill folders you edited are never overwritten or deleted without `--force`, and skills for removed packages are pruned.
41
+ - Agent detection from repository files; the default is Claude Code + Codex, which covers all four agents.
42
+ - Config through a `"nestjs-boost"` key in `package.json` or `.ai/nestjs-boost.json`.
43
+ - CLI: `install`, `list`, `uninstall`, plus `--dry-run`, `--force`, `--no-guidelines`, `--version`.
44
+ - Zero dependencies, Node 20.19+, 18 tests (`node:test`), a Node skill validator run before publish, and CI plus trusted-publishing release workflows.
45
+ - Per-skill evals moved from `skills/*/evals/` to `evals/skills/`, so they're no longer shipped or installed.
46
+
47
+ ### Skills
48
+
49
+ - All **45 skills** written: 8 foundation + 37 package/operational skills, with 29 reference files (74 Markdown files under `skills/`).
50
+ - Coverage: 159 documentation pages, every one owned by exactly one skill (or the core guidelines). All 136 requested URLs map to an owner (`coverage/requested-url-map.md`).
51
+ - New in this release:
52
+ - HTTP and auth: http-platform, http-web-features, openapi, webhooks, authentication, authorization, passport-auth
53
+ - Data: TypeORM, Drizzle, Mongoose, Prisma, MikroORM, Sequelize, caching
54
+ - Application packages: events, scheduling, queues, http-client, mail, i18n, file-storage, cqrs, standalone-apps
55
+ - Reliability: resilience, idempotency, outbox, workflows, locks, health-checks, observability
56
+ - APIs: graphql, websockets, microservices
57
+ - AI: mcp-server, ai
58
+ - Operations: deployment, upgrading
59
+ - Every skill passes `tools/validate_skills.py`, and every API claim was checked against the docs source.
60
+ - New tool: `tools/condense.py` (per-skill digest of owned pages, used to ground skill writing).
61
+ - Deferred: evals for the new skills, and the npm publish of the installer.
62
+
63
+ ## 0.1.0 — 2026-11-05
64
+
65
+ - First build, from docs.nestjs.com @ `05c1fdfac8cf` (2026-11-04, NestJS 12).
66
+ - Core guidelines template with detected project facts and a skill map.
67
+ - 8 foundation skills: architecture, request-pipeline, validation-serialization, configuration, testing, cli-tooling, logging, security-hardening.
68
+ - Installer prototype: `install` / `update` / `list`, with package-based skill selection, four agent targets, marker-based guideline blocks, `.ai/skills` and `.ai/guidelines` overrides, and a lock file.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 nestjs-boost contributors
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/NOTICE.md ADDED
@@ -0,0 +1,6 @@
1
+ # Notice
2
+
3
+ The skills in this package are distilled from the official NestJS documentation
4
+ (https://github.com/nestjs/docs.nestjs.com), Copyright (c) 2017-present Kamil Myśliwiec,
5
+ licensed under the MIT License. nestjs-boost is a community project and is not affiliated
6
+ with or endorsed by the NestJS team.
package/README.md CHANGED
@@ -1,3 +1,169 @@
1
- # Temporary Holding Version
1
+ # nestjs-boost
2
2
 
3
- This version is a temporary placeholder for this package. An operational version to replace this has been submitted for review and is awaiting a staged release.
3
+ Agent Skills and project guidelines for AI-assisted **NestJS 12** development, for Claude Code, GitHub Copilot, Cursor, OpenAI Codex, Gemini CLI, Windsurf, Cline, Roo Code, Kiro, JetBrains Junie and OpenCode.
4
+
5
+ Install it in a NestJS project. It detects which Nest packages you use, then copies in **only the skills you need**: 45 skills built from the official docs, covering everything from DI and testing to TypeORM, BullMQ, GraphQL, microservices, MCP and `@nestjs/ai`. It also adds a short guidelines block describing your project to each agent's instructions file (`CLAUDE.md`, `AGENTS.md`, `GEMINI.md`, ...).
6
+
7
+ ```bash
8
+ npm install -D nestjs-boost
9
+ npx nestjs-boost install
10
+ ```
11
+
12
+ `install` asks which agents you use, shows what it will write, and installs after you confirm:
13
+
14
+ ```text
15
+ ? Which AI coding agents do you use?
16
+ ↑/↓ move · space select · a all/none · enter confirm · esc cancel
17
+ ❯ ◉ Claude Code .claude/skills/ · CLAUDE.md
18
+ ◯ OpenAI Codex .agents/skills/ · AGENTS.md
19
+ ◯ GitHub Copilot .github/skills/ · .github/copilot-instructions.md
20
+ ◉ Cursor (detected) .cursor/skills/ · AGENTS.md
21
+ ◯ Gemini CLI .gemini/skills/ · GEMINI.md
22
+ ...
23
+
24
+ Skills: 14 skills (8 foundation, 6 for your packages)
25
+ .claude/skills/ read by Claude Code, Cursor
26
+ Guidelines block: CLAUDE.md, AGENTS.md
27
+ Changes: 16 new
28
+ ? Install now? (Y/n)
29
+ ```
30
+
31
+ Agents already used in the repo are detected and pre-selected. Your choice is saved in `.ai/nestjs-boost.lock.json`, so later runs and `npm install` reuse it. Run `npx nestjs-boost install` again whenever you want to change it.
32
+
33
+ The first `nestjs-boost install` is an explicit opt-in: installing the package alone never adds agent instructions to your project. After that, every `npm install` keeps the skills in sync.
34
+
35
+ Commit the skill folders, instruction files and `.ai/nestjs-boost.lock.json` so the whole team and CI agents get the same skills.
36
+
37
+ ## Supported agents
38
+
39
+ Every agent below supports the open [Agent Skills](https://agentskills.io) format (one `<name>/SKILL.md` folder per skill), so skills are copied unchanged into the folder that agent documents. Run `npx nestjs-boost agents` for the same table.
40
+
41
+ | Agent | `--agents` id | Skills folder | Guidelines block in |
42
+ | --- | --- | --- | --- |
43
+ | Claude Code | `claude-code` | `.claude/skills/` | `CLAUDE.md` |
44
+ | OpenAI Codex | `codex` | `.agents/skills/` | `AGENTS.md` |
45
+ | GitHub Copilot | `copilot` | `.github/skills/` | `.github/copilot-instructions.md` |
46
+ | Cursor | `cursor` | `.cursor/skills/` | `AGENTS.md` |
47
+ | Gemini CLI | `gemini` | `.gemini/skills/` | `GEMINI.md` |
48
+ | Windsurf | `windsurf` | `.windsurf/skills/` | `AGENTS.md` |
49
+ | Cline | `cline` | `.cline/skills/` | `AGENTS.md` |
50
+ | Roo Code | `roo` | `.roo/skills/` | `AGENTS.md` |
51
+ | Kiro | `kiro` | `.kiro/skills/` | `AGENTS.md` |
52
+ | JetBrains Junie | `junie` | `.junie/skills/` | `AGENTS.md` |
53
+ | OpenCode | `opencode` | `.opencode/skills/` | `AGENTS.md` |
54
+
55
+ **Shared folders.** Several agents also read other agents' folders. Cursor, Copilot and OpenCode read `.claude/skills/`; Gemini CLI, Roo Code, Cursor, Copilot and OpenCode read `.agents/skills/`. When you pick more than one agent, nestjs-boost installs each skill once into the folders that cover all of them, so no agent sees duplicates. For example, Claude Code + Cursor + Copilot share `.claude/skills/`. A single agent always gets its own folder. The install plan shows which agents read each folder.
56
+
57
+ Using another agent that supports Agent Skills and `AGENTS.md`? Pick **OpenAI Codex**: `.agents/skills/` + `AGENTS.md` is the cross-agent convention.
58
+
59
+ ## How it works
60
+
61
+ - **Selection:** the 8 foundation skills always install. Package skills install when their package is in `package.json` (for example `@nestjs/typeorm` → `nestjs-database-typeorm`). Monorepo `apps/*`, `libs/*` and `packages/*` are included. Run `npx nestjs-boost list` to see what was picked and why.
62
+ - **Agents:** you pick them in `install`. Without a terminal to ask in (CI, piped output, `--yes`, the `postinstall` hook), nestjs-boost uses, in order: `--agents`, the `agents` config, your last choice from the lock file, then agents detected from repo files (`.claude/`, `.cursor/`, `.gemini/`, `.windsurf/`, `AGENTS.md`, ...). If nothing applies, it uses Claude Code + Codex, whose folders most agents read.
63
+ - **Switching agents** removes what was installed for the agents you dropped: their skill folders, and the guidelines block in their instructions file. Files nestjs-boost created are deleted if nothing else is left in them. Folders you edited are kept.
64
+ - **Updates:** once the project has opted in (it has `.ai/nestjs-boost.lock.json` from a first `nestjs-boost install`, or a `"nestjs-boost"` key in `package.json`), every `npm install` / `npm ci` re-syncs the skills:
65
+ - New packages get their skills.
66
+ - Upgrading `nestjs-boost` refreshes the skill text.
67
+ - Skills for removed packages are deleted.
68
+ - **Your edits are safe.**
69
+ - A skill folder you changed is never overwritten or deleted. Changes are tracked by hash in the lock file.
70
+ - Text outside the `<!-- nestjs-boost:start/end -->` markers is never touched.
71
+ - It runs offline, has no dependencies, and writes only inside your project.
72
+
73
+ ## Package managers
74
+
75
+ After the first `nestjs-boost install`, a `postinstall` script keeps the skills in sync. It runs only when `nestjs-boost` is a direct dependency of the project, never under `npx`. Some setups don't run dependency scripts. In that case, run the CLI again after adding Nest packages:
76
+
77
+ ```bash
78
+ npx nestjs-boost install
79
+ ```
80
+
81
+ | Setup | What to do |
82
+ | --- | --- |
83
+ | npm 11 (warns about unapproved install scripts) | `npm install-scripts approve nestjs-boost` (adds it to `allowScripts`) |
84
+ | pnpm 10+ (blocks scripts by default) | `pnpm approve-builds`, or add `"pnpm": { "onlyBuiltDependencies": ["nestjs-boost"] }` |
85
+ | Bun | add `"trustedDependencies": ["nestjs-boost"]` |
86
+ | Yarn, npm ≤ 10 | nothing; scripts run |
87
+ | `--ignore-scripts` | run `npx nestjs-boost install` |
88
+ | CI (`CI` set) | skipped on purpose; set `NESTJS_BOOST_CI=1` to sync in CI |
89
+ | Opt out temporarily | `NESTJS_BOOST_SKIP=1 npm install` |
90
+
91
+ ## Commands
92
+
93
+ ```bash
94
+ npx nestjs-boost install # pick agents, review the plan, install (opts the project in)
95
+ npx nestjs-boost install --yes # no questions: reuse the last choice (scripts, CI)
96
+ npx nestjs-boost install --agents cursor,gemini # choose agents without the picker
97
+ npx nestjs-boost install --dry-run # show the plan
98
+ npx nestjs-boost install --force # also overwrite skills you edited
99
+ npx nestjs-boost list # detected facts + selected skills (writes nothing)
100
+ npx nestjs-boost agents # supported agents and their folders
101
+ npx nestjs-boost uninstall # remove skills, guideline blocks and the lock file
102
+ ```
103
+
104
+ Options: `--agents <ids>` (see [Supported agents](#supported-agents)), `-y, --yes`, `--include <skills>`, `--exclude <skills>`, `--all`, `--no-guidelines`, `--root <dir>`.
105
+
106
+ The picker appears only in an interactive terminal. It never appears in CI (`CI` set), when output is piped, with `--yes` or `--agents`, or when `agents` is set in config. Those runs never wait for input.
107
+
108
+ ## Configuration
109
+
110
+ Settings persist in `package.json`, and the postinstall step uses them too. Adding this key also opts the project in to syncing on `npm install`, even before the first `nestjs-boost install`:
111
+
112
+ ```json
113
+ {
114
+ "nestjs-boost": {
115
+ "agents": ["claude-code"],
116
+ "include": ["nestjs-deployment", "nestjs-upgrading"],
117
+ "exclude": ["nestjs-passport-auth"],
118
+ "guidelines": true
119
+ }
120
+ }
121
+ ```
122
+
123
+ You can put the same object in `.ai/nestjs-boost.json` instead. CLI flags override both. When `agents` is set here, `install` uses it and doesn't show the picker. Leave it out to choose interactively.
124
+
125
+ ## Customizing
126
+
127
+ | Want to… | Do this |
128
+ | --- | --- |
129
+ | Change a pack skill for your team | Copy it to `.ai/skills/<skill-name>/` and edit it. Your version replaces the pack's on every sync |
130
+ | Add your own skill | Create `.ai/skills/<new-name>/SKILL.md`. It's installed and listed in the guidelines skill map |
131
+ | Add project rules to the guidelines | Add `.ai/guidelines/*.md`. These files are appended to the guidelines block |
132
+
133
+ ## Skills
134
+
135
+ | Area | Skills |
136
+ | --- | --- |
137
+ | **Foundation** (always) | `nestjs-architecture`, `nestjs-request-pipeline`, `nestjs-validation-serialization`, `nestjs-configuration`, `nestjs-testing`, `nestjs-cli-tooling`, `nestjs-logging`, `nestjs-security-hardening` |
138
+ | HTTP and API | `nestjs-http-platform`, `nestjs-http-web-features`, `nestjs-openapi`, `nestjs-graphql`, `nestjs-websockets`, `nestjs-webhooks` |
139
+ | Auth | `nestjs-authentication`, `nestjs-authorization`, `nestjs-passport-auth` |
140
+ | Data | `nestjs-database-typeorm`, `nestjs-database-drizzle`, `nestjs-database-prisma`, `nestjs-database-mongoose`, `nestjs-database-mikro-orm`, `nestjs-database-sequelize`, `nestjs-caching` |
141
+ | Application | `nestjs-events`, `nestjs-scheduling`, `nestjs-queues`, `nestjs-http-client`, `nestjs-mail`, `nestjs-i18n`, `nestjs-file-storage`, `nestjs-cqrs`, `nestjs-standalone-apps`, `nestjs-microservices` |
142
+ | Reliability and ops | `nestjs-resilience`, `nestjs-idempotency`, `nestjs-outbox`, `nestjs-workflows`, `nestjs-locks`, `nestjs-health-checks`, `nestjs-observability`, `nestjs-deployment`, `nestjs-upgrading` |
143
+ | AI | `nestjs-mcp-server`, `nestjs-ai` |
144
+
145
+ `nestjs-standalone-apps`, `nestjs-deployment` and `nestjs-upgrading` install only when their condition is met (`nest-commander`, a `Dockerfile`/`serverless.yml`, NestJS < 12) or when you `include` them.
146
+
147
+ ## Requirements
148
+
149
+ - NestJS 12 projects. On older majors, the `list` command points you to `nestjs-upgrading`.
150
+ - Node.js 20.19+.
151
+
152
+ ## Security
153
+
154
+ The package has no dependencies and makes no network calls. It reads `package.json`, lockfile names, `nest-cli.json` and `.ai/`, and writes only the paths shown above, inside the project root. The install script never fails your install, and it never writes to a project that hasn't opted in. Source and skills are plain text you can review in `node_modules/nestjs-boost`.
155
+
156
+ Hardening against a hostile repository or a tampered lock file:
157
+
158
+ - **Lock file entries are not trusted.** Only `<agent skills folder>/<name>` folders (the folders in [Supported agents](#supported-agents)) and the agents' instructions files are honoured. Any other entry is ignored with a warning, so a lock file can't be used to delete other project files, even with `--force`.
159
+ - **Symbolic links are never followed.** A link or junction on any path nestjs-boost writes to or deletes (for example a symlinked `.claude/`) stops the sync with an error. Links inside skill folders, `.ai/skills/` and `.ai/guidelines/` are skipped, never copied or read.
160
+ - **The guideline block can't be hijacked.** Marker comments inside `.ai/guidelines/*.md` or a custom skill's description are stripped, so text outside the block stays yours.
161
+
162
+ Report vulnerabilities privately through GitHub security advisories, not public issues.
163
+
164
+ ## License
165
+
166
+ MIT. The skills are distilled from the [NestJS documentation](https://github.com/nestjs/docs.nestjs.com) (MIT); see `NOTICE.md`. This is a community project, not affiliated with the NestJS team.
167
+
168
+ ## Credits
169
+ The NestJS team, with appreciation + love for their clean and clear documentation (https://github.com/nestjs/docs.nestjs.com).
@@ -0,0 +1,148 @@
1
+ #!/usr/bin/env node
2
+ import { realpathSync } from 'node:fs';
3
+ import { resolve } from 'node:path';
4
+ import { fileURLToPath } from 'node:url';
5
+ import { AGENT_IDS, AGENT_LIST, BoostError, DEFAULT_AGENTS, MANIFEST, PACK_VERSION, sync, uninstall } from '../lib/installer.mjs';
6
+ import { PromptCancelled, canPrompt } from '../lib/prompt.mjs';
7
+ import { interactiveInstall } from '../lib/setup.mjs';
8
+
9
+ const HELP = `nestjs-boost ${PACK_VERSION}: Agent Skills for NestJS ${MANIFEST.nestjs.targetMajor}
10
+
11
+ Usage: nestjs-boost <command> [options]
12
+
13
+ Commands:
14
+ install Choose your AI coding agents, then install or refresh skills and guidelines (default)
15
+ list Show detected facts and the skills that would be installed (writes nothing)
16
+ agents Show the supported agents and where each one reads skills
17
+ uninstall Remove installed skills, guideline blocks and the lock file
18
+
19
+ Options:
20
+ --agents <list> Skip the picker: ${AGENT_IDS.join(',')}
21
+ (default: last choice, else detected, else ${DEFAULT_AGENTS.join(',')})
22
+ -y, --yes Don't ask anything; use the last choice or detected agents
23
+ --include <list> Add skills whose packages aren't detected (e.g. nestjs-deployment)
24
+ --exclude <list> Skip skills
25
+ --all Install every skill
26
+ --no-guidelines Don't write the guidelines block into CLAUDE.md / AGENTS.md / ...
27
+ --force Overwrite or remove skill folders you edited
28
+ --dry-run Show the plan without writing
29
+ --root <dir> Project root (default: current directory)
30
+ -v, --version Print the version
31
+ -h, --help Print this help
32
+
33
+ \`install\` asks which agents you use when run in an interactive terminal. It never asks in CI,
34
+ when output is piped, with --yes or --agents, or when agents are set in config.
35
+
36
+ Config: a "nestjs-boost" key in package.json (or .ai/nestjs-boost.json) accepts
37
+ { "agents": [], "include": [], "exclude": [], "all": false, "guidelines": true }.`;
38
+
39
+ const COMMANDS = ['install', 'update', 'list', 'agents', 'uninstall'];
40
+
41
+ export function parseArgs(argv) {
42
+ const flags = new Set(['dry-run', 'all', 'force', 'help', 'version', 'no-guidelines', 'yes', 'no-interactive']);
43
+ const short = { '-h': 'help', '-v': 'version', '-y': 'yes' };
44
+ const args = { _: [] };
45
+ for (let i = 0; i < argv.length; i++) {
46
+ const a = argv[i];
47
+ if (short[a]) { args[short[a]] = true; continue; }
48
+ if (!a.startsWith('--')) { args._.push(a); continue; }
49
+ const [key, inline] = a.slice(2).split('=', 2);
50
+ if (flags.has(key)) args[key] = true;
51
+ else if (inline !== undefined) args[key] = inline;
52
+ else if (argv[i + 1] === undefined || argv[i + 1].startsWith('-')) throw new BoostError(`--${key} needs a value`);
53
+ else args[key] = argv[++i];
54
+ }
55
+ return args;
56
+ }
57
+
58
+ const SIGN = { add: '+', update: '~', remove: '-' };
59
+
60
+ // Skill-folder changes are grouped per folder ("+ .claude/skills/ 12 skills: a, b, c, …") so a
61
+ // full install stays readable; other changes (guideline files) are listed one per line.
62
+ export function formatChanges(changes) {
63
+ const groups = new Map();
64
+ const lines = [];
65
+ for (const c of changes) {
66
+ const m = c.path.match(/^(.+\/skills)\/([a-z0-9-]+)$/);
67
+ if (!m) { lines.push(` ${SIGN[c.action]} ${c.path}`); continue; }
68
+ const key = `${c.action} ${m[1]}`;
69
+ if (!groups.has(key)) groups.set(key, { action: c.action, dir: m[1], names: [] });
70
+ groups.get(key).names.push(m[2]);
71
+ }
72
+ const grouped = [...groups.values()].map(({ action, dir, names }) => {
73
+ const shown = names.slice(0, 4).join(', ') + (names.length > 4 ? ', …' : '');
74
+ return ` ${SIGN[action]} ${dir}/ ${names.length} skill${names.length === 1 ? '' : 's'}: ${shown}`;
75
+ });
76
+ return [...grouped, ...lines];
77
+ }
78
+
79
+ function printFacts({ facts, skills, custom, opts }) {
80
+ const target = MANIFEST.nestjs.targetMajor;
81
+ console.log(`nestjs-boost ${PACK_VERSION}: NestJS ${facts.coreVersion}${facts.nestMajor && facts.nestMajor !== target ? ` (skills target ${target}; see nestjs-upgrading)` : ''}`);
82
+ console.log(` ${facts.adapter} | ${facts.esm ? 'ESM' : 'CommonJS'} | tests: ${facts.testRunner} | lint: ${facts.linter} | ${facts.pm}${facts.monorepo ? ' | monorepo' : ''}`);
83
+ console.log(` agents: ${opts.agents.join(', ')} (${opts.agentSource})`);
84
+ console.log(`Skills (${skills.length}${custom.length ? ` + ${custom.length} project` : ''}):`);
85
+ for (const s of skills) console.log(` ${s.name.padEnd(34)} ${s.reason}`);
86
+ for (const n of custom) console.log(` ${n.padEnd(34)} .ai/skills (project)`);
87
+ }
88
+
89
+ function print(result, { verbose = true } = {}) {
90
+ const { facts, changes, warnings, dryRun } = result;
91
+ if (facts && verbose) printFacts(result);
92
+ if (changes.length) {
93
+ console.log(dryRun ? 'Would change:' : 'Changed:');
94
+ for (const line of formatChanges(changes)) console.log(line);
95
+ } else if (verbose) console.log(dryRun ? 'Nothing would change.' : 'Already up to date.');
96
+ for (const w of warnings) console.warn(` ! ${w}`);
97
+ }
98
+
99
+ function printAgents() {
100
+ const w = Math.max(...AGENT_LIST.map((a) => a.id.length)) + 2;
101
+ const n = Math.max(...AGENT_LIST.map((a) => a.name.length)) + 2;
102
+ console.log(`${'id'.padEnd(w)}${'agent'.padEnd(n)}${'skills folder'.padEnd(20)}instructions file`);
103
+ for (const a of AGENT_LIST) console.log(`${a.id.padEnd(w)}${a.name.padEnd(n)}${`${a.skills.dir}/`.padEnd(20)}${a.instructions}`);
104
+ console.log('\nWhen several agents read the same folder, skills are installed once and shared.');
105
+ }
106
+
107
+ export async function main(argv = process.argv.slice(2), io) {
108
+ const args = parseArgs(argv);
109
+ if (args.version) return console.log(PACK_VERSION);
110
+ const command = args._[0] ?? 'install';
111
+ if (args.help || !COMMANDS.includes(command)) {
112
+ console.log(HELP);
113
+ process.exitCode = args.help ? 0 : 2;
114
+ return;
115
+ }
116
+ if (command === 'agents') return printAgents();
117
+ const root = resolve(args.root ?? process.cwd());
118
+ const run = { dryRun: Boolean(args['dry-run']) || command === 'list', force: Boolean(args.force) };
119
+ if (command === 'uninstall') return print(uninstall(root, run));
120
+ const explicit = {
121
+ agents: args.agents, include: args.include, exclude: args.exclude,
122
+ all: args.all || undefined, guidelines: args['no-guidelines'] ? false : undefined,
123
+ };
124
+
125
+ const interactive = command !== 'list' && !run.dryRun && !args.yes && !args['no-interactive']
126
+ && args.agents === undefined && !process.env.CI && canPrompt(io);
127
+ if (!interactive) return print(sync(root, explicit, run));
128
+
129
+ const result = await interactiveInstall(root, explicit, run, io);
130
+ if (!result) { console.log('Nothing installed.'); return; }
131
+ if (!result.changes.length) { console.log('Already up to date.'); return; }
132
+ print(result, { verbose: false });
133
+ console.log('\nDone. Commit the files above and .ai/nestjs-boost.lock.json so your team gets the same skills.');
134
+ console.log('Run `npx nestjs-boost install` again any time to change agents.');
135
+ }
136
+
137
+ // Run only when executed as the CLI (directly, via npx or a node_modules/.bin link), not when
138
+ // imported by tests. Real paths, because bin links and Windows drive-letter case differ.
139
+ const invokedDirectly = () => {
140
+ try { return realpathSync(process.argv[1]) === realpathSync(fileURLToPath(import.meta.url)); } catch { return false; }
141
+ };
142
+ if (invokedDirectly()) {
143
+ main().catch((err) => {
144
+ if (err instanceof PromptCancelled) { console.log('\nCancelled; nothing was changed.'); process.exitCode = 130; return; }
145
+ console.error(`nestjs-boost: ${err instanceof BoostError ? err.message : err.stack}`);
146
+ process.exitCode = 1;
147
+ });
148
+ }
@@ -0,0 +1,64 @@
1
+ ## NestJS project guidelines (nestjs-boost)
2
+
3
+ This is a **NestJS {{nestjsVersion}}** project. Follow these rules on every task; load the skill named in the skill map for detail. The pack was built from the official docs at https://docs.nestjs.com (crawled {{docsCrawled}}). Where your training data disagrees with these files, these files win: NestJS 12 changed many defaults.
4
+
5
+ ### Project facts (detected)
6
+
7
+ | Fact | Value |
8
+ | --- | --- |
9
+ | HTTP adapter | {{httpAdapter}} |
10
+ | Module format | {{moduleFormat}} |
11
+ | Test runner | {{testRunner}} |
12
+ | Linter | {{linter}} |
13
+ | Package manager | {{packageManager}} |
14
+ | Validation | {{validation}} |
15
+
16
+ {{esmNote}}
17
+
18
+ ### Commands: verify before you report done
19
+
20
+ Run these after every change, and fix failures before saying a task is finished:
21
+
22
+ ```bash
23
+ {{buildCommand}}
24
+ {{lintCommand}}
25
+ {{testCommand}}
26
+ {{e2eCommand}}
27
+ ```
28
+
29
+ When a change affects startup (modules, DI, `main.ts`, configuration), also start the built app once (`{{startCommand}}`), because DI errors only appear at bootstrap, not at compile time.
30
+
31
+ ### Scaffold with the CLI, then edit
32
+
33
+ Use `nest generate` instead of writing boilerplate by hand. It places files where Nest expects them, updates the parent module, and adds spec files. Preview with `--dry-run`.
34
+
35
+ ```bash
36
+ npx nest g resource <name> # module + controller + service + DTOs + entity + specs
37
+ npx nest g module|controller|service|guard|interceptor|pipe|filter|decorator <name>
38
+ ```
39
+
40
+ ### Rules that apply everywhere
41
+
42
+ - **Feature modules.** Group each feature's controller, providers and DTOs in its own module. A provider another module needs must be in its module's `exports`, and the consumer must import that module. Never re-register another module's provider in your own `providers`: that creates a second instance. Avoid `@Global()` except for truly app-wide infrastructure.
43
+ - **Injection tokens exist at runtime.** Constructor injection by type needs a class. Interfaces and type aliases are erased, so inject those with `@Inject(TOKEN)`, using a string, symbol or `InjectionToken`.
44
+ - **No barrel files** (`index.ts`) for module and provider classes; they cause circular-dependency errors.
45
+ - **Request lifecycle order:**
46
+ 1. middleware
47
+ 2. guards (global → controller → route)
48
+ 3. interceptors before the handler
49
+ 4. pipes (global → controller → route → parameter)
50
+ 5. the handler
51
+ 6. interceptors after the handler (route → controller → global)
52
+ 7. exception filters (route → controller → global; the first matching filter wins)
53
+ - **Global enhancers that need DI** are registered as providers: `{ provide: APP_GUARD | APP_PIPE | APP_INTERCEPTOR | APP_FILTER, useClass: X }`. `app.useGlobal*()` in `main.ts` cannot inject dependencies, and tests that build the app with `Test.createTestingModule()` never run `main.ts`, so they miss it.
54
+ - **Errors:** throw Nest's HTTP exceptions (`NotFoundException`, `BadRequestException`, ...). Give clients a stable code with the `errorCode` option, e.g. `new BadRequestException('Cart is empty', { errorCode: 'CART_EMPTY' })`.
55
+ - **Logging:** use `new Logger(MyService.name)` from `@nestjs/common`, never `console.log`. Pass structured fields as a plain object after the message: `logger.log('User created', { userId })`.
56
+ - **Configuration and secrets** come from `@nestjs/config` (`ConfigService`), never hard-coded values or committed `.env` files.
57
+ - **Tests** use `@nestjs/testing` (`Test.createTestingModule`) with the project's runner API ({{testRunnerApi}}).
58
+ - **Upgrades:** after changing NestJS packages, use `nest upgrade`, which moves all `@nestjs/*` packages together.
59
+
60
+ ### Skill map
61
+
62
+ Load the matching skill before starting a task in its area:
63
+
64
+ {{skillMap}}
package/lib/agents.mjs ADDED
@@ -0,0 +1,137 @@
1
+ // Registry of supported AI coding agents. This is the only place that knows where each agent reads
2
+ // skills and project instructions; the installer, CLI picker, lock-file validation and docs all
3
+ // derive from it. To add an agent, add one entry (see CONTRIBUTING.md → "Adding an agent").
4
+ //
5
+ // Every agent here supports the open Agent Skills format (a `<name>/SKILL.md` folder per skill),
6
+ // so skills are copied unchanged; only the location differs.
7
+ //
8
+ // Fields:
9
+ // id stable key used in --agents, config and the lock file (never rename one)
10
+ // name display name in the picker
11
+ // skills.dir the agent's native project skills folder (its documented, recommended location)
12
+ // skills.reads every project skills folder the agent loads, native first. Used to avoid
13
+ // installing the same skills twice when several agents share a folder.
14
+ // instructions the always-loaded project instructions file the guidelines block goes into
15
+ // markers files/folders whose presence means the project already uses this agent
16
+ // docs where the conventions above are documented
17
+ export const AGENT_LIST = [
18
+ {
19
+ id: 'claude-code',
20
+ name: 'Claude Code',
21
+ skills: { dir: '.claude/skills', reads: ['.claude/skills'] },
22
+ instructions: 'CLAUDE.md',
23
+ markers: ['.claude', 'CLAUDE.md'],
24
+ docs: 'https://code.claude.com/docs/en/skills',
25
+ },
26
+ {
27
+ id: 'codex',
28
+ name: 'OpenAI Codex',
29
+ hint: 'also any tool using .agents/skills + AGENTS.md',
30
+ skills: { dir: '.agents/skills', reads: ['.agents/skills'] },
31
+ instructions: 'AGENTS.md',
32
+ markers: ['.codex', '.agents', 'AGENTS.md'],
33
+ docs: 'https://developers.openai.com/codex/skills',
34
+ },
35
+ {
36
+ id: 'copilot',
37
+ name: 'GitHub Copilot',
38
+ skills: { dir: '.github/skills', reads: ['.github/skills', '.claude/skills', '.agents/skills'] },
39
+ instructions: '.github/copilot-instructions.md',
40
+ markers: ['.github/copilot-instructions.md', '.github/instructions', '.github/skills'],
41
+ docs: 'https://docs.github.com/en/copilot/how-tos/use-copilot-agents/cloud-agent/create-skills',
42
+ },
43
+ {
44
+ id: 'cursor',
45
+ name: 'Cursor',
46
+ skills: { dir: '.cursor/skills', reads: ['.cursor/skills', '.agents/skills', '.claude/skills', '.codex/skills'] },
47
+ instructions: 'AGENTS.md',
48
+ markers: ['.cursor', '.cursorrules'],
49
+ docs: 'https://cursor.com/docs/skills',
50
+ },
51
+ {
52
+ id: 'gemini',
53
+ name: 'Gemini CLI',
54
+ skills: { dir: '.gemini/skills', reads: ['.gemini/skills', '.agents/skills'] },
55
+ instructions: 'GEMINI.md',
56
+ markers: ['.gemini', 'GEMINI.md'],
57
+ docs: 'https://geminicli.com/docs/cli/creating-skills',
58
+ },
59
+ {
60
+ id: 'windsurf',
61
+ name: 'Windsurf',
62
+ skills: { dir: '.windsurf/skills', reads: ['.windsurf/skills'] },
63
+ instructions: 'AGENTS.md',
64
+ markers: ['.windsurf', '.windsurfrules'],
65
+ docs: 'https://docs.windsurf.com/windsurf/cascade/skills',
66
+ },
67
+ {
68
+ id: 'cline',
69
+ name: 'Cline',
70
+ skills: { dir: '.cline/skills', reads: ['.cline/skills'] },
71
+ instructions: 'AGENTS.md',
72
+ markers: ['.cline', '.clinerules'],
73
+ docs: 'https://docs.cline.bot/customization/skills',
74
+ },
75
+ {
76
+ id: 'roo',
77
+ name: 'Roo Code',
78
+ skills: { dir: '.roo/skills', reads: ['.roo/skills', '.agents/skills'] },
79
+ instructions: 'AGENTS.md',
80
+ markers: ['.roo', '.roorules'],
81
+ docs: 'https://docs.roocode.com/features/skills',
82
+ },
83
+ {
84
+ id: 'kiro',
85
+ name: 'Kiro',
86
+ skills: { dir: '.kiro/skills', reads: ['.kiro/skills'] },
87
+ instructions: 'AGENTS.md',
88
+ markers: ['.kiro'],
89
+ docs: 'https://kiro.dev/docs/skills/',
90
+ },
91
+ {
92
+ id: 'junie',
93
+ name: 'JetBrains Junie',
94
+ skills: { dir: '.junie/skills', reads: ['.junie/skills'] },
95
+ instructions: 'AGENTS.md',
96
+ markers: ['.junie'],
97
+ docs: 'https://junie.jetbrains.com/docs/agent-skills.html',
98
+ },
99
+ {
100
+ id: 'opencode',
101
+ name: 'OpenCode',
102
+ skills: { dir: '.opencode/skills', reads: ['.opencode/skills', '.claude/skills', '.agents/skills'] },
103
+ instructions: 'AGENTS.md',
104
+ markers: ['.opencode', 'opencode.json', 'opencode.jsonc'],
105
+ docs: 'https://opencode.ai/docs/skills',
106
+ },
107
+ ];
108
+
109
+ export const AGENTS = Object.fromEntries(AGENT_LIST.map((a) => [a.id, a]));
110
+ export const AGENT_IDS = AGENT_LIST.map((a) => a.id);
111
+
112
+ // Used when nothing is detected and no one is asked (postinstall, CI, non-interactive shells).
113
+ // Between them, .claude/skills and .agents/skills are read by most agents in the registry.
114
+ export const DEFAULT_AGENTS = ['claude-code', 'codex'];
115
+
116
+ // Every folder any agent loads skills from, and every instructions file: the only places
117
+ // nestjs-boost may ever write. The lock-file allowlist is built from these.
118
+ export const ALL_SKILL_DIRS = [...new Set(AGENT_LIST.flatMap((a) => a.skills.reads))];
119
+ export const ALL_INSTRUCTION_FILES = [...new Set(AGENT_LIST.map((a) => a.instructions))];
120
+
121
+ // Choose the fewest skills folders that every selected agent reads, so no agent sees each skill
122
+ // twice. Agents that read the fewest folders choose first (they have no alternative); an agent
123
+ // whose folders already include a chosen one is covered. A single agent always gets its native
124
+ // folder. Deterministic: the same selection always gives the same folders.
125
+ export function planSkillDirs(agentIds) {
126
+ const agents = agentIds.map((id) => AGENTS[id]);
127
+ const order = [...agents].sort((a, b) => a.skills.reads.length - b.skills.reads.length
128
+ || AGENT_IDS.indexOf(a.id) - AGENT_IDS.indexOf(b.id));
129
+ const dirs = [];
130
+ for (const a of order) {
131
+ if (!a.skills.reads.some((d) => dirs.includes(d))) dirs.push(a.skills.dir);
132
+ }
133
+ // Report which agents read each chosen folder (for the plan shown to the user).
134
+ return dirs.map((dir) => ({ dir, agents: agents.filter((a) => a.skills.reads.includes(dir)).map((a) => a.id) }));
135
+ }
136
+
137
+ export const instructionFiles = (agentIds) => [...new Set(agentIds.map((id) => AGENTS[id].instructions))];