@vodailoc/kilo-kit-mcp 1.1.0 → 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.
- package/.mcp/kilo-kit.codex-windows.toml +5 -0
- package/LICENSE +190 -190
- package/QUICKSTART.md +265 -255
- package/README.md +321 -267
- package/mcp/README.md +64 -12
- package/mcp/dist/formatters.js +142 -1
- package/mcp/dist/orchestration-audit.js +20 -0
- package/mcp/dist/orchestration-memory.js +258 -0
- package/mcp/dist/orchestration-types.js +1 -0
- package/mcp/dist/orchestrator.js +222 -0
- package/mcp/dist/question-templates.js +249 -0
- package/mcp/dist/route-analytics.js +149 -0
- package/mcp/dist/router.js +75 -82
- package/mcp/dist/routing-policy-data.js +241 -0
- package/mcp/dist/routing-policy.js +145 -0
- package/mcp/dist/server.js +93 -4
- package/mcp/dist/smoke-env.js +18 -0
- package/mcp/dist/smoke.js +68 -1
- package/mcp/package.json +1 -2
- package/package.json +3 -2
- package/skills/README.md +647 -647
- package/skills/SKILLS_INDEX.md +139 -139
- package/skills/ai-media/ai-multimodal/.env.example +97 -97
- package/skills/ai-media/ai-multimodal/SKILL.md +357 -357
- package/skills/ai-media/ai-multimodal/references/audio-processing.md +373 -373
- package/skills/ai-media/ai-multimodal/references/image-generation.md +558 -558
- package/skills/ai-media/ai-multimodal/references/video-analysis.md +502 -502
- package/skills/ai-media/ai-multimodal/references/vision-understanding.md +483 -483
- package/skills/ai-media/ai-multimodal/scripts/document_converter.py +395 -395
- package/skills/ai-media/ai-multimodal/scripts/gemini_batch_process.py +480 -480
- package/skills/ai-media/ai-multimodal/scripts/media_optimizer.py +506 -506
- package/skills/ai-media/ai-multimodal/scripts/requirements.txt +26 -26
- package/skills/ai-media/ai-multimodal/scripts/tests/requirements.txt +20 -20
- package/skills/ai-media/ai-multimodal/scripts/tests/test_document_converter.py +299 -299
- package/skills/ai-media/ai-multimodal/scripts/tests/test_gemini_batch_process.py +362 -362
- package/skills/ai-media/ai-multimodal/scripts/tests/test_media_optimizer.py +373 -373
- package/skills/ai-media/media-processing/SKILL.md +358 -358
- package/skills/ai-media/media-processing/references/ffmpeg-encoding.md +358 -358
- package/skills/ai-media/media-processing/references/ffmpeg-filters.md +503 -503
- package/skills/ai-media/media-processing/references/ffmpeg-streaming.md +403 -403
- package/skills/ai-media/media-processing/references/format-compatibility.md +375 -375
- package/skills/ai-media/media-processing/references/imagemagick-batch.md +612 -612
- package/skills/ai-media/media-processing/references/imagemagick-editing.md +623 -623
- package/skills/ai-media/media-processing/scripts/batch_resize.py +342 -342
- package/skills/ai-media/media-processing/scripts/media_convert.py +311 -311
- package/skills/ai-media/media-processing/scripts/requirements.txt +24 -24
- package/skills/ai-media/media-processing/scripts/tests/requirements.txt +2 -2
- package/skills/ai-media/media-processing/scripts/tests/test_batch_resize.py +372 -372
- package/skills/ai-media/media-processing/scripts/tests/test_media_convert.py +259 -259
- package/skills/ai-media/media-processing/scripts/tests/test_video_optimize.py +397 -397
- package/skills/ai-media/media-processing/scripts/video_optimize.py +414 -414
- package/skills/ai-media/screenshot/LICENSE.txt +201 -201
- package/skills/ai-media/screenshot/SKILL.md +267 -267
- package/skills/ai-media/screenshot/agents/openai.yaml +6 -6
- package/skills/ai-media/screenshot/assets/screenshot-small.svg +5 -5
- package/skills/ai-media/screenshot/scripts/ensure_macos_permissions.sh +54 -54
- package/skills/ai-media/screenshot/scripts/macos_display_info.swift +22 -22
- package/skills/ai-media/screenshot/scripts/macos_permissions.swift +40 -40
- package/skills/ai-media/screenshot/scripts/macos_window_info.swift +126 -126
- package/skills/ai-media/screenshot/scripts/take_screenshot.ps1 +163 -163
- package/skills/ai-media/screenshot/scripts/take_screenshot.py +585 -585
- package/skills/ai-media/sora/LICENSE.txt +201 -201
- package/skills/ai-media/sora/SKILL.md +153 -153
- package/skills/ai-media/sora/agents/openai.yaml +6 -6
- package/skills/ai-media/sora/assets/sora-small.svg +4 -4
- package/skills/ai-media/sora/references/cinematic-shots.md +53 -53
- package/skills/ai-media/sora/references/cli.md +248 -248
- package/skills/ai-media/sora/references/codex-network.md +28 -28
- package/skills/ai-media/sora/references/prompting.md +137 -137
- package/skills/ai-media/sora/references/sample-prompts.md +95 -95
- package/skills/ai-media/sora/references/social-ads.md +42 -42
- package/skills/ai-media/sora/references/troubleshooting.md +58 -58
- package/skills/ai-media/sora/references/video-api.md +45 -45
- package/skills/ai-media/sora/scripts/sora.py +970 -970
- package/skills/design/aesthetic/SKILL.md +121 -121
- package/skills/design/aesthetic/assets/design-guideline-template.md +163 -163
- package/skills/design/aesthetic/assets/design-story-template.md +135 -135
- package/skills/design/aesthetic/references/design-principles.md +62 -62
- package/skills/design/aesthetic/references/design-resources.md +75 -75
- package/skills/design/aesthetic/references/micro-interactions.md +53 -53
- package/skills/design/aesthetic/references/storytelling-design.md +50 -50
- package/skills/design/figma/LICENSE.txt +202 -202
- package/skills/design/figma/SKILL.md +42 -42
- package/skills/design/figma/agents/openai.yaml +14 -14
- package/skills/design/figma/assets/figma-small.svg +3 -3
- package/skills/design/figma/assets/icon.svg +28 -28
- package/skills/design/figma/references/figma-mcp-config.md +35 -35
- package/skills/design/figma/references/figma-tools-and-prompts.md +34 -34
- package/skills/design/figma-implement-design/LICENSE.txt +202 -202
- package/skills/design/figma-implement-design/SKILL.md +264 -264
- package/skills/design/figma-implement-design/agents/openai.yaml +14 -14
- package/skills/design/figma-implement-design/assets/figma-small.svg +3 -3
- package/skills/design/figma-implement-design/assets/icon.svg +28 -28
- package/skills/design/frontend-design/SKILL.md +41 -41
- package/skills/design/frontend-design/references/animejs.md +395 -395
- package/skills/design/ui-styling/LICENSE.txt +201 -201
- package/skills/design/ui-styling/SKILL.md +321 -321
- package/skills/design/ui-styling/canvas-fonts/ArsenalSC-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/BigShoulders-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Boldonse-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/BricolageGrotesque-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/CrimsonPro-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/DMMono-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/EricaOne-OFL.txt +94 -94
- package/skills/design/ui-styling/canvas-fonts/GeistMono-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Gloock-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/IBMPlexMono-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/InstrumentSans-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Italiana-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/JetBrainsMono-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Jura-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/LibreBaskerville-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Lora-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/NationalPark-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/NothingYouCouldDo-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Outfit-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/PixelifySans-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/PoiretOne-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/RedHatMono-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Silkscreen-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/SmoochSans-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/Tektur-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/WorkSans-OFL.txt +93 -93
- package/skills/design/ui-styling/canvas-fonts/YoungSerif-OFL.txt +93 -93
- package/skills/design/ui-styling/references/canvas-design-system.md +320 -320
- package/skills/design/ui-styling/references/shadcn-accessibility.md +471 -471
- package/skills/design/ui-styling/references/shadcn-components.md +424 -424
- package/skills/design/ui-styling/references/shadcn-theming.md +373 -373
- package/skills/design/ui-styling/references/tailwind-customization.md +483 -483
- package/skills/design/ui-styling/references/tailwind-responsive.md +382 -382
- package/skills/design/ui-styling/references/tailwind-utilities.md +455 -455
- package/skills/design/ui-styling/scripts/requirements.txt +17 -17
- package/skills/design/ui-styling/scripts/shadcn_add.py +292 -292
- package/skills/design/ui-styling/scripts/tailwind_config_gen.py +456 -456
- package/skills/design/ui-styling/scripts/tests/requirements.txt +3 -3
- package/skills/design/ui-styling/scripts/tests/test_shadcn_add.py +266 -266
- package/skills/design/ui-styling/scripts/tests/test_tailwind_config_gen.py +336 -336
- package/skills/engineering/aspnet-core/LICENSE.txt +201 -201
- package/skills/engineering/aspnet-core/SKILL.md +61 -61
- package/skills/engineering/aspnet-core/agents/openai.yaml +5 -5
- package/skills/engineering/aspnet-core/references/_sections.md +40 -40
- package/skills/engineering/aspnet-core/references/apis-minimal-and-controllers.md +81 -81
- package/skills/engineering/aspnet-core/references/data-state-and-services.md +69 -69
- package/skills/engineering/aspnet-core/references/program-and-pipeline.md +103 -103
- package/skills/engineering/aspnet-core/references/realtime-grpc-and-background-work.md +58 -58
- package/skills/engineering/aspnet-core/references/security-and-identity.md +75 -75
- package/skills/engineering/aspnet-core/references/source-map.md +43 -43
- package/skills/engineering/aspnet-core/references/stack-selection.md +63 -63
- package/skills/engineering/aspnet-core/references/testing-performance-and-operations.md +92 -92
- package/skills/engineering/aspnet-core/references/ui-blazor.md +53 -53
- package/skills/engineering/aspnet-core/references/ui-mvc.md +56 -56
- package/skills/engineering/aspnet-core/references/ui-razor-pages.md +55 -55
- package/skills/engineering/aspnet-core/references/versioning-and-upgrades.md +51 -51
- package/skills/engineering/backend-development/SKILL.md +95 -95
- package/skills/engineering/backend-development/references/backend-api-design.md +495 -495
- package/skills/engineering/backend-development/references/backend-architecture.md +454 -454
- package/skills/engineering/backend-development/references/backend-authentication.md +338 -338
- package/skills/engineering/backend-development/references/backend-code-quality.md +659 -659
- package/skills/engineering/backend-development/references/backend-debugging.md +904 -904
- package/skills/engineering/backend-development/references/backend-devops.md +494 -494
- package/skills/engineering/backend-development/references/backend-mindset.md +387 -387
- package/skills/engineering/backend-development/references/backend-performance.md +397 -397
- package/skills/engineering/backend-development/references/backend-security.md +290 -290
- package/skills/engineering/backend-development/references/backend-technologies.md +256 -256
- package/skills/engineering/backend-development/references/backend-testing.md +429 -429
- package/skills/engineering/better-auth/SKILL.md +204 -204
- package/skills/engineering/better-auth/references/advanced-features.md +553 -553
- package/skills/engineering/better-auth/references/database-integration.md +577 -577
- package/skills/engineering/better-auth/references/email-password-auth.md +416 -416
- package/skills/engineering/better-auth/references/oauth-providers.md +430 -430
- package/skills/engineering/better-auth/scripts/better_auth_init.py +521 -521
- package/skills/engineering/better-auth/scripts/requirements.txt +15 -15
- package/skills/engineering/better-auth/scripts/tests/test_better_auth_init.py +421 -421
- package/skills/engineering/code-review/SKILL.md +140 -140
- package/skills/engineering/code-review/references/code-review-reception.md +208 -208
- package/skills/engineering/code-review/references/requesting-code-review.md +104 -104
- package/skills/engineering/code-review/references/verification-before-completion.md +138 -138
- package/skills/engineering/context-engineering/SKILL.md +86 -86
- package/skills/engineering/context-engineering/references/context-compression.md +84 -84
- package/skills/engineering/context-engineering/references/context-degradation.md +93 -93
- package/skills/engineering/context-engineering/references/context-fundamentals.md +75 -75
- package/skills/engineering/context-engineering/references/context-optimization.md +82 -82
- package/skills/engineering/context-engineering/references/evaluation.md +89 -89
- package/skills/engineering/context-engineering/references/memory-systems.md +88 -88
- package/skills/engineering/context-engineering/references/multi-agent-patterns.md +90 -90
- package/skills/engineering/context-engineering/references/project-development.md +97 -97
- package/skills/engineering/context-engineering/references/tool-design.md +86 -86
- package/skills/engineering/context-engineering/scripts/compression_evaluator.py +329 -329
- package/skills/engineering/context-engineering/scripts/context_analyzer.py +294 -294
- package/skills/engineering/databases/SKILL.md +232 -232
- package/skills/engineering/databases/references/mongodb-aggregation.md +447 -447
- package/skills/engineering/databases/references/mongodb-atlas.md +465 -465
- package/skills/engineering/databases/references/mongodb-crud.md +408 -408
- package/skills/engineering/databases/references/mongodb-indexing.md +442 -442
- package/skills/engineering/databases/references/postgresql-administration.md +594 -594
- package/skills/engineering/databases/references/postgresql-performance.md +527 -527
- package/skills/engineering/databases/references/postgresql-psql-cli.md +467 -467
- package/skills/engineering/databases/references/postgresql-queries.md +475 -475
- package/skills/engineering/databases/scripts/db_backup.py +502 -502
- package/skills/engineering/databases/scripts/db_migrate.py +414 -414
- package/skills/engineering/databases/scripts/db_performance_check.py +444 -444
- package/skills/engineering/databases/scripts/requirements.txt +20 -20
- package/skills/engineering/databases/scripts/tests/requirements.txt +4 -4
- package/skills/engineering/databases/scripts/tests/test_db_backup.py +340 -340
- package/skills/engineering/databases/scripts/tests/test_db_migrate.py +277 -277
- package/skills/engineering/databases/scripts/tests/test_db_performance_check.py +370 -370
- package/skills/engineering/diagnose/SKILL.md +117 -117
- package/skills/engineering/diagnose/scripts/hitl-loop.template.sh +41 -41
- package/skills/engineering/docs-seeker/SKILL.md +207 -207
- package/skills/engineering/docs-seeker/WORKFLOWS.md +505 -505
- package/skills/engineering/docs-seeker/references/best-practices.md +632 -632
- package/skills/engineering/docs-seeker/references/documentation-sources.md +461 -461
- package/skills/engineering/docs-seeker/references/error-handling.md +621 -621
- package/skills/engineering/docs-seeker/references/limitations.md +821 -821
- package/skills/engineering/docs-seeker/references/performance.md +574 -574
- package/skills/engineering/docs-seeker/references/tool-selection.md +262 -262
- package/skills/engineering/frontend-development/SKILL.md +398 -398
- package/skills/engineering/frontend-development/resources/common-patterns.md +330 -330
- package/skills/engineering/frontend-development/resources/complete-examples.md +871 -871
- package/skills/engineering/frontend-development/resources/component-patterns.md +501 -501
- package/skills/engineering/frontend-development/resources/data-fetching.md +766 -766
- package/skills/engineering/frontend-development/resources/file-organization.md +501 -501
- package/skills/engineering/frontend-development/resources/loading-and-error-states.md +500 -500
- package/skills/engineering/frontend-development/resources/performance.md +405 -405
- package/skills/engineering/frontend-development/resources/routing-guide.md +363 -363
- package/skills/engineering/frontend-development/resources/styling-guide.md +427 -427
- package/skills/engineering/frontend-development/resources/typescript-standards.md +417 -417
- package/skills/engineering/improve-codebase-architecture/DEEPENING.md +37 -37
- package/skills/engineering/improve-codebase-architecture/INTERFACE-DESIGN.md +44 -44
- package/skills/engineering/improve-codebase-architecture/LANGUAGE.md +53 -53
- package/skills/engineering/improve-codebase-architecture/SKILL.md +71 -71
- package/skills/engineering/openai-docs/LICENSE.txt +201 -201
- package/skills/engineering/openai-docs/SKILL.md +69 -69
- package/skills/engineering/openai-docs/agents/openai.yaml +14 -14
- package/skills/engineering/openai-docs/assets/openai-small.svg +3 -3
- package/skills/engineering/openai-docs/references/gpt-5p4-prompting-guide.md +433 -433
- package/skills/engineering/openai-docs/references/latest-model.md +35 -35
- package/skills/engineering/openai-docs/references/upgrading-to-gpt-5p4.md +164 -164
- package/skills/engineering/playwright/LICENSE.txt +201 -201
- package/skills/engineering/playwright/NOTICE.txt +14 -14
- package/skills/engineering/playwright/SKILL.md +147 -147
- package/skills/engineering/playwright/agents/openai.yaml +6 -6
- package/skills/engineering/playwright/assets/playwright-small.svg +3 -3
- package/skills/engineering/playwright/references/cli.md +116 -116
- package/skills/engineering/playwright/references/workflows.md +95 -95
- package/skills/engineering/playwright/scripts/playwright_cli.sh +25 -25
- package/skills/engineering/playwright-interactive/LICENSE.txt +201 -201
- package/skills/engineering/playwright-interactive/NOTICE.txt +13 -13
- package/skills/engineering/playwright-interactive/SKILL.md +689 -689
- package/skills/engineering/playwright-interactive/agents/openai.yaml +6 -6
- package/skills/engineering/playwright-interactive/assets/playwright-small.svg +3 -3
- package/skills/engineering/render-deploy/LICENSE.txt +201 -201
- package/skills/engineering/render-deploy/SKILL.md +479 -479
- package/skills/engineering/render-deploy/agents/openai.yaml +14 -14
- package/skills/engineering/render-deploy/assets/docker.yaml +62 -62
- package/skills/engineering/render-deploy/assets/go-api.yaml +35 -35
- package/skills/engineering/render-deploy/assets/nextjs-postgres.yaml +35 -35
- package/skills/engineering/render-deploy/assets/node-express.yaml +25 -25
- package/skills/engineering/render-deploy/assets/python-django.yaml +89 -89
- package/skills/engineering/render-deploy/assets/render-small.svg +3 -3
- package/skills/engineering/render-deploy/assets/static-site.yaml +54 -54
- package/skills/engineering/render-deploy/references/blueprint-spec.md +718 -718
- package/skills/engineering/render-deploy/references/codebase-analysis.md +49 -49
- package/skills/engineering/render-deploy/references/configuration-guide.md +603 -603
- package/skills/engineering/render-deploy/references/deployment-details.md +224 -224
- package/skills/engineering/render-deploy/references/direct-creation.md +113 -113
- package/skills/engineering/render-deploy/references/error-patterns.md +13 -13
- package/skills/engineering/render-deploy/references/post-deploy-checks.md +36 -36
- package/skills/engineering/render-deploy/references/runtimes.md +473 -473
- package/skills/engineering/render-deploy/references/service-types.md +450 -450
- package/skills/engineering/render-deploy/references/troubleshooting-basics.md +36 -36
- package/skills/engineering/repomix/SKILL.md +215 -215
- package/skills/engineering/repomix/references/configuration.md +211 -211
- package/skills/engineering/repomix/references/usage-patterns.md +232 -232
- package/skills/engineering/repomix/scripts/README.md +179 -179
- package/skills/engineering/repomix/scripts/repomix_batch.py +455 -455
- package/skills/engineering/repomix/scripts/repos.example.json +15 -15
- package/skills/engineering/repomix/scripts/requirements.txt +15 -15
- package/skills/engineering/repomix/scripts/tests/test_repomix_batch.py +531 -531
- package/skills/engineering/setup-matt-pocock-skills/SKILL.md +121 -121
- package/skills/engineering/setup-matt-pocock-skills/domain.md +51 -51
- package/skills/engineering/setup-matt-pocock-skills/issue-tracker-github.md +22 -22
- package/skills/engineering/setup-matt-pocock-skills/issue-tracker-gitlab.md +23 -23
- package/skills/engineering/setup-matt-pocock-skills/issue-tracker-local.md +19 -19
- package/skills/engineering/setup-matt-pocock-skills/triage-labels.md +15 -15
- package/skills/engineering/shopify/README.md +66 -66
- package/skills/engineering/shopify/SKILL.md +319 -319
- package/skills/engineering/shopify/references/app-development.md +470 -470
- package/skills/engineering/shopify/references/extensions.md +493 -493
- package/skills/engineering/shopify/references/themes.md +498 -498
- package/skills/engineering/shopify/scripts/requirements.txt +19 -19
- package/skills/engineering/shopify/scripts/shopify_init.py +423 -423
- package/skills/engineering/shopify/scripts/tests/test_shopify_init.py +385 -385
- package/skills/engineering/tdd/SKILL.md +109 -109
- package/skills/engineering/tdd/deep-modules.md +33 -33
- package/skills/engineering/tdd/interface-design.md +31 -31
- package/skills/engineering/tdd/mocking.md +59 -59
- package/skills/engineering/tdd/refactoring.md +10 -10
- package/skills/engineering/tdd/tests.md +61 -61
- package/skills/engineering/to-issues/SKILL.md +81 -81
- package/skills/engineering/to-prd/SKILL.md +74 -74
- package/skills/engineering/triage/AGENT-BRIEF.md +168 -168
- package/skills/engineering/triage/OUT-OF-SCOPE.md +101 -101
- package/skills/engineering/triage/SKILL.md +103 -103
- package/skills/engineering/web-frameworks/SKILL.md +324 -324
- package/skills/engineering/web-frameworks/references/nextjs-app-router.md +465 -465
- package/skills/engineering/web-frameworks/references/nextjs-data-fetching.md +459 -459
- package/skills/engineering/web-frameworks/references/nextjs-optimization.md +511 -511
- package/skills/engineering/web-frameworks/references/nextjs-server-components.md +495 -495
- package/skills/engineering/web-frameworks/references/remix-icon-integration.md +603 -603
- package/skills/engineering/web-frameworks/references/turborepo-caching.md +551 -551
- package/skills/engineering/web-frameworks/references/turborepo-pipelines.md +517 -517
- package/skills/engineering/web-frameworks/references/turborepo-setup.md +542 -542
- package/skills/engineering/web-frameworks/scripts/nextjs_init.py +547 -547
- package/skills/engineering/web-frameworks/scripts/requirements.txt +16 -16
- package/skills/engineering/web-frameworks/scripts/tests/requirements.txt +3 -3
- package/skills/engineering/web-frameworks/scripts/tests/test_nextjs_init.py +319 -319
- package/skills/engineering/web-frameworks/scripts/tests/test_turborepo_migrate.py +374 -374
- package/skills/engineering/web-frameworks/scripts/turborepo_migrate.py +394 -394
- package/skills/engineering/write-a-skill/SKILL.md +117 -117
- package/skills/kilo-kit/SKILL.md +346 -346
- package/skills/kilo-kit/_template/SKILL.md +185 -185
- package/skills/kilo-kit/debugging/root-cause/SKILL.md +360 -360
- package/skills/kilo-kit/debugging/systematic/SKILL.md +339 -339
- package/skills/kilo-kit/debugging/verification/SKILL.md +424 -424
- package/skills/kilo-kit/development/backend/SKILL.md +540 -540
- package/skills/kilo-kit/development/security/SKILL.md +529 -529
- package/skills/kilo-kit/quality/code-review/SKILL.md +297 -297
- package/skills/kilo-kit/quality/testing/SKILL.md +540 -540
- package/skills/kilo-kit/references/output-formats.md +204 -204
- package/skills/kilo-kit/references/patterns.md +156 -156
- package/skills/kilo-kit/references/performance-benchmarks.md +90 -90
- package/skills/operations/chrome-devtools/SKILL.md +392 -392
- package/skills/operations/chrome-devtools/references/cdp-domains.md +694 -694
- package/skills/operations/chrome-devtools/references/performance-guide.md +940 -940
- package/skills/operations/chrome-devtools/references/puppeteer-reference.md +953 -953
- package/skills/operations/chrome-devtools/scripts/PERSISTENT-BROWSER.md +107 -107
- package/skills/operations/chrome-devtools/scripts/README.md +213 -213
- package/skills/operations/chrome-devtools/scripts/__tests__/selector.test.js +210 -210
- package/skills/operations/chrome-devtools/scripts/click.js +79 -79
- package/skills/operations/chrome-devtools/scripts/close-persistent.js +36 -36
- package/skills/operations/chrome-devtools/scripts/console.js +75 -75
- package/skills/operations/chrome-devtools/scripts/evaluate.js +49 -49
- package/skills/operations/chrome-devtools/scripts/fill.js +72 -72
- package/skills/operations/chrome-devtools/scripts/install-deps.sh +181 -181
- package/skills/operations/chrome-devtools/scripts/install.sh +83 -83
- package/skills/operations/chrome-devtools/scripts/launch-persistent.js +71 -71
- package/skills/operations/chrome-devtools/scripts/lib/browser.js +144 -144
- package/skills/operations/chrome-devtools/scripts/lib/selector.js +178 -178
- package/skills/operations/chrome-devtools/scripts/navigate.js +46 -46
- package/skills/operations/chrome-devtools/scripts/network.js +102 -102
- package/skills/operations/chrome-devtools/scripts/package-lock.json +1206 -1206
- package/skills/operations/chrome-devtools/scripts/package.json +15 -15
- package/skills/operations/chrome-devtools/scripts/performance.js +145 -145
- package/skills/operations/chrome-devtools/scripts/screenshot.js +180 -180
- package/skills/operations/chrome-devtools/scripts/snapshot.js +131 -131
- package/skills/operations/devops/.env.example +76 -76
- package/skills/operations/devops/SKILL.md +285 -285
- package/skills/operations/devops/references/browser-rendering.md +305 -305
- package/skills/operations/devops/references/cloudflare-d1-kv.md +123 -123
- package/skills/operations/devops/references/cloudflare-platform.md +271 -271
- package/skills/operations/devops/references/cloudflare-r2-storage.md +280 -280
- package/skills/operations/devops/references/cloudflare-workers-advanced.md +312 -312
- package/skills/operations/devops/references/cloudflare-workers-apis.md +309 -309
- package/skills/operations/devops/references/cloudflare-workers-basics.md +418 -418
- package/skills/operations/devops/references/docker-basics.md +297 -297
- package/skills/operations/devops/references/docker-compose.md +292 -292
- package/skills/operations/devops/references/gcloud-platform.md +297 -297
- package/skills/operations/devops/references/gcloud-services.md +304 -304
- package/skills/operations/devops/scripts/cloudflare_deploy.py +269 -269
- package/skills/operations/devops/scripts/docker_optimize.py +320 -320
- package/skills/operations/devops/scripts/requirements.txt +20 -20
- package/skills/operations/devops/scripts/tests/requirements.txt +3 -3
- package/skills/operations/devops/scripts/tests/test_cloudflare_deploy.py +285 -285
- package/skills/operations/devops/scripts/tests/test_docker_optimize.py +436 -436
- package/skills/operations/mcp-builder/LICENSE.txt +201 -201
- package/skills/operations/mcp-builder/SKILL.md +328 -328
- package/skills/operations/mcp-builder/reference/evaluation.md +601 -601
- package/skills/operations/mcp-builder/reference/mcp_best_practices.md +915 -915
- package/skills/operations/mcp-builder/reference/node_mcp_server.md +915 -915
- package/skills/operations/mcp-builder/reference/python_mcp_server.md +751 -751
- package/skills/operations/mcp-builder/scripts/connections.py +151 -151
- package/skills/operations/mcp-builder/scripts/evaluation.py +373 -373
- package/skills/operations/mcp-builder/scripts/example_evaluation.xml +22 -22
- package/skills/operations/mcp-builder/scripts/requirements.txt +2 -2
- package/skills/operations/mcp-management/README.md +219 -219
- package/skills/operations/mcp-management/SKILL.md +175 -175
- package/skills/operations/mcp-management/assets/tools.json +3043 -3043
- package/skills/operations/mcp-management/references/configuration.md +114 -114
- package/skills/operations/mcp-management/references/gemini-cli-integration.md +201 -201
- package/skills/operations/mcp-management/references/mcp-protocol.md +116 -116
- package/skills/operations/mcp-management/scripts/.env.example +10 -10
- package/skills/operations/mcp-management/scripts/cli.ts +155 -155
- package/skills/operations/mcp-management/scripts/dist/analyze-tools.js +70 -70
- package/skills/operations/mcp-management/scripts/dist/cli.js +131 -131
- package/skills/operations/mcp-management/scripts/dist/mcp-client.js +115 -115
- package/skills/operations/mcp-management/scripts/mcp-client.ts +163 -163
- package/skills/operations/mcp-management/scripts/package.json +18 -18
- package/skills/operations/mcp-management/scripts/tsconfig.json +15 -15
- package/skills/problem-solving/collision-zone-thinking/SKILL.md +62 -62
- package/skills/problem-solving/defense-in-depth/SKILL.md +130 -130
- package/skills/problem-solving/inversion-exercise/SKILL.md +58 -58
- package/skills/problem-solving/meta-pattern-recognition/SKILL.md +54 -54
- package/skills/problem-solving/root-cause-tracing/SKILL.md +177 -177
- package/skills/problem-solving/root-cause-tracing/find-polluter.sh +63 -63
- package/skills/problem-solving/scale-game/SKILL.md +63 -63
- package/skills/problem-solving/sequential-thinking/README.md +118 -118
- package/skills/problem-solving/sequential-thinking/SKILL.md +93 -93
- package/skills/problem-solving/sequential-thinking/references/advanced.md +122 -122
- package/skills/problem-solving/sequential-thinking/references/examples.md +274 -274
- package/skills/problem-solving/simplification-cascades/SKILL.md +76 -76
- package/skills/problem-solving/when-stuck/SKILL.md +88 -88
- package/skills/productivity/caveman/SKILL.md +49 -49
- package/skills/productivity/grill-me/SKILL.md +10 -10
- package/skills/productivity/grill-with-docs/ADR-FORMAT.md +47 -47
- package/skills/productivity/grill-with-docs/CONTEXT-FORMAT.md +77 -77
- package/skills/productivity/grill-with-docs/SKILL.md +88 -88
- package/skills/productivity/writing-skills/graphviz-conventions.dot +171 -171
- package/skills/productivity/zoom-out/SKILL.md +7 -7
- package/skills/writing-docs/doc/LICENSE.txt +201 -201
- package/skills/writing-docs/doc/SKILL.md +80 -80
- package/skills/writing-docs/doc/agents/openai.yaml +6 -6
- package/skills/writing-docs/doc/assets/doc-small.svg +3 -3
- package/skills/writing-docs/doc/scripts/render_docx.py +296 -296
- package/skills/writing-docs/docx/LICENSE.txt +30 -30
- package/skills/writing-docs/docx/SKILL.md +196 -196
- package/skills/writing-docs/docx/docx-js.md +349 -349
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chart.xsd +1499 -1499
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chartDrawing.xsd +146 -146
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-diagram.xsd +1085 -1085
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-lockedCanvas.xsd +11 -11
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-main.xsd +3081 -3081
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-picture.xsd +23 -23
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-spreadsheetDrawing.xsd +185 -185
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/dml-wordprocessingDrawing.xsd +287 -287
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/pml.xsd +1676 -1676
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-additionalCharacteristics.xsd +28 -28
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-bibliography.xsd +144 -144
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-commonSimpleTypes.xsd +174 -174
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlDataProperties.xsd +25 -25
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlSchemaProperties.xsd +18 -18
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesCustom.xsd +59 -59
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesExtended.xsd +56 -56
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesVariantTypes.xsd +195 -195
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-math.xsd +582 -582
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/shared-relationshipReference.xsd +25 -25
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/sml.xsd +4439 -4439
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/vml-main.xsd +570 -570
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/vml-officeDrawing.xsd +509 -509
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/vml-presentationDrawing.xsd +12 -12
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/vml-spreadsheetDrawing.xsd +108 -108
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/vml-wordprocessingDrawing.xsd +96 -96
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/wml.xsd +3646 -3646
- package/skills/writing-docs/docx/ooxml/schemas/ISO-IEC29500-4_2016/xml.xsd +116 -116
- package/skills/writing-docs/docx/ooxml/schemas/ecma/fouth-edition/opc-contentTypes.xsd +42 -42
- package/skills/writing-docs/docx/ooxml/schemas/ecma/fouth-edition/opc-coreProperties.xsd +50 -50
- package/skills/writing-docs/docx/ooxml/schemas/ecma/fouth-edition/opc-digSig.xsd +49 -49
- package/skills/writing-docs/docx/ooxml/schemas/ecma/fouth-edition/opc-relationships.xsd +33 -33
- package/skills/writing-docs/docx/ooxml/schemas/mce/mc.xsd +75 -75
- package/skills/writing-docs/docx/ooxml/schemas/microsoft/wml-2010.xsd +560 -560
- package/skills/writing-docs/docx/ooxml/schemas/microsoft/wml-2012.xsd +67 -67
- package/skills/writing-docs/docx/ooxml/schemas/microsoft/wml-2018.xsd +14 -14
- package/skills/writing-docs/docx/ooxml/schemas/microsoft/wml-cex-2018.xsd +20 -20
- package/skills/writing-docs/docx/ooxml/schemas/microsoft/wml-cid-2016.xsd +13 -13
- package/skills/writing-docs/docx/ooxml/schemas/microsoft/wml-sdtdatahash-2020.xsd +4 -4
- package/skills/writing-docs/docx/ooxml/schemas/microsoft/wml-symex-2015.xsd +8 -8
- package/skills/writing-docs/docx/ooxml/scripts/pack.py +159 -159
- package/skills/writing-docs/docx/ooxml/scripts/unpack.py +29 -29
- package/skills/writing-docs/docx/ooxml/scripts/validate.py +69 -69
- package/skills/writing-docs/docx/ooxml/scripts/validation/__init__.py +15 -15
- package/skills/writing-docs/docx/ooxml/scripts/validation/base.py +951 -951
- package/skills/writing-docs/docx/ooxml/scripts/validation/docx.py +274 -274
- package/skills/writing-docs/docx/ooxml/scripts/validation/pptx.py +315 -315
- package/skills/writing-docs/docx/ooxml/scripts/validation/redlining.py +279 -279
- package/skills/writing-docs/docx/ooxml.md +609 -609
- package/skills/writing-docs/docx/scripts/__init__.py +1 -1
- package/skills/writing-docs/docx/scripts/document.py +1276 -1276
- package/skills/writing-docs/docx/scripts/templates/comments.xml +2 -2
- package/skills/writing-docs/docx/scripts/templates/commentsExtended.xml +2 -2
- package/skills/writing-docs/docx/scripts/templates/commentsExtensible.xml +2 -2
- package/skills/writing-docs/docx/scripts/templates/commentsIds.xml +2 -2
- package/skills/writing-docs/docx/scripts/templates/people.xml +2 -2
- package/skills/writing-docs/docx/scripts/utilities.py +374 -374
- package/skills/writing-docs/mermaidjs-v11/SKILL.md +115 -115
- package/skills/writing-docs/mermaidjs-v11/references/cli-usage.md +228 -228
- package/skills/writing-docs/mermaidjs-v11/references/configuration.md +232 -232
- package/skills/writing-docs/mermaidjs-v11/references/diagram-types.md +315 -315
- package/skills/writing-docs/mermaidjs-v11/references/examples.md +344 -344
- package/skills/writing-docs/mermaidjs-v11/references/integration.md +310 -310
- package/skills/writing-docs/pdf/LICENSE.txt +30 -30
- package/skills/writing-docs/pdf/SKILL.md +294 -294
- package/skills/writing-docs/pdf/forms.md +205 -205
- package/skills/writing-docs/pdf/reference.md +611 -611
- package/skills/writing-docs/pdf/scripts/check_bounding_boxes.py +70 -70
- package/skills/writing-docs/pdf/scripts/check_bounding_boxes_test.py +226 -226
- package/skills/writing-docs/pdf/scripts/check_fillable_fields.py +12 -12
- package/skills/writing-docs/pdf/scripts/convert_pdf_to_images.py +35 -35
- package/skills/writing-docs/pdf/scripts/create_validation_image.py +41 -41
- package/skills/writing-docs/pdf/scripts/extract_form_field_info.py +152 -152
- package/skills/writing-docs/pdf/scripts/fill_fillable_fields.py +114 -114
- package/skills/writing-docs/pdf/scripts/fill_pdf_form_with_annotations.py +107 -107
- package/skills/writing-docs/pptx/LICENSE.txt +30 -30
- package/skills/writing-docs/pptx/SKILL.md +483 -483
- package/skills/writing-docs/pptx/html2pptx.md +624 -624
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chart.xsd +1499 -1499
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chartDrawing.xsd +146 -146
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-diagram.xsd +1085 -1085
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-lockedCanvas.xsd +11 -11
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-main.xsd +3081 -3081
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-picture.xsd +23 -23
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-spreadsheetDrawing.xsd +185 -185
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-wordprocessingDrawing.xsd +287 -287
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/pml.xsd +1676 -1676
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-additionalCharacteristics.xsd +28 -28
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-bibliography.xsd +144 -144
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-commonSimpleTypes.xsd +174 -174
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlDataProperties.xsd +25 -25
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlSchemaProperties.xsd +18 -18
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesCustom.xsd +59 -59
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesExtended.xsd +56 -56
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesVariantTypes.xsd +195 -195
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-math.xsd +582 -582
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-relationshipReference.xsd +25 -25
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/sml.xsd +4439 -4439
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-main.xsd +570 -570
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-officeDrawing.xsd +509 -509
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-presentationDrawing.xsd +12 -12
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-spreadsheetDrawing.xsd +108 -108
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-wordprocessingDrawing.xsd +96 -96
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/wml.xsd +3646 -3646
- package/skills/writing-docs/pptx/ooxml/schemas/ISO-IEC29500-4_2016/xml.xsd +116 -116
- package/skills/writing-docs/pptx/ooxml/schemas/ecma/fouth-edition/opc-contentTypes.xsd +42 -42
- package/skills/writing-docs/pptx/ooxml/schemas/ecma/fouth-edition/opc-coreProperties.xsd +50 -50
- package/skills/writing-docs/pptx/ooxml/schemas/ecma/fouth-edition/opc-digSig.xsd +49 -49
- package/skills/writing-docs/pptx/ooxml/schemas/ecma/fouth-edition/opc-relationships.xsd +33 -33
- package/skills/writing-docs/pptx/ooxml/schemas/mce/mc.xsd +75 -75
- package/skills/writing-docs/pptx/ooxml/schemas/microsoft/wml-2010.xsd +560 -560
- package/skills/writing-docs/pptx/ooxml/schemas/microsoft/wml-2012.xsd +67 -67
- package/skills/writing-docs/pptx/ooxml/schemas/microsoft/wml-2018.xsd +14 -14
- package/skills/writing-docs/pptx/ooxml/schemas/microsoft/wml-cex-2018.xsd +20 -20
- package/skills/writing-docs/pptx/ooxml/schemas/microsoft/wml-cid-2016.xsd +13 -13
- package/skills/writing-docs/pptx/ooxml/schemas/microsoft/wml-sdtdatahash-2020.xsd +4 -4
- package/skills/writing-docs/pptx/ooxml/schemas/microsoft/wml-symex-2015.xsd +8 -8
- package/skills/writing-docs/pptx/ooxml/scripts/pack.py +159 -159
- package/skills/writing-docs/pptx/ooxml/scripts/unpack.py +29 -29
- package/skills/writing-docs/pptx/ooxml/scripts/validate.py +69 -69
- package/skills/writing-docs/pptx/ooxml/scripts/validation/__init__.py +15 -15
- package/skills/writing-docs/pptx/ooxml/scripts/validation/base.py +951 -951
- package/skills/writing-docs/pptx/ooxml/scripts/validation/docx.py +274 -274
- package/skills/writing-docs/pptx/ooxml/scripts/validation/pptx.py +315 -315
- package/skills/writing-docs/pptx/ooxml/scripts/validation/redlining.py +279 -279
- package/skills/writing-docs/pptx/ooxml.md +426 -426
- package/skills/writing-docs/pptx/scripts/html2pptx.js +978 -978
- package/skills/writing-docs/pptx/scripts/inventory.py +1020 -1020
- package/skills/writing-docs/pptx/scripts/rearrange.py +231 -231
- package/skills/writing-docs/pptx/scripts/replace.py +385 -385
- package/skills/writing-docs/pptx/scripts/thumbnail.py +450 -450
- package/skills/writing-docs/slides/LICENSE.txt +201 -201
- package/skills/writing-docs/slides/SKILL.md +71 -71
- package/skills/writing-docs/slides/agents/openai.yaml +6 -6
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/code.js +104 -104
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/image.js +333 -333
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/index.js +33 -33
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/latex.js +51 -51
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/layout.js +643 -643
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/layout_builders.js +358 -358
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/svg.js +36 -36
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/text.js +789 -789
- package/skills/writing-docs/slides/assets/pptxgenjs_helpers/util.js +24 -24
- package/skills/writing-docs/slides/assets/slides-small.svg +3 -3
- package/skills/writing-docs/slides/references/pptxgenjs-helpers.md +61 -61
- package/skills/writing-docs/slides/scripts/create_montage.py +300 -300
- package/skills/writing-docs/slides/scripts/detect_font.py +873 -873
- package/skills/writing-docs/slides/scripts/ensure_raster_image.py +202 -202
- package/skills/writing-docs/slides/scripts/render_slides.py +273 -273
- package/skills/writing-docs/slides/scripts/slides_test.py +201 -201
- package/skills/writing-docs/template-skill/SKILL.md +26 -26
- package/skills/writing-docs/xlsx/LICENSE.txt +30 -30
- package/skills/writing-docs/xlsx/SKILL.md +288 -288
- package/skills/writing-docs/xlsx/recalc.py +177 -177
- package/src/core/KILO_MASTER.md +448 -448
- package/src/tools/validate-skill.js +421 -421
|
@@ -1,540 +1,540 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: testing-strategy
|
|
3
|
-
description: >-
|
|
4
|
-
Comprehensive testing skill covering unit, integration, and e2e testing with TDD.
|
|
5
|
-
Use when writing tests, improving coverage, or setting up testing infrastructure.
|
|
6
|
-
Keywords: test, TDD, unit test, integration, e2e, coverage, mock, jest, vitest
|
|
7
|
-
version: 1.0.0
|
|
8
|
-
behaviors: [generate_with_validation, run_command, review_and_suggest]
|
|
9
|
-
dependencies: []
|
|
10
|
-
token_estimate:
|
|
11
|
-
min: 1500
|
|
12
|
-
typical: 3500
|
|
13
|
-
max: 8000
|
|
14
|
-
---
|
|
15
|
-
|
|
16
|
-
# 🧪 Testing Strategy Skill
|
|
17
|
-
|
|
18
|
-
> **Philosophy:** If it's not tested, it's broken. You just don't know it yet.
|
|
19
|
-
|
|
20
|
-
## When to Use
|
|
21
|
-
|
|
22
|
-
Use this skill when:
|
|
23
|
-
- Writing new code (TDD approach)
|
|
24
|
-
- Adding tests to existing code
|
|
25
|
-
- Improving test coverage
|
|
26
|
-
- Fixing flaky tests
|
|
27
|
-
- Setting up testing infrastructure
|
|
28
|
-
- Debugging test failures
|
|
29
|
-
|
|
30
|
-
**Do NOT use this skill when:**
|
|
31
|
-
- Just running existing tests
|
|
32
|
-
- Quick syntax check
|
|
33
|
-
|
|
34
|
-
---
|
|
35
|
-
|
|
36
|
-
## The Testing Pyramid
|
|
37
|
-
|
|
38
|
-
```
|
|
39
|
-
╱╲
|
|
40
|
-
╱ ╲
|
|
41
|
-
╱ E2E╲ Few, slow, expensive
|
|
42
|
-
╱──────╲ Full system tests
|
|
43
|
-
╱ ╲
|
|
44
|
-
╱Integration╲ Medium amount
|
|
45
|
-
╱────────────╲ Component interaction
|
|
46
|
-
╱ ╲
|
|
47
|
-
╱ Unit Tests ╲ Many, fast, cheap
|
|
48
|
-
╱──────────────────╲ Single unit isolation
|
|
49
|
-
```
|
|
50
|
-
|
|
51
|
-
---
|
|
52
|
-
|
|
53
|
-
## TDD Workflow: RED → GREEN → REFACTOR
|
|
54
|
-
|
|
55
|
-
### Step 1: RED (Write Failing Test)
|
|
56
|
-
|
|
57
|
-
```typescript
|
|
58
|
-
// Write the test BEFORE the implementation
|
|
59
|
-
describe('calculateDiscount', () => {
|
|
60
|
-
it('should apply 10% discount for orders over $100', () => {
|
|
61
|
-
// This test will FAIL because function doesn't exist yet
|
|
62
|
-
const result = calculateDiscount(150);
|
|
63
|
-
expect(result).toBe(135);
|
|
64
|
-
});
|
|
65
|
-
});
|
|
66
|
-
```
|
|
67
|
-
|
|
68
|
-
**Run test → Should FAIL (RED)**
|
|
69
|
-
|
|
70
|
-
### Step 2: GREEN (Minimal Implementation)
|
|
71
|
-
|
|
72
|
-
```typescript
|
|
73
|
-
// Write the MINIMUM code to pass the test
|
|
74
|
-
function calculateDiscount(amount: number): number {
|
|
75
|
-
if (amount > 100) {
|
|
76
|
-
return amount * 0.9;
|
|
77
|
-
}
|
|
78
|
-
return amount;
|
|
79
|
-
}
|
|
80
|
-
```
|
|
81
|
-
|
|
82
|
-
**Run test → Should PASS (GREEN)**
|
|
83
|
-
|
|
84
|
-
### Step 3: REFACTOR (Improve)
|
|
85
|
-
|
|
86
|
-
```typescript
|
|
87
|
-
// Improve code while keeping tests green
|
|
88
|
-
const DISCOUNT_THRESHOLD = 100;
|
|
89
|
-
const DISCOUNT_RATE = 0.1;
|
|
90
|
-
|
|
91
|
-
function calculateDiscount(amount: number): number {
|
|
92
|
-
if (amount > DISCOUNT_THRESHOLD) {
|
|
93
|
-
return amount * (1 - DISCOUNT_RATE);
|
|
94
|
-
}
|
|
95
|
-
return amount;
|
|
96
|
-
}
|
|
97
|
-
```
|
|
98
|
-
|
|
99
|
-
**Run test → Should still PASS**
|
|
100
|
-
|
|
101
|
-
---
|
|
102
|
-
|
|
103
|
-
## Unit Testing Patterns
|
|
104
|
-
|
|
105
|
-
### Basic Structure (AAA Pattern)
|
|
106
|
-
|
|
107
|
-
```typescript
|
|
108
|
-
describe('UserService', () => {
|
|
109
|
-
describe('createUser', () => {
|
|
110
|
-
it('should create user with valid data', async () => {
|
|
111
|
-
// Arrange
|
|
112
|
-
const userData = { email: 'test@example.com', name: 'Test' };
|
|
113
|
-
const mockRepo = { create: jest.fn().mockResolvedValue({ id: '1', ...userData }) };
|
|
114
|
-
const service = new UserService(mockRepo);
|
|
115
|
-
|
|
116
|
-
// Act
|
|
117
|
-
const result = await service.createUser(userData);
|
|
118
|
-
|
|
119
|
-
// Assert
|
|
120
|
-
expect(result.id).toBe('1');
|
|
121
|
-
expect(result.email).toBe(userData.email);
|
|
122
|
-
expect(mockRepo.create).toHaveBeenCalledWith(userData);
|
|
123
|
-
});
|
|
124
|
-
});
|
|
125
|
-
});
|
|
126
|
-
```
|
|
127
|
-
|
|
128
|
-
### Testing Error Cases
|
|
129
|
-
|
|
130
|
-
```typescript
|
|
131
|
-
describe('createUser', () => {
|
|
132
|
-
it('should throw on duplicate email', async () => {
|
|
133
|
-
// Arrange
|
|
134
|
-
const mockRepo = {
|
|
135
|
-
findByEmail: jest.fn().mockResolvedValue({ id: 'existing' }),
|
|
136
|
-
};
|
|
137
|
-
const service = new UserService(mockRepo);
|
|
138
|
-
|
|
139
|
-
// Act & Assert
|
|
140
|
-
await expect(
|
|
141
|
-
service.createUser({ email: 'exists@example.com' })
|
|
142
|
-
).rejects.toThrow('Email already registered');
|
|
143
|
-
});
|
|
144
|
-
});
|
|
145
|
-
```
|
|
146
|
-
|
|
147
|
-
### Testing Async Code
|
|
148
|
-
|
|
149
|
-
```typescript
|
|
150
|
-
describe('fetchUserData', () => {
|
|
151
|
-
it('should fetch and transform user data', async () => {
|
|
152
|
-
// Arrange
|
|
153
|
-
const mockApi = {
|
|
154
|
-
get: jest.fn().mockResolvedValue({ data: { name: 'John' } }),
|
|
155
|
-
};
|
|
156
|
-
|
|
157
|
-
// Act
|
|
158
|
-
const result = await fetchUserData(mockApi, 'user-id');
|
|
159
|
-
|
|
160
|
-
// Assert
|
|
161
|
-
expect(result).toEqual({ name: 'John' });
|
|
162
|
-
expect(mockApi.get).toHaveBeenCalledWith('/users/user-id');
|
|
163
|
-
});
|
|
164
|
-
|
|
165
|
-
it('should handle API errors gracefully', async () => {
|
|
166
|
-
const mockApi = {
|
|
167
|
-
get: jest.fn().mockRejectedValue(new Error('Network error')),
|
|
168
|
-
};
|
|
169
|
-
|
|
170
|
-
await expect(fetchUserData(mockApi, 'user-id'))
|
|
171
|
-
.rejects.toThrow('Failed to fetch user');
|
|
172
|
-
});
|
|
173
|
-
});
|
|
174
|
-
```
|
|
175
|
-
|
|
176
|
-
---
|
|
177
|
-
|
|
178
|
-
## Mocking Strategies
|
|
179
|
-
|
|
180
|
-
### Mock Functions
|
|
181
|
-
|
|
182
|
-
```typescript
|
|
183
|
-
// Create mock function
|
|
184
|
-
const mockFn = jest.fn();
|
|
185
|
-
|
|
186
|
-
// Define return value
|
|
187
|
-
mockFn.mockReturnValue('static value');
|
|
188
|
-
mockFn.mockResolvedValue('async value');
|
|
189
|
-
mockFn.mockRejectedValue(new Error('error'));
|
|
190
|
-
|
|
191
|
-
// Implementation
|
|
192
|
-
mockFn.mockImplementation((x) => x * 2);
|
|
193
|
-
|
|
194
|
-
// Verify calls
|
|
195
|
-
expect(mockFn).toHaveBeenCalled();
|
|
196
|
-
expect(mockFn).toHaveBeenCalledWith('arg1', 'arg2');
|
|
197
|
-
expect(mockFn).toHaveBeenCalledTimes(3);
|
|
198
|
-
```
|
|
199
|
-
|
|
200
|
-
### Mock Modules
|
|
201
|
-
|
|
202
|
-
```typescript
|
|
203
|
-
// Mock entire module
|
|
204
|
-
jest.mock('./database', () => ({
|
|
205
|
-
connect: jest.fn(),
|
|
206
|
-
query: jest.fn(),
|
|
207
|
-
}));
|
|
208
|
-
|
|
209
|
-
// Mock with factory
|
|
210
|
-
jest.mock('./config', () => ({
|
|
211
|
-
get: (key: string) => {
|
|
212
|
-
const config = { API_URL: 'http://test-api.com' };
|
|
213
|
-
return config[key];
|
|
214
|
-
},
|
|
215
|
-
}));
|
|
216
|
-
```
|
|
217
|
-
|
|
218
|
-
### Spying
|
|
219
|
-
|
|
220
|
-
```typescript
|
|
221
|
-
// Spy on existing method
|
|
222
|
-
const spy = jest.spyOn(userService, 'sendEmail');
|
|
223
|
-
|
|
224
|
-
// Call the code
|
|
225
|
-
await userService.createUser({ email: 'test@example.com' });
|
|
226
|
-
|
|
227
|
-
// Verify the spy
|
|
228
|
-
expect(spy).toHaveBeenCalled();
|
|
229
|
-
|
|
230
|
-
// Restore original
|
|
231
|
-
spy.mockRestore();
|
|
232
|
-
```
|
|
233
|
-
|
|
234
|
-
---
|
|
235
|
-
|
|
236
|
-
## Integration Testing
|
|
237
|
-
|
|
238
|
-
### API Integration Tests
|
|
239
|
-
|
|
240
|
-
```typescript
|
|
241
|
-
describe('POST /users', () => {
|
|
242
|
-
let app: Express;
|
|
243
|
-
let db: Database;
|
|
244
|
-
|
|
245
|
-
beforeAll(async () => {
|
|
246
|
-
db = await Database.connect(TEST_DB_URL);
|
|
247
|
-
app = createApp(db);
|
|
248
|
-
});
|
|
249
|
-
|
|
250
|
-
afterAll(async () => {
|
|
251
|
-
await db.disconnect();
|
|
252
|
-
});
|
|
253
|
-
|
|
254
|
-
beforeEach(async () => {
|
|
255
|
-
await db.clear('users');
|
|
256
|
-
});
|
|
257
|
-
|
|
258
|
-
it('should create user and return 201', async () => {
|
|
259
|
-
const response = await request(app)
|
|
260
|
-
.post('/users')
|
|
261
|
-
.send({ email: 'test@example.com', password: 'Password123!' })
|
|
262
|
-
.expect(201);
|
|
263
|
-
|
|
264
|
-
expect(response.body.email).toBe('test@example.com');
|
|
265
|
-
expect(response.body.password).toBeUndefined();
|
|
266
|
-
|
|
267
|
-
// Verify in database
|
|
268
|
-
const user = await db.users.findOne({ email: 'test@example.com' });
|
|
269
|
-
expect(user).toBeDefined();
|
|
270
|
-
});
|
|
271
|
-
|
|
272
|
-
it('should return 400 for invalid email', async () => {
|
|
273
|
-
const response = await request(app)
|
|
274
|
-
.post('/users')
|
|
275
|
-
.send({ email: 'invalid', password: 'Password123!' })
|
|
276
|
-
.expect(400);
|
|
277
|
-
|
|
278
|
-
expect(response.body.errors).toContainEqual(
|
|
279
|
-
expect.objectContaining({ field: 'email' })
|
|
280
|
-
);
|
|
281
|
-
});
|
|
282
|
-
});
|
|
283
|
-
```
|
|
284
|
-
|
|
285
|
-
### Database Integration Tests
|
|
286
|
-
|
|
287
|
-
```typescript
|
|
288
|
-
describe('UserRepository', () => {
|
|
289
|
-
let db: Database;
|
|
290
|
-
let repo: UserRepository;
|
|
291
|
-
|
|
292
|
-
beforeAll(async () => {
|
|
293
|
-
db = await Database.connect(TEST_DB_URL);
|
|
294
|
-
repo = new UserRepository(db);
|
|
295
|
-
});
|
|
296
|
-
|
|
297
|
-
beforeEach(async () => {
|
|
298
|
-
await db.clear('users');
|
|
299
|
-
await db.seed('users', testUsers);
|
|
300
|
-
});
|
|
301
|
-
|
|
302
|
-
it('should find user by email', async () => {
|
|
303
|
-
const user = await repo.findByEmail('john@example.com');
|
|
304
|
-
expect(user?.name).toBe('John Doe');
|
|
305
|
-
});
|
|
306
|
-
|
|
307
|
-
it('should return null for non-existent email', async () => {
|
|
308
|
-
const user = await repo.findByEmail('nobody@example.com');
|
|
309
|
-
expect(user).toBeNull();
|
|
310
|
-
});
|
|
311
|
-
});
|
|
312
|
-
```
|
|
313
|
-
|
|
314
|
-
---
|
|
315
|
-
|
|
316
|
-
## E2E Testing
|
|
317
|
-
|
|
318
|
-
### Playwright Example
|
|
319
|
-
|
|
320
|
-
```typescript
|
|
321
|
-
import { test, expect } from '@playwright/test';
|
|
322
|
-
|
|
323
|
-
test.describe('User Registration', () => {
|
|
324
|
-
test('should complete registration flow', async ({ page }) => {
|
|
325
|
-
// Navigate to registration
|
|
326
|
-
await page.goto('/register');
|
|
327
|
-
|
|
328
|
-
// Fill form
|
|
329
|
-
await page.fill('[data-testid="email"]', 'newuser@example.com');
|
|
330
|
-
await page.fill('[data-testid="password"]', 'SecurePassword123!');
|
|
331
|
-
await page.fill('[data-testid="name"]', 'New User');
|
|
332
|
-
|
|
333
|
-
// Submit
|
|
334
|
-
await page.click('[data-testid="submit"]');
|
|
335
|
-
|
|
336
|
-
// Verify redirect to dashboard
|
|
337
|
-
await expect(page).toHaveURL('/dashboard');
|
|
338
|
-
await expect(page.locator('[data-testid="welcome-message"]'))
|
|
339
|
-
.toContainText('Welcome, New User');
|
|
340
|
-
});
|
|
341
|
-
|
|
342
|
-
test('should show validation errors', async ({ page }) => {
|
|
343
|
-
await page.goto('/register');
|
|
344
|
-
|
|
345
|
-
await page.fill('[data-testid="email"]', 'invalid-email');
|
|
346
|
-
await page.click('[data-testid="submit"]');
|
|
347
|
-
|
|
348
|
-
await expect(page.locator('[data-testid="email-error"]'))
|
|
349
|
-
.toBeVisible();
|
|
350
|
-
});
|
|
351
|
-
});
|
|
352
|
-
```
|
|
353
|
-
|
|
354
|
-
---
|
|
355
|
-
|
|
356
|
-
## Test Coverage
|
|
357
|
-
|
|
358
|
-
### Coverage Targets
|
|
359
|
-
|
|
360
|
-
```yaml
|
|
361
|
-
coverage_targets:
|
|
362
|
-
statements: 80%
|
|
363
|
-
branches: 80%
|
|
364
|
-
functions: 80%
|
|
365
|
-
lines: 80%
|
|
366
|
-
|
|
367
|
-
priority_areas:
|
|
368
|
-
critical: 95%+ # Auth, payments, core business logic
|
|
369
|
-
high: 85%+ # API endpoints, services
|
|
370
|
-
medium: 70%+ # Utilities, helpers
|
|
371
|
-
low: 50%+ # UI components, config
|
|
372
|
-
```
|
|
373
|
-
|
|
374
|
-
### Coverage Configuration
|
|
375
|
-
|
|
376
|
-
```javascript
|
|
377
|
-
// jest.config.js
|
|
378
|
-
module.exports = {
|
|
379
|
-
collectCoverage: true,
|
|
380
|
-
coverageDirectory: 'coverage',
|
|
381
|
-
coverageReporters: ['text', 'lcov', 'html'],
|
|
382
|
-
coverageThreshold: {
|
|
383
|
-
global: {
|
|
384
|
-
branches: 80,
|
|
385
|
-
functions: 80,
|
|
386
|
-
lines: 80,
|
|
387
|
-
statements: 80,
|
|
388
|
-
},
|
|
389
|
-
},
|
|
390
|
-
collectCoverageFrom: [
|
|
391
|
-
'src/**/*.{ts,tsx}',
|
|
392
|
-
'!src/**/*.d.ts',
|
|
393
|
-
'!src/**/*.stories.{ts,tsx}',
|
|
394
|
-
'!src/test/**/*',
|
|
395
|
-
],
|
|
396
|
-
};
|
|
397
|
-
```
|
|
398
|
-
|
|
399
|
-
---
|
|
400
|
-
|
|
401
|
-
## Fixing Flaky Tests
|
|
402
|
-
|
|
403
|
-
### Common Causes & Solutions
|
|
404
|
-
|
|
405
|
-
| Cause | Symptom | Solution |
|
|
406
|
-
|-------|---------|----------|
|
|
407
|
-
| Race conditions | Fails randomly | Add proper waits, use async/await correctly |
|
|
408
|
-
| Shared state | Fails when run together | Isolate test data, proper cleanup |
|
|
409
|
-
| Time-dependent | Fails at certain times | Mock Date/time |
|
|
410
|
-
| External dependencies | Fails intermittently | Mock external services |
|
|
411
|
-
| Order dependency | Fails when run in different order | Make tests independent |
|
|
412
|
-
|
|
413
|
-
### Debugging Flaky Tests
|
|
414
|
-
|
|
415
|
-
```typescript
|
|
416
|
-
// Add retries for known flaky tests (use sparingly!)
|
|
417
|
-
test('flaky network test', { retry: 2 }, async () => {
|
|
418
|
-
// ...
|
|
419
|
-
});
|
|
420
|
-
|
|
421
|
-
// Log more info on failure
|
|
422
|
-
afterEach(function() {
|
|
423
|
-
if (this.currentTest?.state === 'failed') {
|
|
424
|
-
console.log('Test state:', JSON.stringify(testState, null, 2));
|
|
425
|
-
}
|
|
426
|
-
});
|
|
427
|
-
|
|
428
|
-
// Increase timeout if needed
|
|
429
|
-
test('slow test', async () => {
|
|
430
|
-
// ...
|
|
431
|
-
}, 30000); // 30 second timeout
|
|
432
|
-
```
|
|
433
|
-
|
|
434
|
-
---
|
|
435
|
-
|
|
436
|
-
## Test Organization
|
|
437
|
-
|
|
438
|
-
### File Structure
|
|
439
|
-
|
|
440
|
-
```
|
|
441
|
-
src/
|
|
442
|
-
├── users/
|
|
443
|
-
│ ├── users.service.ts
|
|
444
|
-
│ ├── users.service.spec.ts # Unit tests
|
|
445
|
-
│ └── users.controller.ts
|
|
446
|
-
│
|
|
447
|
-
tests/
|
|
448
|
-
├── unit/ # Additional unit tests
|
|
449
|
-
├── integration/
|
|
450
|
-
│ ├── api/
|
|
451
|
-
│ │ └── users.api.spec.ts
|
|
452
|
-
│ └── db/
|
|
453
|
-
│ └── users.repo.spec.ts
|
|
454
|
-
├── e2e/
|
|
455
|
-
│ └── user-registration.spec.ts
|
|
456
|
-
├── fixtures/
|
|
457
|
-
│ └── users.fixture.ts
|
|
458
|
-
└── helpers/
|
|
459
|
-
├── database.helper.ts
|
|
460
|
-
└── auth.helper.ts
|
|
461
|
-
```
|
|
462
|
-
|
|
463
|
-
### Test Naming Conventions
|
|
464
|
-
|
|
465
|
-
```typescript
|
|
466
|
-
// Use descriptive names
|
|
467
|
-
describe('UserService')
|
|
468
|
-
describe('createUser method')
|
|
469
|
-
|
|
470
|
-
// "should" format
|
|
471
|
-
it('should create user with valid data')
|
|
472
|
-
it('should throw when email is duplicate')
|
|
473
|
-
it('should hash password before saving')
|
|
474
|
-
|
|
475
|
-
// Given-When-Then for complex scenarios
|
|
476
|
-
it('given authenticated admin, when deleting user, should succeed')
|
|
477
|
-
```
|
|
478
|
-
|
|
479
|
-
---
|
|
480
|
-
|
|
481
|
-
## Guidelines
|
|
482
|
-
|
|
483
|
-
### DO ✅
|
|
484
|
-
- Write tests before code (TDD)
|
|
485
|
-
- Test behavior, not implementation
|
|
486
|
-
- Keep tests independent
|
|
487
|
-
- Use descriptive test names
|
|
488
|
-
- Test edge cases and errors
|
|
489
|
-
- Clean up after tests
|
|
490
|
-
|
|
491
|
-
### DON'T ❌
|
|
492
|
-
- Test private methods directly
|
|
493
|
-
- Share state between tests
|
|
494
|
-
- Test framework/library code
|
|
495
|
-
- Write tests that always pass
|
|
496
|
-
- Ignore flaky tests
|
|
497
|
-
- Mock everything
|
|
498
|
-
|
|
499
|
-
---
|
|
500
|
-
|
|
501
|
-
## Test Quality Checklist
|
|
502
|
-
|
|
503
|
-
```yaml
|
|
504
|
-
test_quality:
|
|
505
|
-
- Tests run independently in any order
|
|
506
|
-
- Tests don't depend on external services
|
|
507
|
-
- Tests are deterministic (not flaky)
|
|
508
|
-
- Tests are fast (<100ms for unit tests)
|
|
509
|
-
- Tests have meaningful assertions
|
|
510
|
-
- Tests cover happy path AND error cases
|
|
511
|
-
- Tests are readable and maintainable
|
|
512
|
-
- Tests use realistic data
|
|
513
|
-
```
|
|
514
|
-
|
|
515
|
-
---
|
|
516
|
-
|
|
517
|
-
## Success Criteria
|
|
518
|
-
|
|
519
|
-
Before considering testing complete:
|
|
520
|
-
|
|
521
|
-
- [ ] All new code has tests
|
|
522
|
-
- [ ] Coverage meets targets
|
|
523
|
-
- [ ] All tests pass consistently
|
|
524
|
-
- [ ] No flaky tests
|
|
525
|
-
- [ ] Edge cases covered
|
|
526
|
-
- [ ] Error conditions tested
|
|
527
|
-
- [ ] Tests run in CI pipeline
|
|
528
|
-
- [ ] Tests are maintainable
|
|
529
|
-
|
|
530
|
-
---
|
|
531
|
-
|
|
532
|
-
## Related Skills
|
|
533
|
-
|
|
534
|
-
- `skills/kilo-kit/quality/code-review/` - For reviewing test quality
|
|
535
|
-
- `skills/kilo-kit/debugging/verification/` - For verifying fixes
|
|
536
|
-
- `skills/kilo-kit/development/backend/` - For testing APIs
|
|
537
|
-
|
|
538
|
-
---
|
|
539
|
-
|
|
540
|
-
*Testing Strategy Skill v1.0.0 — Test it or regret it*
|
|
1
|
+
---
|
|
2
|
+
name: testing-strategy
|
|
3
|
+
description: >-
|
|
4
|
+
Comprehensive testing skill covering unit, integration, and e2e testing with TDD.
|
|
5
|
+
Use when writing tests, improving coverage, or setting up testing infrastructure.
|
|
6
|
+
Keywords: test, TDD, unit test, integration, e2e, coverage, mock, jest, vitest
|
|
7
|
+
version: 1.0.0
|
|
8
|
+
behaviors: [generate_with_validation, run_command, review_and_suggest]
|
|
9
|
+
dependencies: []
|
|
10
|
+
token_estimate:
|
|
11
|
+
min: 1500
|
|
12
|
+
typical: 3500
|
|
13
|
+
max: 8000
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
# 🧪 Testing Strategy Skill
|
|
17
|
+
|
|
18
|
+
> **Philosophy:** If it's not tested, it's broken. You just don't know it yet.
|
|
19
|
+
|
|
20
|
+
## When to Use
|
|
21
|
+
|
|
22
|
+
Use this skill when:
|
|
23
|
+
- Writing new code (TDD approach)
|
|
24
|
+
- Adding tests to existing code
|
|
25
|
+
- Improving test coverage
|
|
26
|
+
- Fixing flaky tests
|
|
27
|
+
- Setting up testing infrastructure
|
|
28
|
+
- Debugging test failures
|
|
29
|
+
|
|
30
|
+
**Do NOT use this skill when:**
|
|
31
|
+
- Just running existing tests
|
|
32
|
+
- Quick syntax check
|
|
33
|
+
|
|
34
|
+
---
|
|
35
|
+
|
|
36
|
+
## The Testing Pyramid
|
|
37
|
+
|
|
38
|
+
```
|
|
39
|
+
╱╲
|
|
40
|
+
╱ ╲
|
|
41
|
+
╱ E2E╲ Few, slow, expensive
|
|
42
|
+
╱──────╲ Full system tests
|
|
43
|
+
╱ ╲
|
|
44
|
+
╱Integration╲ Medium amount
|
|
45
|
+
╱────────────╲ Component interaction
|
|
46
|
+
╱ ╲
|
|
47
|
+
╱ Unit Tests ╲ Many, fast, cheap
|
|
48
|
+
╱──────────────────╲ Single unit isolation
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
---
|
|
52
|
+
|
|
53
|
+
## TDD Workflow: RED → GREEN → REFACTOR
|
|
54
|
+
|
|
55
|
+
### Step 1: RED (Write Failing Test)
|
|
56
|
+
|
|
57
|
+
```typescript
|
|
58
|
+
// Write the test BEFORE the implementation
|
|
59
|
+
describe('calculateDiscount', () => {
|
|
60
|
+
it('should apply 10% discount for orders over $100', () => {
|
|
61
|
+
// This test will FAIL because function doesn't exist yet
|
|
62
|
+
const result = calculateDiscount(150);
|
|
63
|
+
expect(result).toBe(135);
|
|
64
|
+
});
|
|
65
|
+
});
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
**Run test → Should FAIL (RED)**
|
|
69
|
+
|
|
70
|
+
### Step 2: GREEN (Minimal Implementation)
|
|
71
|
+
|
|
72
|
+
```typescript
|
|
73
|
+
// Write the MINIMUM code to pass the test
|
|
74
|
+
function calculateDiscount(amount: number): number {
|
|
75
|
+
if (amount > 100) {
|
|
76
|
+
return amount * 0.9;
|
|
77
|
+
}
|
|
78
|
+
return amount;
|
|
79
|
+
}
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
**Run test → Should PASS (GREEN)**
|
|
83
|
+
|
|
84
|
+
### Step 3: REFACTOR (Improve)
|
|
85
|
+
|
|
86
|
+
```typescript
|
|
87
|
+
// Improve code while keeping tests green
|
|
88
|
+
const DISCOUNT_THRESHOLD = 100;
|
|
89
|
+
const DISCOUNT_RATE = 0.1;
|
|
90
|
+
|
|
91
|
+
function calculateDiscount(amount: number): number {
|
|
92
|
+
if (amount > DISCOUNT_THRESHOLD) {
|
|
93
|
+
return amount * (1 - DISCOUNT_RATE);
|
|
94
|
+
}
|
|
95
|
+
return amount;
|
|
96
|
+
}
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
**Run test → Should still PASS**
|
|
100
|
+
|
|
101
|
+
---
|
|
102
|
+
|
|
103
|
+
## Unit Testing Patterns
|
|
104
|
+
|
|
105
|
+
### Basic Structure (AAA Pattern)
|
|
106
|
+
|
|
107
|
+
```typescript
|
|
108
|
+
describe('UserService', () => {
|
|
109
|
+
describe('createUser', () => {
|
|
110
|
+
it('should create user with valid data', async () => {
|
|
111
|
+
// Arrange
|
|
112
|
+
const userData = { email: 'test@example.com', name: 'Test' };
|
|
113
|
+
const mockRepo = { create: jest.fn().mockResolvedValue({ id: '1', ...userData }) };
|
|
114
|
+
const service = new UserService(mockRepo);
|
|
115
|
+
|
|
116
|
+
// Act
|
|
117
|
+
const result = await service.createUser(userData);
|
|
118
|
+
|
|
119
|
+
// Assert
|
|
120
|
+
expect(result.id).toBe('1');
|
|
121
|
+
expect(result.email).toBe(userData.email);
|
|
122
|
+
expect(mockRepo.create).toHaveBeenCalledWith(userData);
|
|
123
|
+
});
|
|
124
|
+
});
|
|
125
|
+
});
|
|
126
|
+
```
|
|
127
|
+
|
|
128
|
+
### Testing Error Cases
|
|
129
|
+
|
|
130
|
+
```typescript
|
|
131
|
+
describe('createUser', () => {
|
|
132
|
+
it('should throw on duplicate email', async () => {
|
|
133
|
+
// Arrange
|
|
134
|
+
const mockRepo = {
|
|
135
|
+
findByEmail: jest.fn().mockResolvedValue({ id: 'existing' }),
|
|
136
|
+
};
|
|
137
|
+
const service = new UserService(mockRepo);
|
|
138
|
+
|
|
139
|
+
// Act & Assert
|
|
140
|
+
await expect(
|
|
141
|
+
service.createUser({ email: 'exists@example.com' })
|
|
142
|
+
).rejects.toThrow('Email already registered');
|
|
143
|
+
});
|
|
144
|
+
});
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
### Testing Async Code
|
|
148
|
+
|
|
149
|
+
```typescript
|
|
150
|
+
describe('fetchUserData', () => {
|
|
151
|
+
it('should fetch and transform user data', async () => {
|
|
152
|
+
// Arrange
|
|
153
|
+
const mockApi = {
|
|
154
|
+
get: jest.fn().mockResolvedValue({ data: { name: 'John' } }),
|
|
155
|
+
};
|
|
156
|
+
|
|
157
|
+
// Act
|
|
158
|
+
const result = await fetchUserData(mockApi, 'user-id');
|
|
159
|
+
|
|
160
|
+
// Assert
|
|
161
|
+
expect(result).toEqual({ name: 'John' });
|
|
162
|
+
expect(mockApi.get).toHaveBeenCalledWith('/users/user-id');
|
|
163
|
+
});
|
|
164
|
+
|
|
165
|
+
it('should handle API errors gracefully', async () => {
|
|
166
|
+
const mockApi = {
|
|
167
|
+
get: jest.fn().mockRejectedValue(new Error('Network error')),
|
|
168
|
+
};
|
|
169
|
+
|
|
170
|
+
await expect(fetchUserData(mockApi, 'user-id'))
|
|
171
|
+
.rejects.toThrow('Failed to fetch user');
|
|
172
|
+
});
|
|
173
|
+
});
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
---
|
|
177
|
+
|
|
178
|
+
## Mocking Strategies
|
|
179
|
+
|
|
180
|
+
### Mock Functions
|
|
181
|
+
|
|
182
|
+
```typescript
|
|
183
|
+
// Create mock function
|
|
184
|
+
const mockFn = jest.fn();
|
|
185
|
+
|
|
186
|
+
// Define return value
|
|
187
|
+
mockFn.mockReturnValue('static value');
|
|
188
|
+
mockFn.mockResolvedValue('async value');
|
|
189
|
+
mockFn.mockRejectedValue(new Error('error'));
|
|
190
|
+
|
|
191
|
+
// Implementation
|
|
192
|
+
mockFn.mockImplementation((x) => x * 2);
|
|
193
|
+
|
|
194
|
+
// Verify calls
|
|
195
|
+
expect(mockFn).toHaveBeenCalled();
|
|
196
|
+
expect(mockFn).toHaveBeenCalledWith('arg1', 'arg2');
|
|
197
|
+
expect(mockFn).toHaveBeenCalledTimes(3);
|
|
198
|
+
```
|
|
199
|
+
|
|
200
|
+
### Mock Modules
|
|
201
|
+
|
|
202
|
+
```typescript
|
|
203
|
+
// Mock entire module
|
|
204
|
+
jest.mock('./database', () => ({
|
|
205
|
+
connect: jest.fn(),
|
|
206
|
+
query: jest.fn(),
|
|
207
|
+
}));
|
|
208
|
+
|
|
209
|
+
// Mock with factory
|
|
210
|
+
jest.mock('./config', () => ({
|
|
211
|
+
get: (key: string) => {
|
|
212
|
+
const config = { API_URL: 'http://test-api.com' };
|
|
213
|
+
return config[key];
|
|
214
|
+
},
|
|
215
|
+
}));
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
### Spying
|
|
219
|
+
|
|
220
|
+
```typescript
|
|
221
|
+
// Spy on existing method
|
|
222
|
+
const spy = jest.spyOn(userService, 'sendEmail');
|
|
223
|
+
|
|
224
|
+
// Call the code
|
|
225
|
+
await userService.createUser({ email: 'test@example.com' });
|
|
226
|
+
|
|
227
|
+
// Verify the spy
|
|
228
|
+
expect(spy).toHaveBeenCalled();
|
|
229
|
+
|
|
230
|
+
// Restore original
|
|
231
|
+
spy.mockRestore();
|
|
232
|
+
```
|
|
233
|
+
|
|
234
|
+
---
|
|
235
|
+
|
|
236
|
+
## Integration Testing
|
|
237
|
+
|
|
238
|
+
### API Integration Tests
|
|
239
|
+
|
|
240
|
+
```typescript
|
|
241
|
+
describe('POST /users', () => {
|
|
242
|
+
let app: Express;
|
|
243
|
+
let db: Database;
|
|
244
|
+
|
|
245
|
+
beforeAll(async () => {
|
|
246
|
+
db = await Database.connect(TEST_DB_URL);
|
|
247
|
+
app = createApp(db);
|
|
248
|
+
});
|
|
249
|
+
|
|
250
|
+
afterAll(async () => {
|
|
251
|
+
await db.disconnect();
|
|
252
|
+
});
|
|
253
|
+
|
|
254
|
+
beforeEach(async () => {
|
|
255
|
+
await db.clear('users');
|
|
256
|
+
});
|
|
257
|
+
|
|
258
|
+
it('should create user and return 201', async () => {
|
|
259
|
+
const response = await request(app)
|
|
260
|
+
.post('/users')
|
|
261
|
+
.send({ email: 'test@example.com', password: 'Password123!' })
|
|
262
|
+
.expect(201);
|
|
263
|
+
|
|
264
|
+
expect(response.body.email).toBe('test@example.com');
|
|
265
|
+
expect(response.body.password).toBeUndefined();
|
|
266
|
+
|
|
267
|
+
// Verify in database
|
|
268
|
+
const user = await db.users.findOne({ email: 'test@example.com' });
|
|
269
|
+
expect(user).toBeDefined();
|
|
270
|
+
});
|
|
271
|
+
|
|
272
|
+
it('should return 400 for invalid email', async () => {
|
|
273
|
+
const response = await request(app)
|
|
274
|
+
.post('/users')
|
|
275
|
+
.send({ email: 'invalid', password: 'Password123!' })
|
|
276
|
+
.expect(400);
|
|
277
|
+
|
|
278
|
+
expect(response.body.errors).toContainEqual(
|
|
279
|
+
expect.objectContaining({ field: 'email' })
|
|
280
|
+
);
|
|
281
|
+
});
|
|
282
|
+
});
|
|
283
|
+
```
|
|
284
|
+
|
|
285
|
+
### Database Integration Tests
|
|
286
|
+
|
|
287
|
+
```typescript
|
|
288
|
+
describe('UserRepository', () => {
|
|
289
|
+
let db: Database;
|
|
290
|
+
let repo: UserRepository;
|
|
291
|
+
|
|
292
|
+
beforeAll(async () => {
|
|
293
|
+
db = await Database.connect(TEST_DB_URL);
|
|
294
|
+
repo = new UserRepository(db);
|
|
295
|
+
});
|
|
296
|
+
|
|
297
|
+
beforeEach(async () => {
|
|
298
|
+
await db.clear('users');
|
|
299
|
+
await db.seed('users', testUsers);
|
|
300
|
+
});
|
|
301
|
+
|
|
302
|
+
it('should find user by email', async () => {
|
|
303
|
+
const user = await repo.findByEmail('john@example.com');
|
|
304
|
+
expect(user?.name).toBe('John Doe');
|
|
305
|
+
});
|
|
306
|
+
|
|
307
|
+
it('should return null for non-existent email', async () => {
|
|
308
|
+
const user = await repo.findByEmail('nobody@example.com');
|
|
309
|
+
expect(user).toBeNull();
|
|
310
|
+
});
|
|
311
|
+
});
|
|
312
|
+
```
|
|
313
|
+
|
|
314
|
+
---
|
|
315
|
+
|
|
316
|
+
## E2E Testing
|
|
317
|
+
|
|
318
|
+
### Playwright Example
|
|
319
|
+
|
|
320
|
+
```typescript
|
|
321
|
+
import { test, expect } from '@playwright/test';
|
|
322
|
+
|
|
323
|
+
test.describe('User Registration', () => {
|
|
324
|
+
test('should complete registration flow', async ({ page }) => {
|
|
325
|
+
// Navigate to registration
|
|
326
|
+
await page.goto('/register');
|
|
327
|
+
|
|
328
|
+
// Fill form
|
|
329
|
+
await page.fill('[data-testid="email"]', 'newuser@example.com');
|
|
330
|
+
await page.fill('[data-testid="password"]', 'SecurePassword123!');
|
|
331
|
+
await page.fill('[data-testid="name"]', 'New User');
|
|
332
|
+
|
|
333
|
+
// Submit
|
|
334
|
+
await page.click('[data-testid="submit"]');
|
|
335
|
+
|
|
336
|
+
// Verify redirect to dashboard
|
|
337
|
+
await expect(page).toHaveURL('/dashboard');
|
|
338
|
+
await expect(page.locator('[data-testid="welcome-message"]'))
|
|
339
|
+
.toContainText('Welcome, New User');
|
|
340
|
+
});
|
|
341
|
+
|
|
342
|
+
test('should show validation errors', async ({ page }) => {
|
|
343
|
+
await page.goto('/register');
|
|
344
|
+
|
|
345
|
+
await page.fill('[data-testid="email"]', 'invalid-email');
|
|
346
|
+
await page.click('[data-testid="submit"]');
|
|
347
|
+
|
|
348
|
+
await expect(page.locator('[data-testid="email-error"]'))
|
|
349
|
+
.toBeVisible();
|
|
350
|
+
});
|
|
351
|
+
});
|
|
352
|
+
```
|
|
353
|
+
|
|
354
|
+
---
|
|
355
|
+
|
|
356
|
+
## Test Coverage
|
|
357
|
+
|
|
358
|
+
### Coverage Targets
|
|
359
|
+
|
|
360
|
+
```yaml
|
|
361
|
+
coverage_targets:
|
|
362
|
+
statements: 80%
|
|
363
|
+
branches: 80%
|
|
364
|
+
functions: 80%
|
|
365
|
+
lines: 80%
|
|
366
|
+
|
|
367
|
+
priority_areas:
|
|
368
|
+
critical: 95%+ # Auth, payments, core business logic
|
|
369
|
+
high: 85%+ # API endpoints, services
|
|
370
|
+
medium: 70%+ # Utilities, helpers
|
|
371
|
+
low: 50%+ # UI components, config
|
|
372
|
+
```
|
|
373
|
+
|
|
374
|
+
### Coverage Configuration
|
|
375
|
+
|
|
376
|
+
```javascript
|
|
377
|
+
// jest.config.js
|
|
378
|
+
module.exports = {
|
|
379
|
+
collectCoverage: true,
|
|
380
|
+
coverageDirectory: 'coverage',
|
|
381
|
+
coverageReporters: ['text', 'lcov', 'html'],
|
|
382
|
+
coverageThreshold: {
|
|
383
|
+
global: {
|
|
384
|
+
branches: 80,
|
|
385
|
+
functions: 80,
|
|
386
|
+
lines: 80,
|
|
387
|
+
statements: 80,
|
|
388
|
+
},
|
|
389
|
+
},
|
|
390
|
+
collectCoverageFrom: [
|
|
391
|
+
'src/**/*.{ts,tsx}',
|
|
392
|
+
'!src/**/*.d.ts',
|
|
393
|
+
'!src/**/*.stories.{ts,tsx}',
|
|
394
|
+
'!src/test/**/*',
|
|
395
|
+
],
|
|
396
|
+
};
|
|
397
|
+
```
|
|
398
|
+
|
|
399
|
+
---
|
|
400
|
+
|
|
401
|
+
## Fixing Flaky Tests
|
|
402
|
+
|
|
403
|
+
### Common Causes & Solutions
|
|
404
|
+
|
|
405
|
+
| Cause | Symptom | Solution |
|
|
406
|
+
|-------|---------|----------|
|
|
407
|
+
| Race conditions | Fails randomly | Add proper waits, use async/await correctly |
|
|
408
|
+
| Shared state | Fails when run together | Isolate test data, proper cleanup |
|
|
409
|
+
| Time-dependent | Fails at certain times | Mock Date/time |
|
|
410
|
+
| External dependencies | Fails intermittently | Mock external services |
|
|
411
|
+
| Order dependency | Fails when run in different order | Make tests independent |
|
|
412
|
+
|
|
413
|
+
### Debugging Flaky Tests
|
|
414
|
+
|
|
415
|
+
```typescript
|
|
416
|
+
// Add retries for known flaky tests (use sparingly!)
|
|
417
|
+
test('flaky network test', { retry: 2 }, async () => {
|
|
418
|
+
// ...
|
|
419
|
+
});
|
|
420
|
+
|
|
421
|
+
// Log more info on failure
|
|
422
|
+
afterEach(function() {
|
|
423
|
+
if (this.currentTest?.state === 'failed') {
|
|
424
|
+
console.log('Test state:', JSON.stringify(testState, null, 2));
|
|
425
|
+
}
|
|
426
|
+
});
|
|
427
|
+
|
|
428
|
+
// Increase timeout if needed
|
|
429
|
+
test('slow test', async () => {
|
|
430
|
+
// ...
|
|
431
|
+
}, 30000); // 30 second timeout
|
|
432
|
+
```
|
|
433
|
+
|
|
434
|
+
---
|
|
435
|
+
|
|
436
|
+
## Test Organization
|
|
437
|
+
|
|
438
|
+
### File Structure
|
|
439
|
+
|
|
440
|
+
```
|
|
441
|
+
src/
|
|
442
|
+
├── users/
|
|
443
|
+
│ ├── users.service.ts
|
|
444
|
+
│ ├── users.service.spec.ts # Unit tests
|
|
445
|
+
│ └── users.controller.ts
|
|
446
|
+
│
|
|
447
|
+
tests/
|
|
448
|
+
├── unit/ # Additional unit tests
|
|
449
|
+
├── integration/
|
|
450
|
+
│ ├── api/
|
|
451
|
+
│ │ └── users.api.spec.ts
|
|
452
|
+
│ └── db/
|
|
453
|
+
│ └── users.repo.spec.ts
|
|
454
|
+
├── e2e/
|
|
455
|
+
│ └── user-registration.spec.ts
|
|
456
|
+
├── fixtures/
|
|
457
|
+
│ └── users.fixture.ts
|
|
458
|
+
└── helpers/
|
|
459
|
+
├── database.helper.ts
|
|
460
|
+
└── auth.helper.ts
|
|
461
|
+
```
|
|
462
|
+
|
|
463
|
+
### Test Naming Conventions
|
|
464
|
+
|
|
465
|
+
```typescript
|
|
466
|
+
// Use descriptive names
|
|
467
|
+
describe('UserService')
|
|
468
|
+
describe('createUser method')
|
|
469
|
+
|
|
470
|
+
// "should" format
|
|
471
|
+
it('should create user with valid data')
|
|
472
|
+
it('should throw when email is duplicate')
|
|
473
|
+
it('should hash password before saving')
|
|
474
|
+
|
|
475
|
+
// Given-When-Then for complex scenarios
|
|
476
|
+
it('given authenticated admin, when deleting user, should succeed')
|
|
477
|
+
```
|
|
478
|
+
|
|
479
|
+
---
|
|
480
|
+
|
|
481
|
+
## Guidelines
|
|
482
|
+
|
|
483
|
+
### DO ✅
|
|
484
|
+
- Write tests before code (TDD)
|
|
485
|
+
- Test behavior, not implementation
|
|
486
|
+
- Keep tests independent
|
|
487
|
+
- Use descriptive test names
|
|
488
|
+
- Test edge cases and errors
|
|
489
|
+
- Clean up after tests
|
|
490
|
+
|
|
491
|
+
### DON'T ❌
|
|
492
|
+
- Test private methods directly
|
|
493
|
+
- Share state between tests
|
|
494
|
+
- Test framework/library code
|
|
495
|
+
- Write tests that always pass
|
|
496
|
+
- Ignore flaky tests
|
|
497
|
+
- Mock everything
|
|
498
|
+
|
|
499
|
+
---
|
|
500
|
+
|
|
501
|
+
## Test Quality Checklist
|
|
502
|
+
|
|
503
|
+
```yaml
|
|
504
|
+
test_quality:
|
|
505
|
+
- Tests run independently in any order
|
|
506
|
+
- Tests don't depend on external services
|
|
507
|
+
- Tests are deterministic (not flaky)
|
|
508
|
+
- Tests are fast (<100ms for unit tests)
|
|
509
|
+
- Tests have meaningful assertions
|
|
510
|
+
- Tests cover happy path AND error cases
|
|
511
|
+
- Tests are readable and maintainable
|
|
512
|
+
- Tests use realistic data
|
|
513
|
+
```
|
|
514
|
+
|
|
515
|
+
---
|
|
516
|
+
|
|
517
|
+
## Success Criteria
|
|
518
|
+
|
|
519
|
+
Before considering testing complete:
|
|
520
|
+
|
|
521
|
+
- [ ] All new code has tests
|
|
522
|
+
- [ ] Coverage meets targets
|
|
523
|
+
- [ ] All tests pass consistently
|
|
524
|
+
- [ ] No flaky tests
|
|
525
|
+
- [ ] Edge cases covered
|
|
526
|
+
- [ ] Error conditions tested
|
|
527
|
+
- [ ] Tests run in CI pipeline
|
|
528
|
+
- [ ] Tests are maintainable
|
|
529
|
+
|
|
530
|
+
---
|
|
531
|
+
|
|
532
|
+
## Related Skills
|
|
533
|
+
|
|
534
|
+
- `skills/kilo-kit/quality/code-review/` - For reviewing test quality
|
|
535
|
+
- `skills/kilo-kit/debugging/verification/` - For verifying fixes
|
|
536
|
+
- `skills/kilo-kit/development/backend/` - For testing APIs
|
|
537
|
+
|
|
538
|
+
---
|
|
539
|
+
|
|
540
|
+
*Testing Strategy Skill v1.0.0 — Test it or regret it*
|