@ryuenn3123/agentic-senior-core 1.8.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 (78) hide show
  1. package/.agent-context/blueprints/api-nextjs.md +184 -0
  2. package/.agent-context/blueprints/aspnet-api.md +247 -0
  3. package/.agent-context/blueprints/ci-github-actions.md +226 -0
  4. package/.agent-context/blueprints/ci-gitlab.md +200 -0
  5. package/.agent-context/blueprints/fastapi-service.md +210 -0
  6. package/.agent-context/blueprints/go-service.md +217 -0
  7. package/.agent-context/blueprints/graphql-grpc-api.md +51 -0
  8. package/.agent-context/blueprints/infrastructure-as-code.md +62 -0
  9. package/.agent-context/blueprints/kubernetes-manifests.md +76 -0
  10. package/.agent-context/blueprints/laravel-api.md +223 -0
  11. package/.agent-context/blueprints/nestjs-logic.md +247 -0
  12. package/.agent-context/blueprints/observability.md +227 -0
  13. package/.agent-context/blueprints/spring-boot-api.md +218 -0
  14. package/.agent-context/policies/llm-judge-threshold.json +20 -0
  15. package/.agent-context/profiles/platform.md +13 -0
  16. package/.agent-context/profiles/regulated.md +13 -0
  17. package/.agent-context/profiles/startup.md +13 -0
  18. package/.agent-context/prompts/init-project.md +86 -0
  19. package/.agent-context/prompts/refactor.md +45 -0
  20. package/.agent-context/prompts/review-code.md +47 -0
  21. package/.agent-context/review-checklists/architecture-review.md +70 -0
  22. package/.agent-context/review-checklists/frontend-usability.md +33 -0
  23. package/.agent-context/review-checklists/performance-audit.md +65 -0
  24. package/.agent-context/review-checklists/pr-checklist.md +97 -0
  25. package/.agent-context/review-checklists/release-operations.md +29 -0
  26. package/.agent-context/review-checklists/security-audit.md +113 -0
  27. package/.agent-context/rules/api-docs.md +186 -0
  28. package/.agent-context/rules/architecture.md +198 -0
  29. package/.agent-context/rules/database-design.md +202 -0
  30. package/.agent-context/rules/efficiency-vs-hype.md +143 -0
  31. package/.agent-context/rules/error-handling.md +234 -0
  32. package/.agent-context/rules/event-driven.md +226 -0
  33. package/.agent-context/rules/frontend-architecture.md +66 -0
  34. package/.agent-context/rules/git-workflow.md +200 -0
  35. package/.agent-context/rules/microservices.md +174 -0
  36. package/.agent-context/rules/naming-conv.md +141 -0
  37. package/.agent-context/rules/performance.md +168 -0
  38. package/.agent-context/rules/realtime.md +47 -0
  39. package/.agent-context/rules/security.md +195 -0
  40. package/.agent-context/rules/testing.md +178 -0
  41. package/.agent-context/stacks/csharp.md +149 -0
  42. package/.agent-context/stacks/go.md +181 -0
  43. package/.agent-context/stacks/java.md +135 -0
  44. package/.agent-context/stacks/php.md +178 -0
  45. package/.agent-context/stacks/python.md +153 -0
  46. package/.agent-context/stacks/ruby.md +80 -0
  47. package/.agent-context/stacks/rust.md +86 -0
  48. package/.agent-context/stacks/typescript.md +317 -0
  49. package/.agent-context/state/architecture-map.md +25 -0
  50. package/.agent-context/state/dependency-map.md +32 -0
  51. package/.agent-override.md +36 -0
  52. package/.agents/workflows/init-project.md +29 -0
  53. package/.agents/workflows/refactor.md +29 -0
  54. package/.agents/workflows/review-code.md +29 -0
  55. package/.cursorrules +140 -0
  56. package/.gemini/instructions.md +97 -0
  57. package/.github/ISSUE_TEMPLATE/v1.7-frontend-work-item.yml +54 -0
  58. package/.github/copilot-instructions.md +104 -0
  59. package/.github/workflows/benchmark-detection.yml +38 -0
  60. package/.github/workflows/frontend-usability-gate.yml +36 -0
  61. package/.github/workflows/release-gate.yml +32 -0
  62. package/.github/workflows/sbom-compliance.yml +32 -0
  63. package/.windsurfrules +106 -0
  64. package/AGENTS.md +131 -0
  65. package/CONTRIBUTING.md +136 -0
  66. package/LICENSE +21 -0
  67. package/README.md +239 -0
  68. package/bin/agentic-senior-core.js +1147 -0
  69. package/mcp.json +29 -0
  70. package/package.json +50 -0
  71. package/scripts/detection-benchmark.mjs +138 -0
  72. package/scripts/frontend-usability-audit.mjs +87 -0
  73. package/scripts/generate-sbom.mjs +61 -0
  74. package/scripts/init-project.ps1 +105 -0
  75. package/scripts/init-project.sh +131 -0
  76. package/scripts/llm-judge.mjs +664 -0
  77. package/scripts/release-gate.mjs +116 -0
  78. package/scripts/validate.mjs +554 -0
@@ -0,0 +1,200 @@
1
+ # Git Workflow — Clean History, Atomic Commits
2
+
3
+ > Your git log is a changelog. If it reads like gibberish, your team is lost.
4
+
5
+ ## Commit Message Format: Conventional Commits (Enforced)
6
+
7
+ ```
8
+ <type>(<scope>): <description>
9
+
10
+ [optional body — explain WHY, not WHAT]
11
+ [optional footer — Breaking changes, issue references]
12
+ ```
13
+
14
+ ### Types (Strict Set)
15
+ | Type | When | Example |
16
+ |------|------|---------|
17
+ | `feat` | New feature | `feat(auth): add JWT refresh token rotation` |
18
+ | `fix` | Bug fix | `fix(payment): handle race condition in checkout` |
19
+ | `refactor` | Code restructuring (no behavior change) | `refactor(user): extract validation to separate service` |
20
+ | `docs` | Documentation only | `docs(api): add OpenAPI schema for /orders endpoint` |
21
+ | `test` | Adding/fixing tests | `test(cart): add edge case for empty cart discount` |
22
+ | `chore` | Build, CI, config, dependencies | `chore(deps): upgrade prisma to 5.x` |
23
+ | `perf` | Performance improvement | `perf(search): add index on users.email column` |
24
+ | `style` | Formatting, semicolons (no logic change) | `style: apply prettier formatting` |
25
+ | `ci` | CI/CD changes | `ci: add Node 20 to test matrix` |
26
+
27
+ ### Rules
28
+ 1. **Type is mandatory.** No commits without a type prefix.
29
+ 2. **Scope is recommended.** Use the module/feature name.
30
+ 3. **Description is imperative mood.** "add", not "added" or "adds".
31
+ 4. **Max 72 characters** for the subject line.
32
+ 5. **Body explains WHY,** not what. The diff shows what.
33
+
34
+ ### ❌ BANNED Commit Messages
35
+ ```
36
+ fix bug
37
+ updates
38
+ WIP
39
+ asdf
40
+ misc changes
41
+ working now
42
+ final fix
43
+ fix fix fix
44
+ ```
45
+
46
+ ---
47
+
48
+ ## Branching Model
49
+
50
+ ### Main Branches
51
+ | Branch | Purpose | Merge Strategy |
52
+ |--------|---------|---------------|
53
+ | `main` | Production-ready code | Merge commit or squash |
54
+ | `develop` | Integration branch (if using GitFlow) | Merge commit |
55
+
56
+ ### Feature Branches
57
+ ```
58
+ Pattern: <type>/<ticket-id>-<short-description>
59
+
60
+ Examples:
61
+ feat/AUTH-123-jwt-refresh
62
+ fix/PAY-456-checkout-race-condition
63
+ refactor/USER-789-extract-validation
64
+ chore/INFRA-101-upgrade-node-20
65
+ ```
66
+
67
+ ### Rules
68
+ 1. Branch from `main` (or `develop` if using GitFlow)
69
+ 2. Keep branches short-lived (max 2-3 days)
70
+ 3. Rebase on `main` before creating PR — don't merge main into your branch
71
+ 4. Delete branch after merge
72
+
73
+ ---
74
+
75
+ ## Pull Request Standards
76
+
77
+ ### PR Size
78
+ | Size | Lines Changed | Verdict |
79
+ |------|--------------|---------|
80
+ | Small | 1-100 | ✅ Ideal — easy to review |
81
+ | Medium | 100-300 | ⚠️ Acceptable — split if possible |
82
+ | Large | 300-500 | 🔶 Needs justification |
83
+ | Massive | 500+ | ❌ MUST be split into smaller PRs |
84
+
85
+ **Rule:** If a PR touches more than 5 files across different modules, it's doing too much. Split it.
86
+
87
+ ### PR Description Template
88
+ ```markdown
89
+ ## What
90
+ Brief description of what this PR does.
91
+
92
+ ## Why
93
+ Why this change is needed. Link to issue/ticket.
94
+
95
+ ## How
96
+ High-level approach. Mention any non-obvious design decisions.
97
+
98
+ ## Testing
99
+ - [ ] Unit tests added/updated
100
+ - [ ] Integration tests (if applicable)
101
+ - [ ] Manual testing steps
102
+
103
+ ## Screenshots (if UI change)
104
+ Before | After
105
+ ```
106
+
107
+ ### PR Review Rules
108
+ 1. Every PR needs at least 1 approval
109
+ 2. Author resolves all comments before merge
110
+ 3. CI must pass (lint, test, build)
111
+ 4. No `// TODO` without a linked issue
112
+ 5. No `console.log` debugging statements in production code
113
+
114
+ ---
115
+
116
+ ## Commit Atomicity
117
+
118
+ ### Rule: Each Commit Must Be a Complete, Working Unit
119
+
120
+ ```
121
+ ❌ BANNED sequence:
122
+ 1. feat(user): add user model ← compiles? maybe
123
+ 2. fix: fix import ← fixing previous commit
124
+ 3. feat(user): add user service ← compiles? probably
125
+ 4. fix: fix typo ← fixing previous commit
126
+ 5. feat(user): add user controller ← finally works together
127
+
128
+ ✅ REQUIRED:
129
+ 1. feat(user): add user registration module
130
+ → Model, Service, Controller, Tests — all in one complete, working commit
131
+ → Or split into logical chunks that each compile and pass tests independently
132
+ ```
133
+
134
+ **Rule:** Every commit on `main` should compile, pass lint, and pass tests. Use interactive rebase (`git rebase -i`) to squash fix-up commits before merging.
135
+
136
+ ---
137
+
138
+ ## .gitignore Standards
139
+
140
+ ### MUST Ignore
141
+ ```
142
+ # Dependencies
143
+ node_modules/
144
+ vendor/
145
+ venv/
146
+ __pycache__/
147
+ .gradle/
148
+ target/
149
+
150
+ # Environment
151
+ .env
152
+ .env.local
153
+ .env.*.local
154
+
155
+ # IDE
156
+ .idea/
157
+ .vscode/settings.json
158
+ *.swp
159
+ *.swo
160
+ .DS_Store
161
+ Thumbs.db
162
+
163
+ # Build output
164
+ dist/
165
+ build/
166
+ out/
167
+ *.min.js
168
+ *.min.css
169
+
170
+ # Logs
171
+ *.log
172
+ npm-debug.log*
173
+
174
+ # OS
175
+ .DS_Store
176
+ Thumbs.db
177
+ ```
178
+
179
+ ### MUST Commit
180
+ ```
181
+ .env.example # Template with placeholder values
182
+ .editorconfig # Consistent formatting across IDEs
183
+ .prettierrc # Formatter config
184
+ .eslintrc.* # Linter config
185
+ tsconfig.json # TypeScript config
186
+ docker-compose.yml # Dev environment
187
+ Makefile / Taskfile # Standard commands
188
+ ```
189
+
190
+ ---
191
+
192
+ ## The Git Health Check
193
+
194
+ Before pushing:
195
+ - [ ] All commits follow Conventional Commits format
196
+ - [ ] No fixup commits (squash them)
197
+ - [ ] Branch is rebased on latest main
198
+ - [ ] CI passes locally (lint, test, build)
199
+ - [ ] No secrets in any commit (check with `git log -p | grep -i "password\|secret\|key"`)
200
+ - [ ] No merge commits in feature branch (rebase instead)
@@ -0,0 +1,174 @@
1
+ # Microservices — When to Split, How to Split
2
+
3
+ > Don't start with microservices. Earn them through pain.
4
+ > A bad monolith becomes a distributed bad monolith faster than you think.
5
+
6
+ ## The Default: Modular Monolith
7
+
8
+ **Start with a modular monolith. Always.** Microservices are a scaling strategy, not a design philosophy.
9
+
10
+ A well-structured modular monolith can handle most applications indefinitely. Splitting prematurely creates distributed complexity without distributed benefits.
11
+
12
+ ---
13
+
14
+ ## The Split Decision Framework
15
+
16
+ ### Prerequisites (ALL Must Be True)
17
+
18
+ Before even considering microservices, these must exist:
19
+
20
+ 1. **Mature CI/CD pipeline** — automated testing, deployment, rollback
21
+ 2. **Observability in place** — distributed tracing, centralized logging, metrics
22
+ 3. **Team maturity** — team understands distributed systems failure modes
23
+ 4. **Clear module boundaries** — modules already communicate through interfaces, not internals
24
+
25
+ If any prerequisite is missing, **stop.** Fix the monolith first.
26
+
27
+ ### Trigger Conditions (2+ Required)
28
+
29
+ Split a module into a service ONLY when **2 or more** of these triggers exist:
30
+
31
+ | # | Trigger | Evidence |
32
+ |---|---------|----------|
33
+ | 1 | **Deploy conflicts** | Teams block each other on releases; merge queues exceed 24h |
34
+ | 2 | **Scale mismatch** | One module needs 50-100x resources of another |
35
+ | 3 | **Team ownership collision** | Multiple teams edit the same module weekly |
36
+ | 4 | **Fault isolation** | One module crashing must not kill the entire system |
37
+ | 5 | **Technology divergence** | Module genuinely requires a different runtime/language |
38
+ | 6 | **Compliance boundary** | Regulatory requirement to isolate data processing (PCI, HIPAA) |
39
+
40
+ ```
41
+ BANNED: "Let's use microservices because Netflix does"
42
+ BANNED: "We might need to scale later"
43
+ BANNED: "It's more modern"
44
+ BANNED: "Each developer gets their own service"
45
+ ```
46
+
47
+ ---
48
+
49
+ ## How to Split (The Extraction Protocol)
50
+
51
+ ### Step 1: Identify the Seam
52
+
53
+ Find the natural boundary in your modular monolith:
54
+ ```
55
+ GOOD seams:
56
+ - Module communicates with others through a defined interface/API
57
+ - Module has its own database tables with no foreign keys to other modules
58
+ - Module can be deployed independently without breaking others
59
+
60
+ BAD seams:
61
+ - Two modules share a database table
62
+ - Extracting requires duplicating business logic
63
+ - Module makes 10+ synchronous calls to other modules per request
64
+ ```
65
+
66
+ ### Step 2: Strangle, Don't Rewrite
67
+
68
+ ```
69
+ ❌ BANNED: "Let's rewrite everything as microservices"
70
+
71
+ ✅ REQUIRED: The Strangler Fig Pattern
72
+ 1. Build the new service alongside the monolith
73
+ 2. Route traffic to the new service gradually (feature flags, proxy rules)
74
+ 3. Verify the new service handles all cases correctly
75
+ 4. Remove the old code from the monolith
76
+ 5. Repeat for the next service, ONE AT A TIME
77
+ ```
78
+
79
+ ### Step 3: Define the Contract
80
+
81
+ Before extracting, define the communication contract:
82
+
83
+ ```
84
+ REQUIRED for every service boundary:
85
+ - API contract (OpenAPI 3.1, Protobuf, or AsyncAPI for events)
86
+ - Versioning strategy (URL versioning, header versioning)
87
+ - Error contract (standardized error response format)
88
+ - SLA definition (latency, availability, throughput)
89
+ - Ownership (which team owns this service)
90
+ ```
91
+
92
+ ---
93
+
94
+ ## Communication Patterns
95
+
96
+ ### Synchronous (Request-Response)
97
+
98
+ | Pattern | When | Watch Out |
99
+ |---------|------|-----------|
100
+ | REST/HTTP | Standard CRUD operations | Cascading failures, tight coupling |
101
+ | gRPC | High-performance, internal services | Schema evolution, debugging complexity |
102
+
103
+ **Rules:**
104
+ - Always set timeouts (connection: 1s, request: 5s default)
105
+ - Implement circuit breakers (fail-fast after N failures)
106
+ - Never chain more than 3 synchronous calls
107
+ - Implement retries with exponential backoff (transient errors only)
108
+
109
+ ### Asynchronous (Events)
110
+
111
+ | Pattern | When | Watch Out |
112
+ |---------|------|-----------|
113
+ | Pub/Sub | One event, multiple consumers | Message ordering, at-least-once delivery |
114
+ | Command Queue | Exactly-once processing needed | Dead letter queues, poison messages |
115
+ | Event Sourcing | Full audit trail required | Complexity, event schema evolution |
116
+
117
+ **Rules:**
118
+ - Prefer async communication over sync between services
119
+ - Events are facts (past tense): `OrderPlaced`, `PaymentProcessed`
120
+ - Commands are requests (imperative): `ProcessPayment`, `ShipOrder`
121
+ - Always handle duplicate messages (idempotency)
122
+
123
+ ---
124
+
125
+ ## Data Ownership
126
+
127
+ ### The Database-Per-Service Rule
128
+
129
+ ```
130
+ ❌ DEATH PENALTY: Shared databases between services
131
+ Service A → Database ← Service B
132
+ // One schema change breaks both services
133
+
134
+ ✅ REQUIRED: Each service owns its data
135
+ Service A → Database A
136
+ Service B → Database B
137
+ // Services communicate through APIs or events
138
+ ```
139
+
140
+ ### Data Consistency
141
+
142
+ - **Accept eventual consistency** — strong consistency across services is extremely expensive
143
+ - **Use the Saga pattern** for distributed transactions (choreography or orchestration)
144
+ - **Never use distributed 2PC (two-phase commit)** in production — it doesn't scale
145
+
146
+ ---
147
+
148
+ ## Anti-Patterns (Instant Rejection)
149
+
150
+ | Anti-Pattern | Why It's Dangerous |
151
+ |-------------|-------------------|
152
+ | **Distributed Monolith** | Services that must be deployed together defeat the purpose |
153
+ | **Nano-services** | One function per service creates operational nightmare |
154
+ | **Shared libraries with logic** | Tight coupling through shared code |
155
+ | **Synchronous chains** | A→B→C→D means one failure kills everything |
156
+ | **Shared database** | Schema changes break multiple services |
157
+ | **"We'll figure out observability later"** | You won't find bugs without tracing. Ever. |
158
+
159
+ ---
160
+
161
+ ## The Microservices Readiness Checklist
162
+
163
+ Before splitting ANY module:
164
+
165
+ - [ ] 2+ trigger conditions met (documented with evidence)
166
+ - [ ] All prerequisites in place (CI/CD, observability, team maturity)
167
+ - [ ] Service boundary defined with clear ownership
168
+ - [ ] API contract defined (OpenAPI, Protobuf, AsyncAPI)
169
+ - [ ] Data ownership clear — no shared tables
170
+ - [ ] Communication pattern chosen (sync vs async)
171
+ - [ ] Failure handling designed (timeouts, circuit breakers, retries)
172
+ - [ ] Monitoring and alerting planned
173
+ - [ ] Rollback strategy defined
174
+ - [ ] Team agrees this is the right decision (not just the architect)
@@ -0,0 +1,141 @@
1
+ # Naming Conventions — The "No Lazy Names" Standard
2
+
3
+ > If your variable name needs a comment to explain it, the name is wrong.
4
+
5
+ ## Universal Rules (All Languages)
6
+
7
+ ### Variables: Nouns That Tell a Story
8
+ ```
9
+ ❌ BANNED ✅ REQUIRED
10
+ ─────────────────────────────────────────────
11
+ d durationInSeconds
12
+ data userProfilePayload
13
+ res httpResponse
14
+ temp unsortedItems
15
+ val discountPercentage
16
+ info orderSummary
17
+ item cartLineItem
18
+ list activeSubscriptions
19
+ obj paymentConfiguration
20
+ ```
21
+
22
+ **Rule:** A variable name must answer "WHAT is this?" without reading surrounding code.
23
+
24
+ ### Functions: Verbs That Declare Intent
25
+ ```
26
+ ❌ BANNED ✅ REQUIRED
27
+ ─────────────────────────────────────────────
28
+ process() validatePaymentDetails()
29
+ handle() routeIncomingWebhook()
30
+ doStuff() calculateShippingCost()
31
+ run() executeScheduledCleanup()
32
+ getData() fetchActiveUsersByRegion()
33
+ check() isEligibleForDiscount()
34
+ ```
35
+
36
+ **Rule:** A function name must answer "WHAT does this do?" as a verb phrase. Generic verbs like `process`, `handle`, `manage` are BANNED unless suffixed with a specific noun (e.g., `handlePaymentFailure`).
37
+
38
+ ### Booleans: is/has/can/should Prefix
39
+ ```
40
+ ❌ BANNED ✅ REQUIRED
41
+ ─────────────────────────────────────────────
42
+ active isActive
43
+ logged isLoggedIn
44
+ admin hasAdminRole
45
+ edit canEditDocument
46
+ visible shouldRenderSidebar
47
+ ```
48
+
49
+ **Rule:** Boolean variables MUST use `is`, `has`, `can`, or `should` prefix. No exceptions.
50
+
51
+ ### Constants: SCREAMING_SNAKE for True Constants
52
+ ```
53
+ ❌ BANNED ✅ REQUIRED
54
+ ─────────────────────────────────────────────
55
+ maxRetries = 3 MAX_RETRY_COUNT = 3
56
+ timeout = 5000 REQUEST_TIMEOUT_MS = 5000
57
+ apiUrl = "..." API_BASE_URL = "..."
58
+ ```
59
+
60
+ **Rule:** Use SCREAMING_SNAKE_CASE for compile-time constants and config values. Include the unit in the name when applicable (`_MS`, `_BYTES`, `_COUNT`).
61
+
62
+ ### Single-Letter Variables
63
+ **BANNED.** With exactly ONE exception:
64
+
65
+ ```
66
+ // ALLOWED: Classic loop counter in simple iterations
67
+ for (let i = 0; i < items.length; i++) { ... }
68
+
69
+ // BANNED: Everything else
70
+ const x = getPrice(); // ❌ What is x?
71
+ const n = users.length; // ❌ Use userCount
72
+ arr.map(v => v.id); // ❌ Use user => user.id
73
+ ```
74
+
75
+ ---
76
+
77
+ ## File & Directory Naming
78
+
79
+ ### Files
80
+ | Type | Convention | Example |
81
+ |------|-----------|---------|
82
+ | Component (React/Vue) | PascalCase | `PaymentForm.tsx` |
83
+ | Module/Service | camelCase or kebab-case | `paymentService.ts` or `payment-service.ts` |
84
+ | Utility | camelCase or kebab-case | `formatCurrency.ts` or `format-currency.ts` |
85
+ | Test | Same as source + `.test`/`.spec` | `paymentService.test.ts` |
86
+ | Type/Interface | PascalCase | `PaymentTypes.ts` |
87
+ | Constant file | SCREAMING_SNAKE or kebab-case | `constants.ts` or `api-endpoints.ts` |
88
+ | Config | kebab-case | `database-config.ts` |
89
+
90
+ **Rule:** Pick ONE convention per project and enforce it everywhere. Mixing `camelCase` and `kebab-case` in the same project is a code smell.
91
+
92
+ ### Directories
93
+ - Always `kebab-case`: `user-management/`, `payment-processing/`
94
+ - Never PascalCase for directories (except component folders in React convention)
95
+ - No abbreviations: `auth/` → `authentication/` (unless universally understood like `api/`, `db/`)
96
+
97
+ ---
98
+
99
+ ## Abbreviation Policy
100
+
101
+ ### Allowed (Universal)
102
+ `id`, `url`, `api`, `db`, `http`, `io`, `ui`, `dto`, `config`, `env`, `auth`, `admin`, `src`, `lib`, `pkg`, `cmd`, `ctx`, `err`, `req`, `res` (in HTTP handler context only)
103
+
104
+ ### Banned
105
+ Everything else. Spell it out:
106
+ ```
107
+ ❌ usr → ✅ user
108
+ ❌ cnt → ✅ count
109
+ ❌ mgr → ✅ manager
110
+ ❌ btn → ✅ button
111
+ ❌ msg → ✅ message
112
+ ❌ impl → ✅ implementation
113
+ ❌ calc → ✅ calculate
114
+ ❌ proc → ✅ process
115
+ ```
116
+
117
+ ---
118
+
119
+ ## The Naming Decision Tree
120
+
121
+ ```
122
+ Is it a boolean?
123
+ → Yes → Add is/has/can/should prefix
124
+ → No ↓
125
+
126
+ Is it a function?
127
+ → Yes → Start with a verb (fetch, create, validate, calculate, is, has)
128
+ → No ↓
129
+
130
+ Is it a constant?
131
+ → Yes → SCREAMING_SNAKE_CASE with unit suffix
132
+ → No ↓
133
+
134
+ Is it a class/type/interface?
135
+ → Yes → PascalCase, noun, no prefix (not IUser, not UserInterface)
136
+ → No ↓
137
+
138
+ It's a variable
139
+ → Descriptive noun, camelCase
140
+ → Must be understandable without context
141
+ ```
@@ -0,0 +1,168 @@
1
+ # Performance — Measure Before You Optimize
2
+
3
+ > Premature optimization is the root of all evil.
4
+ > But ignoring obvious performance traps is just incompetence.
5
+
6
+ ## The Performance Prime Directive
7
+
8
+ **Do NOT optimize without evidence.** CPU time is cheap. Developer time is expensive.
9
+
10
+ BUT — there are patterns so obviously bad that they don't need benchmarks to reject.
11
+ Those are listed below as **Death Penalties**.
12
+
13
+ ---
14
+
15
+ ## Death Penalties (Always Reject)
16
+
17
+ ### 1. N+1 Queries
18
+ ```
19
+ ❌ INSTANT REJECTION:
20
+ const users = await db.query('SELECT * FROM users');
21
+ for (const user of users) {
22
+ user.orders = await db.query('SELECT * FROM orders WHERE user_id = ?', [user.id]);
23
+ // This runs 1 + N queries. For 1000 users = 1001 database round trips.
24
+ }
25
+
26
+ ✅ REQUIRED:
27
+ const users = await db.query('SELECT * FROM users');
28
+ const userIds = users.map(u => u.id);
29
+ const orders = await db.query('SELECT * FROM orders WHERE user_id = ANY($1)', [userIds]);
30
+ // 2 queries total, regardless of user count
31
+ // Or use ORM eager loading / DataLoader pattern
32
+ ```
33
+
34
+ **Rule:** If you see a query inside a loop, it is almost certainly an N+1 bug. Fix it with JOINs, batch queries, or DataLoader.
35
+
36
+ ### 2. Unbounded Queries
37
+ ```
38
+ ❌ INSTANT REJECTION:
39
+ const allUsers = await db.query('SELECT * FROM users');
40
+ // In production, "users" table has 2 million rows. Enjoy your OOM.
41
+
42
+ ✅ REQUIRED:
43
+ const users = await db.query('SELECT * FROM users LIMIT $1 OFFSET $2', [pageSize, offset]);
44
+ // Or use cursor-based pagination for large datasets
45
+ ```
46
+
47
+ **Rule:** EVERY query that returns a list MUST have a LIMIT. APIs MUST support pagination. Default page size: 20-50.
48
+
49
+ ### 3. SELECT * in Production
50
+ ```
51
+ ❌ BANNED:
52
+ SELECT * FROM users; -- Fetches 30 columns when you need 3
53
+
54
+ ✅ REQUIRED:
55
+ SELECT id, email, display_name FROM users;
56
+ ```
57
+
58
+ **Rule:** Select only the columns you need. `SELECT *` wastes bandwidth, memory, and makes schema changes dangerous.
59
+
60
+ ### 4. Synchronous I/O in Async Context
61
+ ```
62
+ ❌ BANNED:
63
+ // In an async Node.js server
64
+ const data = fs.readFileSync('/path/to/file');
65
+ const result = execSync('some-command');
66
+
67
+ ✅ REQUIRED:
68
+ const data = await fs.promises.readFile('/path/to/file');
69
+ const result = await exec('some-command');
70
+ ```
71
+
72
+ **Rule:** In async environments (Node.js, Python asyncio), NEVER block the event loop with synchronous I/O.
73
+
74
+ ---
75
+
76
+ ## Optimize Only With Evidence
77
+
78
+ For everything else, follow this protocol:
79
+
80
+ ### Step 1: Measure
81
+ ```
82
+ // Use profiling tools, not guesses
83
+ console.time('operation');
84
+ await heavyOperation();
85
+ console.timeEnd('operation');
86
+
87
+ // Use proper APM: Datadog, New Relic, OpenTelemetry
88
+ ```
89
+
90
+ ### Step 2: Identify the Bottleneck
91
+ - Is it CPU? Memory? I/O? Network?
92
+ - Don't optimize CPU when the bottleneck is a slow database query
93
+
94
+ ### Step 3: Optimize the Bottleneck (Not Everything Else)
95
+ - Fix the slowest thing first
96
+ - Re-measure after each change
97
+ - Stop when performance meets requirements
98
+
99
+ ---
100
+
101
+ ## Caching Rules
102
+
103
+ ### When to Cache
104
+ - Data that is read frequently, written rarely
105
+ - Expensive computations that produce the same result for same inputs
106
+ - External API responses (respect their cache headers)
107
+
108
+ ### When NOT to Cache
109
+ - Data that changes every request
110
+ - Small, fast queries (cache overhead > query time)
111
+ - When you can't define a clear invalidation strategy
112
+
113
+ ### The Caching Devil's Triangle
114
+ You can have 2 of 3:
115
+ 1. **Fresh data** (always up-to-date)
116
+ 2. **Fast reads** (sub-millisecond)
117
+ 3. **Simple code** (no cache layer)
118
+
119
+ Pick your 2 and document the trade-off.
120
+
121
+ ### Invalidation Strategy (MANDATORY)
122
+ ```
123
+ ❌ BANNED:
124
+ cache.set('users', data); // When does this expire? Who invalidates it? Nobody knows.
125
+
126
+ ✅ REQUIRED:
127
+ cache.set('users:active', data, { ttl: 300 }); // 5 min TTL, explicit key
128
+ // AND document: "Invalidated on user.created, user.deleted, user.deactivated events"
129
+ ```
130
+
131
+ **Rule:** NEVER add a cache without documenting the invalidation strategy. "We'll figure it out later" means "we'll have stale data in production."
132
+
133
+ ---
134
+
135
+ ## Connection Management
136
+
137
+ 1. **Use connection pools** — never open/close connections per request
138
+ 2. **Set pool limits** — max connections based on infrastructure, not infinity
139
+ 3. **Implement timeouts** — connection timeout, query timeout, request timeout
140
+ 4. **Handle pool exhaustion** — fail fast with clear error, don't queue forever
141
+
142
+ ---
143
+
144
+ ## Frontend Performance (When Applicable)
145
+
146
+ 1. **Lazy load** routes and heavy components
147
+ 2. **Debounce** search inputs and scroll handlers (300ms minimum)
148
+ 3. **Virtualize** long lists (don't render 10,000 DOM nodes)
149
+ 4. **Optimize images** — WebP/AVIF, responsive sizes, lazy loading
150
+ 5. **Bundle analysis** — if your JS bundle exceeds 200KB gzipped, investigate
151
+
152
+ ---
153
+
154
+ ## The Performance Decision Framework
155
+
156
+ ```
157
+ Is it a known Death Penalty pattern (N+1, unbounded, SELECT *, sync I/O)?
158
+ → Yes → Fix it now, no measurement needed
159
+ → No ↓
160
+
161
+ Is there a measurable performance problem?
162
+ → No → Don't optimize. Ship it.
163
+ → Yes ↓
164
+
165
+ Have you identified the specific bottleneck?
166
+ → No → Profile first
167
+ → Yes → Optimize ONLY that bottleneck, re-measure, stop when sufficient
168
+ ```