@mohammadhprp/system-prompt 0.11.1 → 0.12.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/framework/agents/backend-architect.md +1 -1
- package/framework/agents/researcher.md +1 -1
- package/framework/mcps/figma-mcp-go/README.md +0 -1
- package/framework/mcps/github-mcp/README.md +1 -1
- package/framework/mcps/github-mcp/configs/.env.example +1 -1
- package/framework/mcps/gitlab-mcp/README.md +0 -1
- package/framework/mcps/jira-mcp/README.md +0 -1
- package/framework/mcps/laravel-boost/README.md +0 -1
- package/framework/mcps/notion-mcp/README.md +0 -1
- package/framework/mcps/supabase-mcp/README.md +0 -1
- package/framework/plugins/opencode-goal-plugin/README.md +0 -1
- package/framework/plugins/ponytail/README.md +1 -1
- package/framework/plugins/ponytail/capabilities.md +1 -1
- package/framework/references/standards/api.md +0 -1
- package/framework/references/standards/architecture.md +0 -1
- package/framework/references/standards/database.md +0 -1
- package/framework/references/standards/debugging.md +0 -1
- package/framework/references/standards/documentation.md +0 -2
- package/framework/references/standards/logging.md +0 -1
- package/framework/references/standards/naming.md +0 -1
- package/framework/references/standards/observability.md +0 -1
- package/framework/references/standards/performance.md +0 -1
- package/framework/references/standards/pull-requests.md +1 -2
- package/framework/references/standards/security.md +0 -1
- package/framework/references/standards/testing.md +0 -1
- package/framework/skills/README.md +16 -4
- package/framework/skills/codenavi/SKILL.md +306 -0
- package/framework/skills/codenavi/examples.md +33 -0
- package/framework/skills/codenavi/references/coding-principles.md +143 -0
- package/framework/skills/codenavi/references/notebook-spec.md +171 -0
- package/framework/skills/create-adr/SKILL.md +429 -0
- package/framework/skills/create-adr/examples.md +35 -0
- package/framework/skills/diagram-design/SKILL.md +1 -1
- package/framework/skills/docs-writer/SKILL.md +39 -0
- package/framework/skills/docs-writer/examples.md +34 -0
- package/framework/skills/docs-writer/references/style-guide.md +72 -0
- package/framework/skills/frontend-design/SKILL.md +55 -0
- package/framework/skills/frontend-design/examples.md +45 -0
- package/framework/skills/humanizer/SKILL.md +412 -0
- package/framework/skills/humanizer/examples.md +46 -0
- package/framework/skills/learning-opportunities/SKILL.md +140 -0
- package/framework/skills/learning-opportunities/examples.md +34 -0
- package/framework/skills/learning-opportunities/references/PRINCIPLES.md +42 -0
- package/framework/skills/perf-web-optimization/SKILL.md +163 -0
- package/framework/skills/perf-web-optimization/examples.md +35 -0
- package/framework/skills/perf-web-optimization/references/bundle-optimization.md +180 -0
- package/framework/skills/perf-web-optimization/references/core-web-vitals.md +154 -0
- package/framework/skills/perf-web-optimization/references/image-optimization.md +170 -0
- package/framework/skills/security-best-practices/LICENSE.txt +201 -0
- package/framework/skills/security-best-practices/SKILL.md +89 -0
- package/framework/skills/security-best-practices/examples.md +35 -0
- package/framework/skills/security-best-practices/references/golang-general-backend-security.md +988 -0
- package/framework/skills/security-best-practices/references/javascript-express-web-server-security.md +1151 -0
- package/framework/skills/security-best-practices/references/javascript-general-web-frontend-security.md +725 -0
- package/framework/skills/security-best-practices/references/javascript-jquery-web-frontend-security.md +672 -0
- package/framework/skills/security-best-practices/references/javascript-typescript-nextjs-web-server-security.md +1138 -0
- package/framework/skills/security-best-practices/references/javascript-typescript-react-web-frontend-security.md +975 -0
- package/framework/skills/security-best-practices/references/javascript-typescript-vue-web-frontend-security.md +789 -0
- package/framework/skills/security-best-practices/references/python-django-web-server-security.md +880 -0
- package/framework/skills/security-best-practices/references/python-fastapi-web-server-security.md +1030 -0
- package/framework/skills/security-best-practices/references/python-flask-web-server-security.md +835 -0
- package/framework/skills/sentry/SKILL.md +127 -0
- package/framework/skills/sentry/examples.md +34 -0
- package/framework/skills/sentry/scripts/sentry_api.py +238 -0
- package/framework/skills/show-me/SKILL.md +127 -0
- package/framework/skills/show-me/examples.md +78 -0
- package/framework/skills/spec-driven-eval/SKILL.md +341 -0
- package/framework/skills/spec-driven-eval/examples.md +35 -0
- package/framework/skills/spec-driven-eval/references/quickstart.md +118 -0
- package/framework/skills/spec-driven-eval/references/reference.md +295 -0
- package/framework/skills/taste/SKILL.md +47 -0
- package/framework/skills/taste/examples.md +73 -0
- package/framework/skills/taste/references/brandkit.md +793 -0
- package/framework/skills/taste/references/design-taste-frontend-v1.md +221 -0
- package/framework/skills/taste/references/design-taste-frontend.md +1201 -0
- package/framework/skills/taste/references/full-output-enforcement.md +44 -0
- package/framework/skills/taste/references/gpt-taste.md +69 -0
- package/framework/skills/taste/references/high-end-visual-design.md +93 -0
- package/framework/skills/taste/references/image-to-code.md +1223 -0
- package/framework/skills/taste/references/imagegen-frontend-mobile.md +1460 -0
- package/framework/skills/taste/references/imagegen-frontend-web.md +982 -0
- package/framework/skills/taste/references/industrial-brutalist-ui.md +87 -0
- package/framework/skills/taste/references/minimalist-ui.md +80 -0
- package/framework/skills/taste/references/redesign-existing-projects.md +173 -0
- package/framework/skills/taste/references/stitch-design-taste-design.md +121 -0
- package/framework/skills/taste/references/stitch-design-taste.md +179 -0
- package/framework/skills/technical-design-doc-creator/README.md +411 -0
- package/framework/skills/technical-design-doc-creator/SKILL.md +1484 -0
- package/framework/skills/technical-design-doc-creator/examples.md +35 -0
- package/framework/skills/tlc-spec-driven/SKILL.md +184 -0
- package/framework/skills/tlc-spec-driven/examples.md +34 -0
- package/framework/skills/tlc-spec-driven/references/code-analysis.md +98 -0
- package/framework/skills/tlc-spec-driven/references/coding-principles.md +72 -0
- package/framework/skills/tlc-spec-driven/references/context-limits.md +31 -0
- package/framework/skills/tlc-spec-driven/references/design.md +199 -0
- package/framework/skills/tlc-spec-driven/references/discuss.md +159 -0
- package/framework/skills/tlc-spec-driven/references/implement.md +436 -0
- package/framework/skills/tlc-spec-driven/references/lessons.md +115 -0
- package/framework/skills/tlc-spec-driven/references/memory.md +144 -0
- package/framework/skills/tlc-spec-driven/references/specify.md +228 -0
- package/framework/skills/tlc-spec-driven/references/sub-agents.md +147 -0
- package/framework/skills/tlc-spec-driven/references/tasks.md +451 -0
- package/framework/skills/tlc-spec-driven/references/validate.md +355 -0
- package/framework/skills/tlc-spec-driven/scripts/check_commit.py +115 -0
- package/framework/skills/tlc-spec-driven/scripts/lessons.py +412 -0
- package/framework/skills/tlc-spec-driven/scripts/validate_spec.py +260 -0
- package/framework/skills/tlc-spec-driven/scripts/validate_state.py +162 -0
- package/framework/skills/tlc-spec-driven/scripts/validate_tasks.py +251 -0
- package/framework/skills/web-design-guidelines/SKILL.md +65 -0
- package/framework/skills/web-design-guidelines/examples.md +32 -0
- package/framework/skills/web-design-guidelines/references/guideline.md +174 -0
- package/package.json +1 -1
- package/src/agent-configs.js +6 -2
- package/src/catalog.js +16 -3
- package/src/cli.js +82 -2
- package/src/doctor.js +84 -0
- package/src/installer.js +337 -154
- package/framework/skills/backend-engineer/SKILL.md +0 -76
- package/framework/skills/backend-engineer/examples.md +0 -31
- package/framework/skills/documentation/SKILL.md +0 -74
- package/framework/skills/documentation/examples.md +0 -31
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: learning-opportunities
|
|
3
|
+
description: Facilitates deliberate skill development during AI-assisted coding. Offers interactive learning exercises after architectural work (new files, schema changes, refactors). Use when completing features, making design decisions, or when user asks to understand code better. Triggers on "learning exercise", "help me understand", "teach me", "why does this work", or after creating new files/modules. Do NOT use for urgent debugging, quick fixes, or when user says "just ship it".
|
|
4
|
+
license: CC-BY-4.0
|
|
5
|
+
metadata:
|
|
6
|
+
original_author: Chris Hicks
|
|
7
|
+
modified_by: Felipe Rodrigues - github.com/felipfr
|
|
8
|
+
source: https://www.fightforthehuman.com
|
|
9
|
+
version: 1.1.0
|
|
10
|
+
---
|
|
11
|
+
|
|
12
|
+
# Learning Opportunities
|
|
13
|
+
|
|
14
|
+
Facilitate deliberate skill development during AI-assisted coding sessions. Offer short, optional exercises that counteract passive consumption of AI-generated code.
|
|
15
|
+
|
|
16
|
+
When adapting techniques or making judgment calls about learning approaches, consult `references/PRINCIPLES.md` for the underlying learning science.
|
|
17
|
+
|
|
18
|
+
## When to offer exercises
|
|
19
|
+
|
|
20
|
+
Offer an optional 10-15 minute exercise after:
|
|
21
|
+
|
|
22
|
+
- Creating new files or modules
|
|
23
|
+
- Database schema changes
|
|
24
|
+
- Architectural decisions or refactors
|
|
25
|
+
- Implementing unfamiliar patterns
|
|
26
|
+
- Any work where the user asked "why" questions during development
|
|
27
|
+
|
|
28
|
+
Always ask before starting: "Would you like to do a quick learning exercise on [topic]? About 10-15 minutes."
|
|
29
|
+
|
|
30
|
+
## When NOT to offer
|
|
31
|
+
|
|
32
|
+
- User declined an exercise this session
|
|
33
|
+
- User already completed 2 exercises this session
|
|
34
|
+
- User signals urgency ("fix this quick", "just ship it", "deploy now")
|
|
35
|
+
- Pure debugging/hotfix context
|
|
36
|
+
|
|
37
|
+
Keep offers to one short sentence. Do not repeat or insist.
|
|
38
|
+
|
|
39
|
+
## Core principle: Pause for input
|
|
40
|
+
|
|
41
|
+
This is the most important rule. After posing a question:
|
|
42
|
+
|
|
43
|
+
1. **Stop generating immediately.** Do not continue after the question mark.
|
|
44
|
+
2. Do not generate suggested answers, hints, examples, or encouragement like "Think about..." or "Consider..."
|
|
45
|
+
3. Wait for the user's actual response before continuing.
|
|
46
|
+
|
|
47
|
+
Allowed after the question:
|
|
48
|
+
|
|
49
|
+
- "(Take your best guess — wrong predictions are useful data.)"
|
|
50
|
+
- "(Or we can skip this one.)"
|
|
51
|
+
|
|
52
|
+
After their response:
|
|
53
|
+
|
|
54
|
+
- If correct: confirm and deepen ("Exactly. And what would change if [variation]?")
|
|
55
|
+
- If wrong: **be direct** about what's incorrect, then explore the gap — this is high-value learning
|
|
56
|
+
|
|
57
|
+
## Exercise types
|
|
58
|
+
|
|
59
|
+
### 1. Predict then observe
|
|
60
|
+
|
|
61
|
+
Ask what they predict will happen in a specific scenario before revealing the answer.
|
|
62
|
+
|
|
63
|
+
```
|
|
64
|
+
Example:
|
|
65
|
+
User just created auth middleware.
|
|
66
|
+
|
|
67
|
+
Agent: "Would you like a quick learning exercise on middleware patterns?"
|
|
68
|
+
User: "sure"
|
|
69
|
+
Agent: "What do you think happens when a request hits your middleware with an expired token?
|
|
70
|
+
|
|
71
|
+
(Take your best guess — wrong predictions are useful data.)"
|
|
72
|
+
|
|
73
|
+
[STOP — wait for response]
|
|
74
|
+
|
|
75
|
+
After response:
|
|
76
|
+
Agent: "Actually [correct behavior]. The key difference is [explanation].
|
|
77
|
+
What surprised you about that?"
|
|
78
|
+
|
|
79
|
+
[STOP — wait for response]
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
### 2. Generate then compare
|
|
83
|
+
|
|
84
|
+
Ask them to sketch an approach before showing the actual implementation.
|
|
85
|
+
|
|
86
|
+
```
|
|
87
|
+
Example:
|
|
88
|
+
Agent: "Before I show you — how would you structure the error handling for this API endpoint?"
|
|
89
|
+
|
|
90
|
+
[STOP — wait for response]
|
|
91
|
+
|
|
92
|
+
After response:
|
|
93
|
+
Agent: "Here's what we went with: [implementation].
|
|
94
|
+
What's similar to your approach? What's different, and why do you think we chose this direction?"
|
|
95
|
+
|
|
96
|
+
[STOP — wait for response]
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
### 3. Teach it back
|
|
100
|
+
|
|
101
|
+
Ask them to explain a component as if to a new team member.
|
|
102
|
+
|
|
103
|
+
```
|
|
104
|
+
Example:
|
|
105
|
+
Agent: "Explain how the caching layer we just built works, as if I'm a new developer joining the project."
|
|
106
|
+
|
|
107
|
+
[STOP — wait for response]
|
|
108
|
+
|
|
109
|
+
After response:
|
|
110
|
+
Agent: "You nailed [specific part]. One thing to refine: [specific gap]."
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
## Hands-on code exploration
|
|
114
|
+
|
|
115
|
+
Prefer directing users to files over showing code snippets. Having learners locate code themselves builds codebase familiarity.
|
|
116
|
+
|
|
117
|
+
**Adjust guidance based on demonstrated familiarity:**
|
|
118
|
+
|
|
119
|
+
- Early: "Open `src/middleware/auth.ts`, around line 45. What does `validateToken` return?"
|
|
120
|
+
- Later: "Find where we handle token refresh."
|
|
121
|
+
- Eventually: "Where would you look to change how session expiry works?"
|
|
122
|
+
|
|
123
|
+
After they locate code, prompt self-explanation:
|
|
124
|
+
|
|
125
|
+
"You found it. Before I say anything — what do you think this line does?"
|
|
126
|
+
|
|
127
|
+
## Techniques to weave in naturally
|
|
128
|
+
|
|
129
|
+
- **"Why" questions:** "Why did we use a Map here instead of an object?"
|
|
130
|
+
- **Transfer prompts:** "This is the strategy pattern. Where else in this codebase might it apply?"
|
|
131
|
+
- **Varied context:** "We used this for auth — how would you apply it to API rate limiting?"
|
|
132
|
+
- **Error analysis:** "Here's a bug someone might introduce — what would go wrong and why?"
|
|
133
|
+
|
|
134
|
+
## Anti-patterns to avoid
|
|
135
|
+
|
|
136
|
+
- Dumping multiple questions at once
|
|
137
|
+
- Softening wrong answers into ambiguity ("well, that's partially right...")
|
|
138
|
+
- Offering exercises more than twice per session
|
|
139
|
+
- Making exercises feel like tests rather than exploration
|
|
140
|
+
- Continuing to generate after posing a question
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
# Learning Opportunities Examples
|
|
2
|
+
|
|
3
|
+
## Offer an exercise after creating a module
|
|
4
|
+
|
|
5
|
+
User just created auth middleware: "Done, that's the middleware working."
|
|
6
|
+
|
|
7
|
+
Good agent behavior:
|
|
8
|
+
|
|
9
|
+
- Offer one short, optional exercise: "Would you like a quick learning exercise on middleware patterns? About 10-15 minutes."
|
|
10
|
+
- If the user agrees, use a predict-then-observe exercise: ask what happens when a request hits the middleware with an expired token.
|
|
11
|
+
- Stop generating immediately after the question and wait for the user's answer.
|
|
12
|
+
- If the prediction is wrong, be direct about what's incorrect, then explore the gap.
|
|
13
|
+
|
|
14
|
+
## Teach it back after a refactor
|
|
15
|
+
|
|
16
|
+
User: "We just replaced the cache layer. I want to make sure I actually understand it."
|
|
17
|
+
|
|
18
|
+
Good agent behavior:
|
|
19
|
+
|
|
20
|
+
- Ask the user to explain the caching layer as if to a new developer joining the project.
|
|
21
|
+
- Stop after posing the question and wait for the response.
|
|
22
|
+
- Confirm the specific parts they nailed, then name one concrete gap to refine.
|
|
23
|
+
- Keep the exercise exploratory rather than test-like.
|
|
24
|
+
|
|
25
|
+
## Decline when the user is in a hurry
|
|
26
|
+
|
|
27
|
+
User: "Just ship it, this needs to go out now."
|
|
28
|
+
|
|
29
|
+
Good agent behavior:
|
|
30
|
+
|
|
31
|
+
- Recognize urgency and skip the exercise offer entirely.
|
|
32
|
+
- Avoid repeating the offer when the user has already declined once this session.
|
|
33
|
+
- Cap the session at two completed exercises and stop offering.
|
|
34
|
+
- Keep any offer to a single sentence without insisting.
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
# Learning Principles
|
|
2
|
+
|
|
3
|
+
Consult this file when adapting techniques or making judgment calls about learning approaches. These principles explain WHY the techniques in the main skill work.
|
|
4
|
+
|
|
5
|
+
## Generation Effect
|
|
6
|
+
|
|
7
|
+
Users encode information better when they produce it rather than passively consume it. Active retrieval strengthens memory traces in ways that passive review does not. This is why we ask for predictions and explanations before revealing answers.
|
|
8
|
+
|
|
9
|
+
## Pre-testing
|
|
10
|
+
|
|
11
|
+
Attempting to answer before learning new information produces stronger memory — even when the attempt is wrong. A failed attempt makes the correct answer more memorable by contrast. Wrong predictions are valuable data, not failures.
|
|
12
|
+
|
|
13
|
+
## Spacing Effect
|
|
14
|
+
|
|
15
|
+
Distributing learning over time beats cramming. This is why we use retrieval check-ins at session starts and limit exercises to 2 per session rather than drilling continuously.
|
|
16
|
+
|
|
17
|
+
## Desirable Difficulties
|
|
18
|
+
|
|
19
|
+
Conditions that make learning harder in the short term often produce better long-term retention. Exercises should require effort without being frustrating. Struggle during learning is a sign it's working, not failing.
|
|
20
|
+
|
|
21
|
+
## Fluency Illusion
|
|
22
|
+
|
|
23
|
+
When AI-generated code is clean and readable, users overestimate how well they understand it. The fluency of the output masks gaps in mental models. This is the primary risk this skill counteracts.
|
|
24
|
+
|
|
25
|
+
## Dynamic Testing
|
|
26
|
+
|
|
27
|
+
Errors during learning, when followed by clear corrective feedback, enhance retention compared to error-free learning. This is why we are direct about wrong answers rather than softening them.
|
|
28
|
+
|
|
29
|
+
## Transfer and Interleaving
|
|
30
|
+
|
|
31
|
+
Knowledge transfers better when connected to underlying principles and varied contexts. Asking "where else would this apply?" builds flexible knowledge rather than context-bound recall.
|
|
32
|
+
|
|
33
|
+
## Sources
|
|
34
|
+
|
|
35
|
+
- Bjork, R. A., Dunlosky, J., & Kornell, N. (2013). Self-regulated learning: Beliefs, techniques, and illusions.
|
|
36
|
+
- Dunlosky, J., et al. (2013). Improving students' learning with effective learning techniques.
|
|
37
|
+
- Giebl, S., et al. (2021). Answer first or Google first?
|
|
38
|
+
- Hicks, C. M., Lee, C. S., & Foster-Marks, K. (2025). The New Developer: AI Skill Threat, Identity Change & Developer Thriving.
|
|
39
|
+
- Roediger III, H. L., & Karpicke, J. D. (2006). The power of testing memory.
|
|
40
|
+
- Soderstrom, N. C., & Bjork, R. A. (2015). Learning versus performance: An integrative review.
|
|
41
|
+
- Tankelevitch, L., et al. (2024). The metacognitive demands and opportunities of generative AI.
|
|
42
|
+
- Hicks, C. (2025). Cognitive helmets for the AI bicycle. Fight for the Human.
|
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: perf-web-optimization
|
|
3
|
+
description: 'Optimize web performance: bundle size, images, caching, lazy loading, and overall page speed. Use when site is slow, reducing bundle size, fixing layout shifts, improving Time to Interactive, or optimizing for Lighthouse scores. Triggers on: web performance, bundle size, page speed, slow site, lazy loading. Do NOT use for Core Web Vitals-specific fixes (use core-web-vitals), running Lighthouse audits (use perf-lighthouse), or Astro-specific optimization (use perf-astro).'
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Web Performance Optimization
|
|
7
|
+
|
|
8
|
+
Systematic approach: Measure → Identify → Prioritize → Implement → Verify.
|
|
9
|
+
|
|
10
|
+
## Target Metrics
|
|
11
|
+
|
|
12
|
+
| Metric | Good | Needs Work | Poor |
|
|
13
|
+
| ------ | ------- | ---------- | ------- |
|
|
14
|
+
| LCP | < 2.5s | 2.5-4s | > 4s |
|
|
15
|
+
| INP | < 200ms | 200-500ms | > 500ms |
|
|
16
|
+
| CLS | < 0.1 | 0.1-0.25 | > 0.25 |
|
|
17
|
+
| TTFB | < 800ms | 800ms-1.8s | > 1.8s |
|
|
18
|
+
|
|
19
|
+
## Quick Wins
|
|
20
|
+
|
|
21
|
+
### 1. Images (usually biggest impact on LCP)
|
|
22
|
+
|
|
23
|
+
```html
|
|
24
|
+
<!-- Hero/LCP image: eager + high priority -->
|
|
25
|
+
<img src="/hero.webp" alt="Hero" width="1200" height="600" loading="eager" fetchpriority="high" decoding="async" />
|
|
26
|
+
|
|
27
|
+
<!-- Below fold: lazy load -->
|
|
28
|
+
<img src="/product.webp" alt="Product" width="400" height="300" loading="lazy" decoding="async" />
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
Always set `width` and `height` to prevent CLS.
|
|
32
|
+
|
|
33
|
+
### 2. Fonts (common LCP/CLS culprit)
|
|
34
|
+
|
|
35
|
+
```html
|
|
36
|
+
<!-- Preconnect to font origin -->
|
|
37
|
+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
|
38
|
+
|
|
39
|
+
<!-- Non-blocking font load -->
|
|
40
|
+
<link
|
|
41
|
+
rel="stylesheet"
|
|
42
|
+
href="https://fonts.googleapis.com/css2?family=Inter&display=swap"
|
|
43
|
+
media="print"
|
|
44
|
+
onload="this.media='all'"
|
|
45
|
+
/>
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
### 3. Third-party Scripts (common INP killer)
|
|
49
|
+
|
|
50
|
+
```html
|
|
51
|
+
<!-- Defer to user interaction -->
|
|
52
|
+
<script>
|
|
53
|
+
function loadThirdParty() {
|
|
54
|
+
// Load analytics, chat widgets, etc.
|
|
55
|
+
}
|
|
56
|
+
;['scroll', 'click', 'touchstart'].forEach((e) => addEventListener(e, loadThirdParty, { once: true, passive: true }))
|
|
57
|
+
setTimeout(loadThirdParty, 5000)
|
|
58
|
+
</script>
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
### 4. Critical CSS
|
|
62
|
+
|
|
63
|
+
Inline critical CSS in `<head>`, defer the rest:
|
|
64
|
+
|
|
65
|
+
```html
|
|
66
|
+
<style>
|
|
67
|
+
/* critical styles */
|
|
68
|
+
</style>
|
|
69
|
+
<link rel="preload" href="/styles.css" as="style" onload="this.rel='stylesheet'" />
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
## Bundle Analysis
|
|
73
|
+
|
|
74
|
+
```bash
|
|
75
|
+
# Webpack
|
|
76
|
+
npx webpack-bundle-analyzer dist/stats.json
|
|
77
|
+
|
|
78
|
+
# Vite
|
|
79
|
+
npx vite-bundle-visualizer
|
|
80
|
+
|
|
81
|
+
# Check package size before installing
|
|
82
|
+
npx bundlephobia <package-name>
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
Common heavy packages to replace:
|
|
86
|
+
|
|
87
|
+
- `moment` (67KB) → `date-fns` (12KB) or `dayjs` (2KB)
|
|
88
|
+
- `lodash` (72KB) → cherry-pick imports or native methods
|
|
89
|
+
|
|
90
|
+
## Code Splitting Patterns
|
|
91
|
+
|
|
92
|
+
```javascript
|
|
93
|
+
// React lazy
|
|
94
|
+
const Chart = lazy(() => import('./Chart'))
|
|
95
|
+
|
|
96
|
+
// Next.js dynamic
|
|
97
|
+
const Admin = dynamic(() => import('./Admin'), { ssr: false })
|
|
98
|
+
|
|
99
|
+
// Vite/Rollup manual chunks
|
|
100
|
+
build: {
|
|
101
|
+
rollupOptions: {
|
|
102
|
+
output: {
|
|
103
|
+
manualChunks: {
|
|
104
|
+
vendor: ['react', 'react-dom']
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
## Caching Headers
|
|
112
|
+
|
|
113
|
+
```
|
|
114
|
+
# Static assets (immutable hash in filename)
|
|
115
|
+
Cache-Control: public, max-age=31536000, immutable
|
|
116
|
+
|
|
117
|
+
# HTML (revalidate)
|
|
118
|
+
Cache-Control: no-cache
|
|
119
|
+
|
|
120
|
+
# API responses
|
|
121
|
+
Cache-Control: private, max-age=0, must-revalidate
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
## Measurement
|
|
125
|
+
|
|
126
|
+
For running audits, reading reports, and setting budgets, use the **perf-lighthouse** skill.
|
|
127
|
+
|
|
128
|
+
## Checklist
|
|
129
|
+
|
|
130
|
+
### Images
|
|
131
|
+
|
|
132
|
+
- [ ] Modern formats (WebP/AVIF)
|
|
133
|
+
- [ ] Responsive `srcset`
|
|
134
|
+
- [ ] `width`/`height` attributes
|
|
135
|
+
- [ ] `loading="lazy"` below fold
|
|
136
|
+
- [ ] `fetchpriority="high"` on LCP image
|
|
137
|
+
|
|
138
|
+
### JavaScript
|
|
139
|
+
|
|
140
|
+
- [ ] Bundle < 200KB gzipped
|
|
141
|
+
- [ ] Code splitting by route
|
|
142
|
+
- [ ] Third-party scripts deferred
|
|
143
|
+
- [ ] No unused dependencies
|
|
144
|
+
|
|
145
|
+
### CSS
|
|
146
|
+
|
|
147
|
+
- [ ] Critical CSS inlined
|
|
148
|
+
- [ ] Non-critical CSS deferred
|
|
149
|
+
- [ ] No unused CSS
|
|
150
|
+
|
|
151
|
+
### Fonts
|
|
152
|
+
|
|
153
|
+
- [ ] `font-display: swap`
|
|
154
|
+
- [ ] Preconnect to font origin
|
|
155
|
+
- [ ] Subset if possible
|
|
156
|
+
|
|
157
|
+
## Detailed Examples
|
|
158
|
+
|
|
159
|
+
For in-depth optimization patterns, see:
|
|
160
|
+
|
|
161
|
+
- [references/core-web-vitals.md](references/core-web-vitals.md) - Fixing LCP, CLS, INP issues
|
|
162
|
+
- [references/bundle-optimization.md](references/bundle-optimization.md) - Reducing JS bundle size
|
|
163
|
+
- [references/image-optimization.md](references/image-optimization.md) - Image formats, responsive images, sharp scripts
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
# Web Performance Optimization Examples
|
|
2
|
+
|
|
3
|
+
## Slow landing page
|
|
4
|
+
|
|
5
|
+
User: "Our landing page takes forever to load. Make it faster."
|
|
6
|
+
|
|
7
|
+
Good agent behavior:
|
|
8
|
+
|
|
9
|
+
- Follow the measure-identify-prioritize-implement-verify cycle rather than guessing.
|
|
10
|
+
- Start with the highest-impact quick wins: LCP image loading with `fetchpriority="high"`, explicit dimensions, and modern formats.
|
|
11
|
+
- Fix font loading with `font-display: swap` and preconnect to the font origin.
|
|
12
|
+
- Verify against target metrics (LCP < 2.5s, INP < 200ms, CLS < 0.1) before calling it done.
|
|
13
|
+
|
|
14
|
+
## Reduce JavaScript bundle size
|
|
15
|
+
|
|
16
|
+
User: "The main bundle is over 1MB. How do we cut it down?"
|
|
17
|
+
|
|
18
|
+
Good agent behavior:
|
|
19
|
+
|
|
20
|
+
- Run a bundle analyzer (webpack or Vite) to find the heavy dependencies before proposing swaps.
|
|
21
|
+
- Replace large packages like `moment` with lighter alternatives when the API allows.
|
|
22
|
+
- Add route-level code splitting with lazy imports and vendor chunking.
|
|
23
|
+
- Defer third-party scripts to user interaction rather than loading them eagerly.
|
|
24
|
+
- Confirm the gzipped bundle is under 200KB afterward.
|
|
25
|
+
|
|
26
|
+
## Fix layout shift on product pages
|
|
27
|
+
|
|
28
|
+
User: "The images keep jumping around while the page loads."
|
|
29
|
+
|
|
30
|
+
Good agent behavior:
|
|
31
|
+
|
|
32
|
+
- Recognize CLS as the metric and add explicit `width`/`height` attributes to all images.
|
|
33
|
+
- Reserve space for below-fold content instead of letting it shift on load.
|
|
34
|
+
- Lazy load below-the-fold images while keeping the LCP image eager and high priority.
|
|
35
|
+
- Verify the CLS score drops below 0.1 after the change.
|
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
# Bundle Size Optimization
|
|
2
|
+
|
|
3
|
+
## Table of Contents
|
|
4
|
+
- [Analysis Tools](#analysis-tools)
|
|
5
|
+
- [Heavy Dependencies](#heavy-dependencies)
|
|
6
|
+
- [Code Splitting](#code-splitting)
|
|
7
|
+
- [Tree Shaking](#tree-shaking)
|
|
8
|
+
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
## Analysis Tools
|
|
12
|
+
|
|
13
|
+
```bash
|
|
14
|
+
# Webpack - generates interactive treemap
|
|
15
|
+
npx webpack-bundle-analyzer dist/stats.json
|
|
16
|
+
|
|
17
|
+
# Generate stats file first
|
|
18
|
+
webpack --profile --json > dist/stats.json
|
|
19
|
+
|
|
20
|
+
# Vite
|
|
21
|
+
npx vite-bundle-visualizer
|
|
22
|
+
|
|
23
|
+
# Source map explorer
|
|
24
|
+
npx source-map-explorer dist/**/*.js
|
|
25
|
+
|
|
26
|
+
# Check package size before adding
|
|
27
|
+
npx bundlephobia lodash
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
---
|
|
31
|
+
|
|
32
|
+
## Heavy Dependencies
|
|
33
|
+
|
|
34
|
+
### moment → date-fns/dayjs
|
|
35
|
+
|
|
36
|
+
```javascript
|
|
37
|
+
// Before: moment (67KB)
|
|
38
|
+
import moment from 'moment';
|
|
39
|
+
moment(date).format('YYYY-MM-DD');
|
|
40
|
+
|
|
41
|
+
// After: date-fns (tree-shakeable, ~2KB per function)
|
|
42
|
+
import { format } from 'date-fns';
|
|
43
|
+
format(date, 'yyyy-MM-dd');
|
|
44
|
+
|
|
45
|
+
// After: dayjs (2KB total, moment-compatible API)
|
|
46
|
+
import dayjs from 'dayjs';
|
|
47
|
+
dayjs(date).format('YYYY-MM-DD');
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
### lodash → cherry-pick or native
|
|
51
|
+
|
|
52
|
+
```javascript
|
|
53
|
+
// Before: entire lodash (72KB)
|
|
54
|
+
import _ from 'lodash';
|
|
55
|
+
_.uniq(array);
|
|
56
|
+
_.debounce(fn, 300);
|
|
57
|
+
|
|
58
|
+
// After: cherry-pick (2KB each)
|
|
59
|
+
import uniq from 'lodash/uniq';
|
|
60
|
+
import debounce from 'lodash/debounce';
|
|
61
|
+
|
|
62
|
+
// After: native alternatives
|
|
63
|
+
[...new Set(array)]; // uniq
|
|
64
|
+
// debounce - use custom or lodash-es/debounce
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
### Other common swaps
|
|
68
|
+
|
|
69
|
+
| Heavy | Light Alternative |
|
|
70
|
+
|-------|-------------------|
|
|
71
|
+
| `axios` (13KB) | `fetch` (native) or `ky` (3KB) |
|
|
72
|
+
| `uuid` (4KB) | `crypto.randomUUID()` (native) |
|
|
73
|
+
| `classnames` (1KB) | template literals |
|
|
74
|
+
|
|
75
|
+
---
|
|
76
|
+
|
|
77
|
+
## Code Splitting
|
|
78
|
+
|
|
79
|
+
### React.lazy
|
|
80
|
+
|
|
81
|
+
```javascript
|
|
82
|
+
import { lazy, Suspense } from 'react';
|
|
83
|
+
|
|
84
|
+
const Chart = lazy(() => import('./Chart'));
|
|
85
|
+
const AdminPanel = lazy(() => import('./AdminPanel'));
|
|
86
|
+
|
|
87
|
+
function App() {
|
|
88
|
+
return (
|
|
89
|
+
<Suspense fallback={<Loading />}>
|
|
90
|
+
{showChart && <Chart />}
|
|
91
|
+
{isAdmin && <AdminPanel />}
|
|
92
|
+
</Suspense>
|
|
93
|
+
);
|
|
94
|
+
}
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
### Next.js dynamic
|
|
98
|
+
|
|
99
|
+
```javascript
|
|
100
|
+
import dynamic from 'next/dynamic';
|
|
101
|
+
|
|
102
|
+
// Client-only component
|
|
103
|
+
const Map = dynamic(() => import('./Map'), { ssr: false });
|
|
104
|
+
|
|
105
|
+
// With loading state
|
|
106
|
+
const Chart = dynamic(() => import('./Chart'), {
|
|
107
|
+
loading: () => <Skeleton height={300} />
|
|
108
|
+
});
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
### Route-based splitting (automatic in most frameworks)
|
|
112
|
+
|
|
113
|
+
```javascript
|
|
114
|
+
// Next.js - each page is a separate chunk
|
|
115
|
+
// pages/dashboard.js → chunks/pages/dashboard.js
|
|
116
|
+
// pages/admin.js → chunks/pages/admin.js
|
|
117
|
+
|
|
118
|
+
// React Router with lazy
|
|
119
|
+
const Dashboard = lazy(() => import('./pages/Dashboard'));
|
|
120
|
+
const Admin = lazy(() => import('./pages/Admin'));
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
### Manual chunks (Vite/Rollup)
|
|
124
|
+
|
|
125
|
+
```javascript
|
|
126
|
+
// vite.config.js
|
|
127
|
+
export default {
|
|
128
|
+
build: {
|
|
129
|
+
rollupOptions: {
|
|
130
|
+
output: {
|
|
131
|
+
manualChunks: {
|
|
132
|
+
vendor: ['react', 'react-dom'],
|
|
133
|
+
charts: ['recharts', 'd3'],
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
};
|
|
139
|
+
```
|
|
140
|
+
|
|
141
|
+
---
|
|
142
|
+
|
|
143
|
+
## Tree Shaking
|
|
144
|
+
|
|
145
|
+
### Enable in webpack
|
|
146
|
+
|
|
147
|
+
```javascript
|
|
148
|
+
// webpack.config.js
|
|
149
|
+
module.exports = {
|
|
150
|
+
mode: 'production', // enables tree shaking
|
|
151
|
+
optimization: {
|
|
152
|
+
usedExports: true,
|
|
153
|
+
sideEffects: true,
|
|
154
|
+
}
|
|
155
|
+
};
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
### Mark package as side-effect free
|
|
159
|
+
|
|
160
|
+
```json
|
|
161
|
+
// package.json
|
|
162
|
+
{
|
|
163
|
+
"sideEffects": false
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
// Or specify files with side effects
|
|
167
|
+
{
|
|
168
|
+
"sideEffects": ["*.css", "*.scss"]
|
|
169
|
+
}
|
|
170
|
+
```
|
|
171
|
+
|
|
172
|
+
### Write tree-shakeable exports
|
|
173
|
+
|
|
174
|
+
```javascript
|
|
175
|
+
// Bad: default export of object
|
|
176
|
+
export default { foo, bar, baz };
|
|
177
|
+
|
|
178
|
+
// Good: named exports
|
|
179
|
+
export { foo, bar, baz };
|
|
180
|
+
```
|