devrites 2.0.0 → 2.1.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.
- package/CHANGELOG.md +6 -0
- package/README.md +1 -1
- package/pack/.claude/agents/devrites-performance-reviewer.md +56 -8
- package/pack/.claude/rules/performance.md +9 -0
- package/pack/.claude/skills/devrites-browser-proof/SKILL.md +23 -3
- package/pack/.claude/skills/rite-review/reference/performance-checklist.md +80 -0
- package/pack/.claude/skills/rite-review/reference/performance-review.md +4 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,12 @@
|
|
|
2
2
|
|
|
3
3
|
All notable changes to DevRites are documented here. The format follows [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) and DevRites adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). Releases are generated automatically by [semantic-release](https://semantic-release.gitbook.io/) from Conventional Commits on `main`.
|
|
4
4
|
|
|
5
|
+
## [2.1.0](https://github.com/ViktorsBaikers/DevRites/compare/v2.0.0...v2.1.0) (2026-06-23)
|
|
6
|
+
|
|
7
|
+
### Added
|
|
8
|
+
|
|
9
|
+
* **agents:** perf reviewer gets Source/Measured CWV modes ([be82b20](https://github.com/ViktorsBaikers/DevRites/commit/be82b20b37252a9f55d77e0f71659ec58a213ca6))
|
|
10
|
+
|
|
5
11
|
## [2.0.0](https://github.com/ViktorsBaikers/DevRites/compare/v1.18.0...v2.0.0) (2026-06-23)
|
|
6
12
|
|
|
7
13
|
### ⚠ BREAKING CHANGES
|
package/README.md
CHANGED
|
@@ -94,7 +94,7 @@ Full diagram set (lifecycle, polish orchestrator, review fan-out, debug loop,
|
|
|
94
94
|
rules carrier, workspace state, namespace map) →
|
|
95
95
|
[`docs/flow.md`](docs/flow.md).
|
|
96
96
|
|
|
97
|
-
**Status:** [`v2.
|
|
97
|
+
**Status:** [`v2.1.0`](https://github.com/ViktorsBaikers/DevRites/releases/tag/v2.1.0) — see [`CHANGELOG.md`](CHANGELOG.md) for release notes.
|
|
98
98
|
|
|
99
99
|
## Contents
|
|
100
100
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: devrites-performance-reviewer
|
|
3
|
-
description: Fresh-context, measure-first performance reviewer for /rite-seal. Use to independently review a DevRites feature diff for N+1s, hot-path work, payload/bundle size, and Core Web Vitals risks. Won't claim a slowdown without a number or a measurement to take.
|
|
3
|
+
description: Fresh-context, measure-first performance reviewer for /rite-seal. Use to independently review a DevRites feature diff for N+1s, hot-path work, payload/bundle size, and Core Web Vitals risks. Runs in Source mode (static scan, findings tagged potential) or Measured mode (judges real Lighthouse/PSI/CrUX/trace numbers and leads with a source-labeled CWV scorecard). Won't claim a slowdown without a number or a measurement to take, and never presents lab data as field data.
|
|
4
4
|
tools: Read, Grep, Glob, Bash
|
|
5
5
|
hooks:
|
|
6
6
|
PreToolUse:
|
|
@@ -17,19 +17,50 @@ You are measure-first: no performance claim without a number or a specified meas
|
|
|
17
17
|
|
|
18
18
|
## Inputs
|
|
19
19
|
Workspace `.devrites/work/<slug>/`: read `spec.md` (any perf budget), `evidence.md`,
|
|
20
|
-
`touched-files.md`. Run `git diff` and read the touched files.
|
|
20
|
+
`touched-files.md`. Run `git diff` and read the touched files. Also look for Core Web
|
|
21
|
+
Vitals artifacts — numbers already in `evidence.md`, a Lighthouse / PageSpeed Insights /
|
|
22
|
+
CrUX JSON path the builder left, or a browser-proof capture in `browser-evidence.md`.
|
|
23
|
+
|
|
24
|
+
Read the baseline checklist on demand (resolve the path like the readonly hook):
|
|
25
|
+
```
|
|
26
|
+
C=.claude/skills/rite-review/reference/performance-checklist.md
|
|
27
|
+
[ -f "$C" ] || C="$CLAUDE_PLUGIN_ROOT/pack/.claude/skills/rite-review/reference/performance-checklist.md"
|
|
28
|
+
[ -f "$C" ] || C=pack/.claude/skills/rite-review/reference/performance-checklist.md
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
## Two modes (the inputs set the mode, not a flag)
|
|
32
|
+
- **Source mode** — default, no perf artifacts present. Scan the diff statically for
|
|
33
|
+
structural anti-patterns. Every frontend finding is **potential impact**, never a
|
|
34
|
+
measurement; name the command that would confirm it. Emit **no scorecard**.
|
|
35
|
+
- **Measured mode** — a CWV artifact or a real number exists. Judge it against the
|
|
36
|
+
`spec.md` budget or the pre-change baseline, and lead with the scorecard.
|
|
37
|
+
|
|
38
|
+
Source mode is the same discipline as the old "specify the measurement" — it just names
|
|
39
|
+
the contract for when the scorecard appears.
|
|
21
40
|
|
|
22
41
|
## Review (feature scope)
|
|
23
|
-
- **Backend** — N+1 queries, missing indexes on new queries,
|
|
24
|
-
per-request work that should be cached/batched, blocking sync
|
|
25
|
-
-
|
|
26
|
-
|
|
42
|
+
- **Backend** (always, every feature) — N+1 queries, missing indexes on new queries,
|
|
43
|
+
unbounded result sets, per-request work that should be cached/batched, blocking sync
|
|
44
|
+
work. *AI-codegen smell:* over-fetching "just in case", sequential `await`s where
|
|
45
|
+
`Promise.all` fits, redundant calls a dedup would collapse.
|
|
46
|
+
- **Frontend (Core Web Vitals)** — only when the feature is UI-facing. Identify the
|
|
47
|
+
framework and rendering model first (React / Vue / Svelte / Angular / Next / Astro /
|
|
48
|
+
vanilla) and apply only that stack's idioms — don't recommend `next/image` to a Vue app
|
|
49
|
+
or `React.memo` to Svelte. Check LCP (oversized images, render-blocking work, missing
|
|
50
|
+
`fetchpriority`), CLS (layout shift, missing image dimensions), INP (long tasks, heavy
|
|
51
|
+
event handlers), bundle growth, unnecessary re-renders. *AI-codegen smell:* `memo` /
|
|
52
|
+
`useMemo` / `useCallback` wrapping everything, over-eager effect deps, broad watchers.
|
|
27
53
|
- **General** — accidental quadratic loops, repeated hot-path work, large allocations.
|
|
28
54
|
|
|
29
55
|
## Measure-first discipline
|
|
30
|
-
- If a real number exists
|
|
56
|
+
- If a real number exists, judge it against the budget/baseline; state the before/after.
|
|
31
57
|
- If not, **specify the measurement** (command, scenario, metric) instead of asserting a
|
|
32
58
|
regression. Distinguish "measured regression" from "likely hot spot, verify with X".
|
|
59
|
+
- **Source-honesty.** Label every measured CWV value with where it came from —
|
|
60
|
+
`Field (CrUX)` (real users, p75), `Lab (Lighthouse)` (one synthetic run), or
|
|
61
|
+
`Trace (DevTools)`. Field and lab are not interchangeable; presenting one as the other
|
|
62
|
+
is fabrication. Reading static source cannot measure LCP / INP / CLS — never invent a
|
|
63
|
+
number for a value you did not capture.
|
|
33
64
|
|
|
34
65
|
## Rules
|
|
35
66
|
- Don't edit. Findings only, labeled Critical / Important / Suggestion / Nit / FYI with
|
|
@@ -37,9 +68,26 @@ Workspace `.devrites/work/<slug>/`: read `spec.md` (any perf budget), `evidence.
|
|
|
37
68
|
micro-opt with no measured impact is a Suggestion at most. Feature scope only.
|
|
38
69
|
|
|
39
70
|
## Output
|
|
71
|
+
|
|
72
|
+
**Measured mode** — lead with a compact scorecard, then the line findings:
|
|
73
|
+
```
|
|
74
|
+
Performance review (<slug>) — independent
|
|
75
|
+
Scorecard (source-labeled):
|
|
76
|
+
LCP <value> <Field(CrUX) | Lab(LH) | Trace> <Good/Needs Work/Poor> (target ≤2.5s)
|
|
77
|
+
INP <value> <source> <status> (target ≤200ms)
|
|
78
|
+
CLS <value> <source> <status> (target ≤0.1)
|
|
79
|
+
[Lighthouse perf <score> Lab(LH)] Artifacts: <which> Stack: <detected>
|
|
80
|
+
[Critical]/[Important] file:line — issue. measured: <number>. direction.
|
|
81
|
+
[Suggestion]/[Nit]/[FYI] ...
|
|
82
|
+
Budget: <breached? | none stated>
|
|
83
|
+
Verdict: <blockers? none/list>
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
**Source mode** — no artifacts; one scorecard line, findings tagged `potential`:
|
|
40
87
|
```
|
|
41
88
|
Performance review (<slug>) — independent
|
|
42
|
-
|
|
89
|
+
Scorecard: not measured (Source mode)
|
|
90
|
+
[Important] file:line — issue. potential; verify: <cmd/metric>. direction.
|
|
43
91
|
[Suggestion]/[Nit]/[FYI] ...
|
|
44
92
|
Budget: <breached? | none stated>
|
|
45
93
|
To prove any win: <measure X before/after>
|
|
@@ -21,6 +21,15 @@ Measure first. An optimization without a measurement is a guess that adds comple
|
|
|
21
21
|
- Don't trade correctness or readability for a micro-win that doesn't matter.
|
|
22
22
|
- Prefer a better algorithm or query over micro-tuning; the big wins are structural.
|
|
23
23
|
|
|
24
|
+
## Frontend — Core Web Vitals
|
|
25
|
+
For UI work, measure-first means LCP / INP / CLS judged against real numbers, each labeled
|
|
26
|
+
by source (`Field (CrUX)`, `Lab (Lighthouse)`, `Trace (DevTools)`) — field and lab are not
|
|
27
|
+
interchangeable, and static source cannot measure a CWV. The reviewer captures these via the
|
|
28
|
+
browser-proof ladder when a budget exists, then judges them in Measured mode (a
|
|
29
|
+
source-labeled scorecard); with no artifact it runs in Source mode and names the command.
|
|
30
|
+
Baseline checks + measurement commands:
|
|
31
|
+
[`rite-review/reference/performance-checklist.md`](../skills/rite-review/reference/performance-checklist.md).
|
|
32
|
+
|
|
24
33
|
## Scope
|
|
25
34
|
Optimize what the change touches or what a measurement flags. Project-wide performance
|
|
26
35
|
work is its own effort — record it as a follow-up, don't smuggle it into an unrelated
|
|
@@ -22,12 +22,32 @@ of the ladder that's available; record which one.
|
|
|
22
22
|
the project's existing commands. Don't add a new framework.
|
|
23
23
|
5. **Manual fallback** — none available: record the limitation + exact manual steps.
|
|
24
24
|
|
|
25
|
+
## Core Web Vitals capture (when the spec states a perf budget)
|
|
26
|
+
If `spec.md` carries a perf budget — or a frontend regression risk is visible — capture the
|
|
27
|
+
CWV numbers here so the perf reviewer judges real data instead of guessing. Use the highest
|
|
28
|
+
rung available; **detect, don't install**.
|
|
29
|
+
|
|
30
|
+
1. **Chrome DevTools MCP** (if configured) — `lighthouse_audit` for LCP/INP/CLS + the
|
|
31
|
+
Lighthouse performance score. Source label: **Lab (Lighthouse)**. A `performance_*` trace
|
|
32
|
+
gives **Trace (DevTools)** attribution.
|
|
33
|
+
2. **browser-harness** — drive the route, capture a performance trace over CDP. Source
|
|
34
|
+
label: **Trace (DevTools)**.
|
|
35
|
+
3. **CrUX / PageSpeed Insights** — only if the user supplied an API key. Field data, p75.
|
|
36
|
+
Source label: **Field (CrUX)**.
|
|
37
|
+
4. **None available** → mark CWV **pending (manual)** and name the exact command
|
|
38
|
+
(`npx lighthouse <url> --output json …`). Don't install anything; don't fake a number.
|
|
39
|
+
|
|
40
|
+
Write each captured value **with its source label** to `evidence.md` (so the perf reviewer
|
|
41
|
+
reads it in Measured mode) and note the tool + route in `browser-evidence.md`. Never present
|
|
42
|
+
a lab value as a field value or vice versa.
|
|
43
|
+
|
|
25
44
|
## Evidence schema → `browser-evidence.md`
|
|
26
45
|
Tooling used · route(s) · viewports (375/768/1280) · screenshot paths **opened and
|
|
27
46
|
described** · console errors/warnings · network failures · interaction path tested ·
|
|
28
|
-
accessibility basics · responsive checks · **
|
|
29
|
-
|
|
30
|
-
|
|
47
|
+
accessibility basics · responsive checks · **CWV capture** (tool + route + each
|
|
48
|
+
source-labeled value, or `pending (manual)` + the command) · **design-reference match** (if
|
|
49
|
+
the spec saved references in `references/`, compare the built UI to them and note
|
|
50
|
+
match/diffs) · limitations.
|
|
31
51
|
|
|
32
52
|
## Hard rules
|
|
33
53
|
- A screenshot **path is not proof** — open it and describe what's visible.
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
# Performance checklist (baseline for the perf reviewer)
|
|
2
|
+
|
|
3
|
+
The minimum baseline `devrites-performance-reviewer` checks against, in feature scope. It
|
|
4
|
+
is a checklist, not a mandate: flag what the diff actually touches or what a measurement
|
|
5
|
+
flags, never a project-wide sweep. The philosophy lives in
|
|
6
|
+
[`rules/performance.md`](../../../rules/performance.md) (measure first) — this file is the
|
|
7
|
+
concrete what-to-look-for.
|
|
8
|
+
|
|
9
|
+
## Core Web Vitals targets
|
|
10
|
+
|
|
11
|
+
| Metric | Good | Needs work | Poor |
|
|
12
|
+
|---|---|---|---|
|
|
13
|
+
| LCP — Largest Contentful Paint | ≤ 2.5s | ≤ 4.0s | > 4.0s |
|
|
14
|
+
| INP — Interaction to Next Paint | ≤ 200ms | ≤ 500ms | > 500ms |
|
|
15
|
+
| CLS — Cumulative Layout Shift | ≤ 0.1 | ≤ 0.25 | > 0.25 |
|
|
16
|
+
|
|
17
|
+
A CWV value only counts when it carries a source — `Field (CrUX)`, `Lab (Lighthouse)`, or
|
|
18
|
+
`Trace (DevTools)`. No source → it's a Source-mode hypothesis, not a measurement.
|
|
19
|
+
|
|
20
|
+
## Frontend (only when the feature is UI-facing)
|
|
21
|
+
|
|
22
|
+
Identify the framework first; apply only its idioms.
|
|
23
|
+
|
|
24
|
+
- **Images** — modern format (WebP/AVIF); responsive `srcset`/`sizes`; explicit
|
|
25
|
+
`width`/`height` to reserve space (CLS); below-the-fold `loading="lazy"`; the LCP image
|
|
26
|
+
gets `fetchpriority="high"` and is **not** lazy-loaded.
|
|
27
|
+
- **JavaScript** — initial bundle stays small (≈200KB gzipped is the usual line); code-split
|
|
28
|
+
routes and heavy features; no blocking script in `<head>` without `defer`/`async`; break
|
|
29
|
+
long tasks (>50ms) so the main thread stays free (the main INP lever); `memo`/`useMemo`/
|
|
30
|
+
`useCallback` only where profiling shows a win, not wrapped over everything.
|
|
31
|
+
- **CSS** — critical CSS not render-blocking; no per-render CSS-in-JS runtime cost in prod.
|
|
32
|
+
- **Fonts** — 2–3 families max; WOFF2; self-hosted where possible; preload the LCP font;
|
|
33
|
+
`font-display: swap`; subset with `unicode-range`.
|
|
34
|
+
- **Rendering** — no layout thrashing (batch reads, then writes); animate `transform`/
|
|
35
|
+
`opacity` only; virtualize long lists; `content-visibility: auto` for off-screen sections;
|
|
36
|
+
don't break bfcache (no `unload` handler, no `Cache-Control: no-store` on HTML).
|
|
37
|
+
|
|
38
|
+
## Backend (every feature, UI or not)
|
|
39
|
+
|
|
40
|
+
- No N+1 queries; eager-load / join / batch instead.
|
|
41
|
+
- New queries have the indexes they need for their filter/sort columns.
|
|
42
|
+
- List endpoints paginate — never an unbounded `SELECT *`.
|
|
43
|
+
- Per-request work that doesn't change per call is cached or hoisted.
|
|
44
|
+
- Responses compressed (gzip/brotli); bulk operations instead of a loop of single calls.
|
|
45
|
+
|
|
46
|
+
## Network
|
|
47
|
+
|
|
48
|
+
- Static assets cached with a long `max-age` + content hashing.
|
|
49
|
+
- Known origins `preconnect`-ed; no unnecessary redirects; HTTP/2 or HTTP/3 where available.
|
|
50
|
+
|
|
51
|
+
## AI-codegen perf smells (fold into the area above, not a separate finding category)
|
|
52
|
+
|
|
53
|
+
- State duplicated instead of lifted; effects with over-broad deps that re-run needlessly.
|
|
54
|
+
- Sequential `await`s where `Promise.all` / parallel fetch fits.
|
|
55
|
+
- Over-fetching "just in case"; redundant calls a dedup would collapse.
|
|
56
|
+
- Defensive memoization wrapping cheap components — cost with no benefit.
|
|
57
|
+
|
|
58
|
+
## Modern APIs to consider (one-liners — reach for these, don't gate on them)
|
|
59
|
+
|
|
60
|
+
`scheduler.yield()` to keep input responsive in long loops · Speculation Rules for
|
|
61
|
+
prefetch/prerender · View Transitions on SPA navigation · Long Animation Frames (LoAF) for
|
|
62
|
+
production INP attribution · `fetchpriority` on critical non-image resources.
|
|
63
|
+
|
|
64
|
+
## Measurement commands (name these in Source mode; don't run installs in review)
|
|
65
|
+
|
|
66
|
+
```bash
|
|
67
|
+
# Lighthouse (lab)
|
|
68
|
+
npx lighthouse <url> --output json --output-path ./report.json
|
|
69
|
+
# or via the Chrome DevTools MCP CLI, no install:
|
|
70
|
+
npx -p chrome-devtools-mcp chrome-devtools lighthouse_audit --output-format=json > report.json
|
|
71
|
+
|
|
72
|
+
# Bundle size
|
|
73
|
+
npx vite-bundle-visualizer # Vite
|
|
74
|
+
npx webpack-bundle-analyzer stats.json # webpack
|
|
75
|
+
|
|
76
|
+
# Field data: CrUX / PageSpeed Insights (real users, p75) — needs an API key
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
Field is what real users experienced; lab is one synthetic run. Don't present one as the
|
|
80
|
+
other.
|
|
@@ -17,6 +17,10 @@ a hunch.
|
|
|
17
17
|
unnecessary re-renders.
|
|
18
18
|
- **General**: accidental quadratic loops, repeated work in hot paths, large allocations.
|
|
19
19
|
|
|
20
|
+
The agent runs **Source mode** (static scan, findings tagged `potential` + the verify
|
|
21
|
+
command) or **Measured mode** (real CWV numbers → a source-labeled scorecard). Baseline
|
|
22
|
+
checks + measurement commands: [`performance-checklist.md`](performance-checklist.md).
|
|
23
|
+
|
|
20
24
|
## Optimize responsibly
|
|
21
25
|
- Fix the measured bottleneck, then **re-measure** to prove the win (before/after in
|
|
22
26
|
`evidence.md`). An optimization with no measured improvement is just added complexity.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "devrites",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.1.0",
|
|
4
4
|
"description": "DevRites — disciplined senior-engineer workflow skills pack for Claude Code",
|
|
5
5
|
"license": "SEE LICENSE IN LICENSE",
|
|
6
6
|
"homepage": "https://github.com/ViktorsBaikers/DevRites#readme",
|