@smicolon/ai-kit 0.3.2 → 0.4.1
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/README.md +73 -40
- package/dist/index.js +312 -127
- package/package.json +5 -5
- package/.claude-plugin/marketplace.json +0 -369
- package/packs/architect/CHANGELOG.md +0 -17
- package/packs/architect/README.md +0 -58
- package/packs/architect/agents/system-architect.md +0 -768
- package/packs/architect/commands/diagram-create.md +0 -300
- package/packs/better-auth/.mcp.json +0 -14
- package/packs/better-auth/CHANGELOG.md +0 -26
- package/packs/better-auth/README.md +0 -125
- package/packs/better-auth/agents/auth-architect.md +0 -278
- package/packs/better-auth/commands/auth-provider-add.md +0 -265
- package/packs/better-auth/commands/auth-setup.md +0 -298
- package/packs/better-auth/skills/auth-security/SKILL.md +0 -425
- package/packs/better-auth/skills/better-auth-patterns/SKILL.md +0 -455
- package/packs/dev-loop/CHANGELOG.md +0 -69
- package/packs/dev-loop/README.md +0 -155
- package/packs/dev-loop/commands/cancel-dev.md +0 -21
- package/packs/dev-loop/commands/dev-loop.md +0 -72
- package/packs/dev-loop/commands/dev-plan.md +0 -351
- package/packs/dev-loop/hooks/hooks.json +0 -15
- package/packs/dev-loop/hooks/stop-hook.sh +0 -178
- package/packs/dev-loop/scripts/setup-dev-loop.sh +0 -194
- package/packs/dev-loop/skills/tdd-planner/SKILL.md +0 -249
- package/packs/dev-loop/skills/tdd-planner/references/framework-patterns.md +0 -874
- package/packs/dev-loop/skills/tdd-planner/references/good-example.md +0 -260
- package/packs/dev-loop/skills/tdd-planner/references/plan-template.md +0 -275
- package/packs/django/CHANGELOG.md +0 -39
- package/packs/django/README.md +0 -92
- package/packs/django/agents/django-architect.md +0 -182
- package/packs/django/agents/django-builder.md +0 -250
- package/packs/django/agents/django-feature-based.md +0 -420
- package/packs/django/agents/django-reviewer.md +0 -253
- package/packs/django/agents/django-tester.md +0 -230
- package/packs/django/commands/api-endpoint.md +0 -285
- package/packs/django/commands/model-create.md +0 -178
- package/packs/django/commands/test-generate.md +0 -325
- package/packs/django/rules/migrations.md +0 -138
- package/packs/django/rules/models.md +0 -167
- package/packs/django/rules/serializers.md +0 -126
- package/packs/django/rules/services.md +0 -131
- package/packs/django/rules/tests.md +0 -140
- package/packs/django/rules/views.md +0 -102
- package/packs/django/skills/import-convention-enforcer/SKILL.md +0 -226
- package/packs/django/skills/import-convention-enforcer/patterns/django-imports.md +0 -343
- package/packs/django/skills/migration-safety-checker/SKILL.md +0 -375
- package/packs/django/skills/model-entity-validator/SKILL.md +0 -298
- package/packs/django/skills/performance-optimizer/SKILL.md +0 -447
- package/packs/django/skills/red-phase-verifier/SKILL.md +0 -180
- package/packs/django/skills/security-first-validator/SKILL.md +0 -435
- package/packs/django/skills/test-coverage-advisor/SKILL.md +0 -394
- package/packs/django/skills/test-validity-checker/SKILL.md +0 -194
- package/packs/failure-log/CHANGELOG.md +0 -20
- package/packs/failure-log/README.md +0 -168
- package/packs/failure-log/commands/failure-add.md +0 -106
- package/packs/failure-log/commands/failure-list.md +0 -89
- package/packs/failure-log/hooks/hooks.json +0 -16
- package/packs/failure-log/hooks/scripts/inject-failures.sh +0 -64
- package/packs/failure-log/skills/failure-log-manager/SKILL.md +0 -164
- package/packs/flutter/CHANGELOG.md +0 -19
- package/packs/flutter/README.md +0 -170
- package/packs/flutter/agents/flutter-architect.md +0 -166
- package/packs/flutter/agents/flutter-builder.md +0 -303
- package/packs/flutter/agents/release-manager.md +0 -355
- package/packs/flutter/commands/fastlane-setup.md +0 -188
- package/packs/flutter/commands/flutter-build.md +0 -90
- package/packs/flutter/commands/flutter-deploy.md +0 -133
- package/packs/flutter/commands/flutter-test.md +0 -117
- package/packs/flutter/commands/signing-setup.md +0 -209
- package/packs/flutter/hooks/hooks.json +0 -17
- package/packs/flutter/skills/fastlane-knowledge/SKILL.md +0 -193
- package/packs/flutter/skills/flutter-architecture/SKILL.md +0 -127
- package/packs/flutter/skills/store-publishing/SKILL.md +0 -163
- package/packs/hono/CHANGELOG.md +0 -19
- package/packs/hono/README.md +0 -143
- package/packs/hono/agents/hono-architect.md +0 -240
- package/packs/hono/agents/hono-builder.md +0 -285
- package/packs/hono/agents/hono-reviewer.md +0 -279
- package/packs/hono/agents/hono-tester.md +0 -346
- package/packs/hono/commands/middleware-create.md +0 -223
- package/packs/hono/commands/project-init.md +0 -306
- package/packs/hono/commands/route-create.md +0 -153
- package/packs/hono/commands/rpc-client.md +0 -263
- package/packs/hono/skills/cloudflare-bindings/SKILL.md +0 -408
- package/packs/hono/skills/hono-patterns/SKILL.md +0 -309
- package/packs/hono/skills/rpc-typesafe/SKILL.md +0 -388
- package/packs/hono/skills/zod-validation/SKILL.md +0 -332
- package/packs/nestjs/CHANGELOG.md +0 -29
- package/packs/nestjs/README.md +0 -75
- package/packs/nestjs/agents/nestjs-architect.md +0 -402
- package/packs/nestjs/agents/nestjs-builder.md +0 -301
- package/packs/nestjs/agents/nestjs-tester.md +0 -437
- package/packs/nestjs/commands/module-create.md +0 -369
- package/packs/nestjs/rules/controllers.md +0 -92
- package/packs/nestjs/rules/dto.md +0 -124
- package/packs/nestjs/rules/entities.md +0 -102
- package/packs/nestjs/rules/services.md +0 -106
- package/packs/nestjs/skills/barrel-export-manager/SKILL.md +0 -389
- package/packs/nestjs/skills/import-convention-enforcer/SKILL.md +0 -365
- package/packs/nextjs/CHANGELOG.md +0 -36
- package/packs/nextjs/README.md +0 -76
- package/packs/nextjs/agents/frontend-tester.md +0 -680
- package/packs/nextjs/agents/frontend-visual.md +0 -820
- package/packs/nextjs/agents/nextjs-architect.md +0 -331
- package/packs/nextjs/agents/nextjs-modular.md +0 -433
- package/packs/nextjs/commands/component-create.md +0 -398
- package/packs/nextjs/rules/api-routes.md +0 -129
- package/packs/nextjs/rules/components.md +0 -106
- package/packs/nextjs/rules/hooks.md +0 -132
- package/packs/nextjs/skills/accessibility-validator/SKILL.md +0 -445
- package/packs/nextjs/skills/import-convention-enforcer/SKILL.md +0 -399
- package/packs/nextjs/skills/react-form-validator/SKILL.md +0 -569
- package/packs/nuxtjs/CHANGELOG.md +0 -30
- package/packs/nuxtjs/README.md +0 -56
- package/packs/nuxtjs/agents/frontend-tester.md +0 -680
- package/packs/nuxtjs/agents/frontend-visual.md +0 -820
- package/packs/nuxtjs/agents/nuxtjs-architect.md +0 -537
- package/packs/nuxtjs/commands/component-create.md +0 -223
- package/packs/nuxtjs/rules/components.md +0 -101
- package/packs/nuxtjs/rules/composables.md +0 -118
- package/packs/nuxtjs/rules/server-routes.md +0 -127
- package/packs/nuxtjs/skills/accessibility-validator/SKILL.md +0 -183
- package/packs/nuxtjs/skills/import-convention-enforcer/SKILL.md +0 -196
- package/packs/nuxtjs/skills/veevalidate-form-validator/SKILL.md +0 -190
- package/packs/onboard/CHANGELOG.md +0 -22
- package/packs/onboard/README.md +0 -103
- package/packs/onboard/agents/onboard-guide.md +0 -118
- package/packs/onboard/commands/onboard.md +0 -313
- package/packs/onboard/skills/onboard-context-provider/SKILL.md +0 -98
- package/packs/tanstack-router/CHANGELOG.md +0 -30
- package/packs/tanstack-router/README.md +0 -113
- package/packs/tanstack-router/agents/tanstack-architect.md +0 -173
- package/packs/tanstack-router/agents/tanstack-builder.md +0 -360
- package/packs/tanstack-router/agents/tanstack-tester.md +0 -454
- package/packs/tanstack-router/commands/form-create.md +0 -313
- package/packs/tanstack-router/commands/query-create.md +0 -263
- package/packs/tanstack-router/commands/route-create.md +0 -190
- package/packs/tanstack-router/commands/table-create.md +0 -413
- package/packs/tanstack-router/skills/ai-patterns/SKILL.md +0 -370
- package/packs/tanstack-router/skills/db-patterns/SKILL.md +0 -346
- package/packs/tanstack-router/skills/devtools-patterns/SKILL.md +0 -415
- package/packs/tanstack-router/skills/form-patterns/SKILL.md +0 -425
- package/packs/tanstack-router/skills/pacer-patterns/SKILL.md +0 -341
- package/packs/tanstack-router/skills/query-patterns/SKILL.md +0 -359
- package/packs/tanstack-router/skills/router-patterns/SKILL.md +0 -285
- package/packs/tanstack-router/skills/store-patterns/SKILL.md +0 -351
- package/packs/tanstack-router/skills/table-patterns/SKILL.md +0 -531
- package/packs/tanstack-router/skills/tanstack-conventions/SKILL.md +0 -428
- package/packs/tanstack-router/skills/virtual-patterns/SKILL.md +0 -490
- package/packs/worktree/CHANGELOG.md +0 -45
- package/packs/worktree/README.md +0 -219
- package/packs/worktree/commands/wt.md +0 -93
- package/packs/worktree/scripts/wt.sh +0 -957
- package/packs/worktree/skills/worktree-manager/SKILL.md +0 -113
|
@@ -1,394 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: test-coverage-advisor
|
|
3
|
-
description: This skill should be used when the user asks to "write tests", "generate tests", "check coverage", "add test cases", or when completing features and saying "done", "finished", "ready for review". Suggests tests for 90%+ coverage.
|
|
4
|
-
---
|
|
5
|
-
|
|
6
|
-
# Test Coverage Advisor
|
|
7
|
-
|
|
8
|
-
Auto-suggests comprehensive test cases to achieve Smicolon's 90%+ coverage target.
|
|
9
|
-
|
|
10
|
-
## Activation Triggers
|
|
11
|
-
|
|
12
|
-
This skill activates when:
|
|
13
|
-
- Completing feature implementation
|
|
14
|
-
- Mentioning "done", "finished", "ready", "complete"
|
|
15
|
-
- Saying "review this code"
|
|
16
|
-
- Creating models, services, views, or APIs
|
|
17
|
-
- Asking about testing
|
|
18
|
-
- Before code is marked as complete
|
|
19
|
-
|
|
20
|
-
## Coverage Target (MANDATORY)
|
|
21
|
-
|
|
22
|
-
**90%+ test coverage required for ALL code.**
|
|
23
|
-
|
|
24
|
-
Test categories:
|
|
25
|
-
1. **Unit Tests** - Models, services, utilities (80%+ of tests)
|
|
26
|
-
2. **Integration Tests** - API endpoints, workflows (15%+ of tests)
|
|
27
|
-
3. **Edge Cases** - Error handling, validation (5%+ of tests)
|
|
28
|
-
|
|
29
|
-
## Auto-Analysis Process
|
|
30
|
-
|
|
31
|
-
### Step 1: Identify Untested Code
|
|
32
|
-
|
|
33
|
-
When feature implementation is complete, scan for:
|
|
34
|
-
|
|
35
|
-
```python
|
|
36
|
-
# models.py - Has tests? ❓
|
|
37
|
-
class User(models.Model):
|
|
38
|
-
def activate(self): # Needs test
|
|
39
|
-
self.is_active = True
|
|
40
|
-
self.save()
|
|
41
|
-
|
|
42
|
-
# services.py - Has tests? ❓
|
|
43
|
-
class UserService:
|
|
44
|
-
@staticmethod
|
|
45
|
-
def create_user(data): # Needs test
|
|
46
|
-
# ...business logic
|
|
47
|
-
|
|
48
|
-
# views.py - Has tests? ❓
|
|
49
|
-
class UserViewSet(viewsets.ModelViewSet):
|
|
50
|
-
def create(self, request): # Needs test
|
|
51
|
-
# ...
|
|
52
|
-
```
|
|
53
|
-
|
|
54
|
-
### Step 2: Calculate Coverage Gap
|
|
55
|
-
|
|
56
|
-
```
|
|
57
|
-
Current coverage: X%
|
|
58
|
-
Target coverage: 90%
|
|
59
|
-
Gap: Y%
|
|
60
|
-
Missing: Z test cases
|
|
61
|
-
```
|
|
62
|
-
|
|
63
|
-
### Step 3: Generate Missing Test Cases
|
|
64
|
-
|
|
65
|
-
**For Model:**
|
|
66
|
-
```python
|
|
67
|
-
# users/tests/test_models.py
|
|
68
|
-
import pytest
|
|
69
|
-
import users.models as _users_models
|
|
70
|
-
|
|
71
|
-
@pytest.mark.django_db
|
|
72
|
-
class TestUserModel:
|
|
73
|
-
"""User model tests."""
|
|
74
|
-
|
|
75
|
-
def test_create_user(self):
|
|
76
|
-
"""Test user creation with required fields."""
|
|
77
|
-
user = _users_models.User.objects.create(
|
|
78
|
-
email='test@example.com',
|
|
79
|
-
first_name='Test'
|
|
80
|
-
)
|
|
81
|
-
|
|
82
|
-
assert user.id is not None # UUID assigned
|
|
83
|
-
assert user.email == 'test@example.com'
|
|
84
|
-
assert user.created_at is not None
|
|
85
|
-
assert user.is_deleted is False
|
|
86
|
-
|
|
87
|
-
def test_user_str_representation(self):
|
|
88
|
-
"""Test __str__ returns email."""
|
|
89
|
-
user = _users_models.User.objects.create(email='test@example.com')
|
|
90
|
-
assert str(user) == 'test@example.com'
|
|
91
|
-
|
|
92
|
-
def test_activate_user(self):
|
|
93
|
-
"""Test activate method sets is_active."""
|
|
94
|
-
user = _users_models.User.objects.create(email='test@example.com')
|
|
95
|
-
user.activate()
|
|
96
|
-
|
|
97
|
-
assert user.is_active is True
|
|
98
|
-
|
|
99
|
-
def test_soft_delete(self):
|
|
100
|
-
"""Test soft delete sets is_deleted flag."""
|
|
101
|
-
user = _users_models.User.objects.create(email='test@example.com')
|
|
102
|
-
user.soft_delete()
|
|
103
|
-
|
|
104
|
-
assert user.is_deleted is True
|
|
105
|
-
# User still in database
|
|
106
|
-
assert _users_models.User.objects.filter(id=user.id).exists()
|
|
107
|
-
```
|
|
108
|
-
|
|
109
|
-
**For Service:**
|
|
110
|
-
```python
|
|
111
|
-
# users/tests/test_services.py
|
|
112
|
-
import pytest
|
|
113
|
-
from unittest.mock import Mock, patch
|
|
114
|
-
import users.models as _users_models
|
|
115
|
-
import users.services as _users_services
|
|
116
|
-
|
|
117
|
-
@pytest.mark.django_db
|
|
118
|
-
class TestUserService:
|
|
119
|
-
"""UserService tests."""
|
|
120
|
-
|
|
121
|
-
def test_create_user_success(self):
|
|
122
|
-
"""Test successful user creation."""
|
|
123
|
-
data = {'email': 'test@example.com', 'first_name': 'Test'}
|
|
124
|
-
user = _users_services.UserService.create_user(data)
|
|
125
|
-
|
|
126
|
-
assert user.email == 'test@example.com'
|
|
127
|
-
assert user.first_name == 'Test'
|
|
128
|
-
|
|
129
|
-
def test_create_user_duplicate_email(self):
|
|
130
|
-
"""Test creation fails with duplicate email."""
|
|
131
|
-
_users_models.User.objects.create(email='test@example.com')
|
|
132
|
-
|
|
133
|
-
with pytest.raises(ValidationError):
|
|
134
|
-
_users_services.UserService.create_user({'email': 'test@example.com'})
|
|
135
|
-
|
|
136
|
-
def test_create_user_invalid_data(self):
|
|
137
|
-
"""Test creation fails with invalid data."""
|
|
138
|
-
with pytest.raises(ValidationError):
|
|
139
|
-
_users_services.UserService.create_user({'email': 'invalid'})
|
|
140
|
-
|
|
141
|
-
@patch('users.services.send_welcome_email')
|
|
142
|
-
def test_create_user_sends_email(self, mock_send):
|
|
143
|
-
"""Test welcome email is sent on user creation."""
|
|
144
|
-
data = {'email': 'test@example.com'}
|
|
145
|
-
user = _users_services.UserService.create_user(data)
|
|
146
|
-
|
|
147
|
-
mock_send.assert_called_once_with(user)
|
|
148
|
-
```
|
|
149
|
-
|
|
150
|
-
**For API Endpoint:**
|
|
151
|
-
```python
|
|
152
|
-
# users/tests/test_views.py
|
|
153
|
-
import pytest
|
|
154
|
-
from rest_framework.test import APIClient
|
|
155
|
-
from rest_framework import status
|
|
156
|
-
import users.models as _users_models
|
|
157
|
-
|
|
158
|
-
@pytest.mark.django_db
|
|
159
|
-
class TestUserViewSet:
|
|
160
|
-
"""UserViewSet API tests."""
|
|
161
|
-
|
|
162
|
-
def setup_method(self):
|
|
163
|
-
"""Set up test client and user."""
|
|
164
|
-
self.client = APIClient()
|
|
165
|
-
self.user = _users_models.User.objects.create(
|
|
166
|
-
email='test@example.com'
|
|
167
|
-
)
|
|
168
|
-
self.client.force_authenticate(user=self.user)
|
|
169
|
-
|
|
170
|
-
def test_list_users_authenticated(self):
|
|
171
|
-
"""Test authenticated user can list users."""
|
|
172
|
-
response = self.client.get('/api/users/')
|
|
173
|
-
|
|
174
|
-
assert response.status_code == status.HTTP_200_OK
|
|
175
|
-
assert len(response.data) > 0
|
|
176
|
-
|
|
177
|
-
def test_list_users_unauthenticated(self):
|
|
178
|
-
"""Test unauthenticated request is rejected."""
|
|
179
|
-
self.client.force_authenticate(user=None)
|
|
180
|
-
response = self.client.get('/api/users/')
|
|
181
|
-
|
|
182
|
-
assert response.status_code == status.HTTP_401_UNAUTHORIZED
|
|
183
|
-
|
|
184
|
-
def test_create_user(self):
|
|
185
|
-
"""Test user creation via API."""
|
|
186
|
-
data = {'email': 'new@example.com', 'first_name': 'New'}
|
|
187
|
-
response = self.client.post('/api/users/', data)
|
|
188
|
-
|
|
189
|
-
assert response.status_code == status.HTTP_201_CREATED
|
|
190
|
-
assert response.data['email'] == 'new@example.com'
|
|
191
|
-
|
|
192
|
-
def test_create_user_invalid_data(self):
|
|
193
|
-
"""Test creation fails with invalid data."""
|
|
194
|
-
data = {'email': 'invalid'}
|
|
195
|
-
response = self.client.post('/api/users/', data)
|
|
196
|
-
|
|
197
|
-
assert response.status_code == status.HTTP_400_BAD_REQUEST
|
|
198
|
-
|
|
199
|
-
def test_update_user(self):
|
|
200
|
-
"""Test user update via PATCH."""
|
|
201
|
-
data = {'first_name': 'Updated'}
|
|
202
|
-
response = self.client.patch(f'/api/users/{self.user.id}/', data)
|
|
203
|
-
|
|
204
|
-
assert response.status_code == status.HTTP_200_OK
|
|
205
|
-
assert response.data['first_name'] == 'Updated'
|
|
206
|
-
|
|
207
|
-
def test_update_user_permission_denied(self):
|
|
208
|
-
"""Test user cannot update other users."""
|
|
209
|
-
other_user = _users_models.User.objects.create(email='other@example.com')
|
|
210
|
-
data = {'first_name': 'Hacked'}
|
|
211
|
-
response = self.client.patch(f'/api/users/{other_user.id}/', data)
|
|
212
|
-
|
|
213
|
-
assert response.status_code == status.HTTP_403_FORBIDDEN
|
|
214
|
-
|
|
215
|
-
def test_soft_delete_user(self):
|
|
216
|
-
"""Test user soft delete."""
|
|
217
|
-
response = self.client.delete(f'/api/users/{self.user.id}/')
|
|
218
|
-
|
|
219
|
-
assert response.status_code == status.HTTP_204_NO_CONTENT
|
|
220
|
-
self.user.refresh_from_db()
|
|
221
|
-
assert self.user.is_deleted is True
|
|
222
|
-
```
|
|
223
|
-
|
|
224
|
-
### Step 4: Report Coverage Plan
|
|
225
|
-
|
|
226
|
-
Provide a detailed report:
|
|
227
|
-
|
|
228
|
-
> **Test Coverage Analysis**
|
|
229
|
-
>
|
|
230
|
-
> **Untested Code Detected:**
|
|
231
|
-
> - `User` model: 4 methods
|
|
232
|
-
> - `UserService`: 3 methods
|
|
233
|
-
> - `UserViewSet`: 5 endpoints
|
|
234
|
-
>
|
|
235
|
-
> **Suggested Tests: 23**
|
|
236
|
-
> - Model tests: 8 (unit)
|
|
237
|
-
> - Service tests: 10 (unit + integration)
|
|
238
|
-
> - API tests: 5 (integration)
|
|
239
|
-
>
|
|
240
|
-
> **Estimated Coverage:**
|
|
241
|
-
> - Current: 45%
|
|
242
|
-
> - After tests: 92%
|
|
243
|
-
> - Target: 90% ✅
|
|
244
|
-
>
|
|
245
|
-
> **Implementation:**
|
|
246
|
-
> I can generate all tests now. Should I proceed?
|
|
247
|
-
|
|
248
|
-
## Edge Case Checklist
|
|
249
|
-
|
|
250
|
-
For every function/method, suggest tests for:
|
|
251
|
-
|
|
252
|
-
### Input Validation
|
|
253
|
-
- ✅ Valid input (happy path)
|
|
254
|
-
- ✅ Invalid input (validation errors)
|
|
255
|
-
- ✅ Missing required fields
|
|
256
|
-
- ✅ Empty strings/None values
|
|
257
|
-
- ✅ Boundary conditions (min/max)
|
|
258
|
-
|
|
259
|
-
### Business Logic
|
|
260
|
-
- ✅ Expected behavior
|
|
261
|
-
- ✅ Side effects (emails sent, logs created)
|
|
262
|
-
- ✅ Database changes
|
|
263
|
-
- ✅ Return values correct
|
|
264
|
-
|
|
265
|
-
### Error Handling
|
|
266
|
-
- ✅ Exceptions raised correctly
|
|
267
|
-
- ✅ Database errors handled
|
|
268
|
-
- ✅ External service failures
|
|
269
|
-
|
|
270
|
-
### Permissions
|
|
271
|
-
- ✅ Authenticated access
|
|
272
|
-
- ✅ Unauthorized rejection
|
|
273
|
-
- ✅ Permission-based access
|
|
274
|
-
- ✅ Ownership validation
|
|
275
|
-
|
|
276
|
-
### Edge Cases
|
|
277
|
-
- ✅ Concurrent modifications
|
|
278
|
-
- ✅ Duplicate entries
|
|
279
|
-
- ✅ Soft-deleted records
|
|
280
|
-
- ✅ Large datasets
|
|
281
|
-
|
|
282
|
-
## Test File Organization
|
|
283
|
-
|
|
284
|
-
```
|
|
285
|
-
users/
|
|
286
|
-
├── tests/
|
|
287
|
-
│ ├── __init__.py
|
|
288
|
-
│ ├── conftest.py # Shared fixtures
|
|
289
|
-
│ ├── test_models.py # Model unit tests
|
|
290
|
-
│ ├── test_services.py # Service tests
|
|
291
|
-
│ ├── test_serializers.py # Serializer tests
|
|
292
|
-
│ ├── test_views.py # API integration tests
|
|
293
|
-
│ └── test_permissions.py # Permission tests
|
|
294
|
-
```
|
|
295
|
-
|
|
296
|
-
## Pytest Configuration
|
|
297
|
-
|
|
298
|
-
Also suggest pytest setup:
|
|
299
|
-
|
|
300
|
-
```python
|
|
301
|
-
# conftest.py
|
|
302
|
-
import pytest
|
|
303
|
-
import users.models as _users_models
|
|
304
|
-
|
|
305
|
-
@pytest.fixture
|
|
306
|
-
def user():
|
|
307
|
-
"""Create test user."""
|
|
308
|
-
return _users_models.User.objects.create(
|
|
309
|
-
email='test@example.com',
|
|
310
|
-
first_name='Test'
|
|
311
|
-
)
|
|
312
|
-
|
|
313
|
-
@pytest.fixture
|
|
314
|
-
def authenticated_client(user):
|
|
315
|
-
"""Create authenticated API client."""
|
|
316
|
-
from rest_framework.test import APIClient
|
|
317
|
-
client = APIClient()
|
|
318
|
-
client.force_authenticate(user=user)
|
|
319
|
-
return client
|
|
320
|
-
```
|
|
321
|
-
|
|
322
|
-
```ini
|
|
323
|
-
# pytest.ini
|
|
324
|
-
[pytest]
|
|
325
|
-
DJANGO_SETTINGS_MODULE = config.settings.test
|
|
326
|
-
python_files = tests.py test_*.py *_tests.py
|
|
327
|
-
addopts = --cov=. --cov-report=html --cov-report=term-missing
|
|
328
|
-
```
|
|
329
|
-
|
|
330
|
-
## Factory Pattern (factory_boy)
|
|
331
|
-
|
|
332
|
-
For complex test data, suggest factories:
|
|
333
|
-
|
|
334
|
-
```python
|
|
335
|
-
# users/tests/factories.py
|
|
336
|
-
import factory
|
|
337
|
-
import users.models as _users_models
|
|
338
|
-
|
|
339
|
-
class UserFactory(factory.django.DjangoModelFactory):
|
|
340
|
-
class Meta:
|
|
341
|
-
model = _users_models.User
|
|
342
|
-
|
|
343
|
-
email = factory.Sequence(lambda n: f'user{n}@example.com')
|
|
344
|
-
first_name = factory.Faker('first_name')
|
|
345
|
-
last_name = factory.Faker('last_name')
|
|
346
|
-
|
|
347
|
-
# Usage in tests
|
|
348
|
-
def test_bulk_users():
|
|
349
|
-
users = UserFactory.create_batch(100) # Create 100 users
|
|
350
|
-
assert len(users) == 100
|
|
351
|
-
```
|
|
352
|
-
|
|
353
|
-
## Integration with CI/CD
|
|
354
|
-
|
|
355
|
-
Suggest coverage enforcement in CI:
|
|
356
|
-
|
|
357
|
-
```yaml
|
|
358
|
-
# .github/workflows/tests.yml
|
|
359
|
-
- name: Run tests with coverage
|
|
360
|
-
run: |
|
|
361
|
-
pytest --cov=. --cov-fail-under=90
|
|
362
|
-
```
|
|
363
|
-
|
|
364
|
-
## Success Criteria
|
|
365
|
-
|
|
366
|
-
✅ 90%+ coverage achieved
|
|
367
|
-
✅ All models tested
|
|
368
|
-
✅ All services tested
|
|
369
|
-
✅ All API endpoints tested
|
|
370
|
-
✅ Edge cases covered
|
|
371
|
-
✅ Permissions tested
|
|
372
|
-
✅ Error handling tested
|
|
373
|
-
|
|
374
|
-
## Behavior
|
|
375
|
-
|
|
376
|
-
**Proactive enforcement:**
|
|
377
|
-
- Analyze coverage without being asked
|
|
378
|
-
- Suggest tests when code is complete
|
|
379
|
-
- Generate complete test files
|
|
380
|
-
- Explain what each test verifies
|
|
381
|
-
- Calculate coverage impact
|
|
382
|
-
|
|
383
|
-
**Never:**
|
|
384
|
-
- Require explicit "write tests" request
|
|
385
|
-
- Wait for coverage report
|
|
386
|
-
- Just list what to test without writing tests
|
|
387
|
-
|
|
388
|
-
**When user says "done" or "ready":**
|
|
389
|
-
- Immediately analyze test coverage
|
|
390
|
-
- Identify gaps
|
|
391
|
-
- Suggest (or write) missing tests
|
|
392
|
-
- Don't let code be "complete" without tests
|
|
393
|
-
|
|
394
|
-
This ensures 90%+ coverage is maintained from day one.
|
|
@@ -1,194 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: test-validity-checker
|
|
3
|
-
description: This skill should be used when the user asks to "check tests", "validate tests", "review test quality", "verify test coverage", or when writing test files or running pytest. Ensures tests are meaningful.
|
|
4
|
-
---
|
|
5
|
-
|
|
6
|
-
# Test Validity Checker
|
|
7
|
-
|
|
8
|
-
Auto-validates that tests are meaningful and catch real bugs.
|
|
9
|
-
|
|
10
|
-
## Activation Triggers
|
|
11
|
-
|
|
12
|
-
This skill activates when:
|
|
13
|
-
- Writing test files
|
|
14
|
-
- Before pytest execution
|
|
15
|
-
- When test coverage is checked
|
|
16
|
-
- When dev loop is running
|
|
17
|
-
|
|
18
|
-
## Validity Checks
|
|
19
|
-
|
|
20
|
-
### Check 1: Empty Test Detection
|
|
21
|
-
|
|
22
|
-
```python
|
|
23
|
-
# INVALID - Empty body
|
|
24
|
-
def test_user():
|
|
25
|
-
pass
|
|
26
|
-
|
|
27
|
-
# INVALID - Only setup, no assertions
|
|
28
|
-
def test_create():
|
|
29
|
-
user = create_user()
|
|
30
|
-
# No assertions!
|
|
31
|
-
|
|
32
|
-
# VALID
|
|
33
|
-
def test_user_creation():
|
|
34
|
-
user = create_user()
|
|
35
|
-
assert user.id is not None
|
|
36
|
-
assert user.is_active
|
|
37
|
-
```
|
|
38
|
-
|
|
39
|
-
**Action**: Flag empty tests, require assertions
|
|
40
|
-
|
|
41
|
-
### Check 2: Trivial Assertion Detection
|
|
42
|
-
|
|
43
|
-
```python
|
|
44
|
-
# INVALID - Always passes
|
|
45
|
-
def test_always_passes():
|
|
46
|
-
assert True
|
|
47
|
-
|
|
48
|
-
def test_truthy():
|
|
49
|
-
user = create_user()
|
|
50
|
-
assert user # Just checks existence
|
|
51
|
-
|
|
52
|
-
# INVALID - Testing constants
|
|
53
|
-
def test_constant():
|
|
54
|
-
assert 1 + 1 == 2
|
|
55
|
-
|
|
56
|
-
# VALID - Tests actual behavior
|
|
57
|
-
def test_user_email_lowercase():
|
|
58
|
-
user = create_user(email='TEST@Example.COM')
|
|
59
|
-
assert user.email == 'test@example.com'
|
|
60
|
-
```
|
|
61
|
-
|
|
62
|
-
**Action**: Require value comparisons, not just truthiness
|
|
63
|
-
|
|
64
|
-
### Check 3: Assertion Count
|
|
65
|
-
|
|
66
|
-
```python
|
|
67
|
-
# WEAK - Only 1 assertion
|
|
68
|
-
def test_single_assertion():
|
|
69
|
-
response = client.get('/api/users/')
|
|
70
|
-
assert response.status_code == 200
|
|
71
|
-
|
|
72
|
-
# STRONG - Multiple assertions
|
|
73
|
-
def test_list_users():
|
|
74
|
-
response = client.get('/api/users/')
|
|
75
|
-
assert response.status_code == 200
|
|
76
|
-
assert 'results' in response.data
|
|
77
|
-
assert len(response.data['results']) > 0
|
|
78
|
-
assert 'email' in response.data['results'][0]
|
|
79
|
-
```
|
|
80
|
-
|
|
81
|
-
**Minimum**: 2 meaningful assertions per test
|
|
82
|
-
|
|
83
|
-
### Check 4: Edge Case Coverage
|
|
84
|
-
|
|
85
|
-
For each function under test, require:
|
|
86
|
-
|
|
87
|
-
- Happy path (valid input -> expected output)
|
|
88
|
-
- Invalid input (validation error)
|
|
89
|
-
- Boundary conditions (min, max, empty)
|
|
90
|
-
- Error handling (exceptions caught)
|
|
91
|
-
|
|
92
|
-
```python
|
|
93
|
-
# Complete test suite example
|
|
94
|
-
class TestUserService:
|
|
95
|
-
# Happy path
|
|
96
|
-
def test_create_user_success(self):
|
|
97
|
-
...
|
|
98
|
-
|
|
99
|
-
# Invalid input
|
|
100
|
-
def test_create_user_invalid_email(self):
|
|
101
|
-
with pytest.raises(ValidationError):
|
|
102
|
-
...
|
|
103
|
-
|
|
104
|
-
# Boundary
|
|
105
|
-
def test_create_user_max_length_name(self):
|
|
106
|
-
user = create_user(name='x' * 255) # Max length
|
|
107
|
-
...
|
|
108
|
-
|
|
109
|
-
# Error handling
|
|
110
|
-
def test_create_user_database_error(self, mocker):
|
|
111
|
-
mocker.patch('app.models.User.save', side_effect=DatabaseError)
|
|
112
|
-
with pytest.raises(ServiceError):
|
|
113
|
-
...
|
|
114
|
-
```
|
|
115
|
-
|
|
116
|
-
### Check 5: Test Independence
|
|
117
|
-
|
|
118
|
-
```python
|
|
119
|
-
# INVALID - Shared state
|
|
120
|
-
shared_user = None
|
|
121
|
-
|
|
122
|
-
def test_create():
|
|
123
|
-
global shared_user
|
|
124
|
-
shared_user = create_user() # Modifies global
|
|
125
|
-
|
|
126
|
-
def test_read():
|
|
127
|
-
assert shared_user.email # Depends on previous test
|
|
128
|
-
|
|
129
|
-
# VALID - Independent tests
|
|
130
|
-
def test_create(user_factory):
|
|
131
|
-
user = user_factory()
|
|
132
|
-
assert user.id
|
|
133
|
-
|
|
134
|
-
def test_read(user_factory):
|
|
135
|
-
user = user_factory()
|
|
136
|
-
assert user.email
|
|
137
|
-
```
|
|
138
|
-
|
|
139
|
-
**Action**: Each test must be runnable in isolation
|
|
140
|
-
|
|
141
|
-
### Check 6: No Mocking Internals
|
|
142
|
-
|
|
143
|
-
```python
|
|
144
|
-
# INVALID - Testing implementation
|
|
145
|
-
def test_service_calls_model(self, mocker):
|
|
146
|
-
mock_create = mocker.patch('User.objects.create')
|
|
147
|
-
service.create_user(data)
|
|
148
|
-
mock_create.assert_called_once() # Tests HOW, not WHAT
|
|
149
|
-
|
|
150
|
-
# VALID - Testing behavior
|
|
151
|
-
def test_service_creates_user(self):
|
|
152
|
-
user = service.create_user(data)
|
|
153
|
-
assert User.objects.filter(id=user.id).exists() # Tests WHAT
|
|
154
|
-
```
|
|
155
|
-
|
|
156
|
-
## Validation Report
|
|
157
|
-
|
|
158
|
-
When checking tests, output:
|
|
159
|
-
|
|
160
|
-
```
|
|
161
|
-
TEST VALIDITY REPORT
|
|
162
|
-
|
|
163
|
-
File: tests/test_user_service.py
|
|
164
|
-
|
|
165
|
-
test_create_user_success
|
|
166
|
-
- Assertions: 4
|
|
167
|
-
- Tests behavior: Yes
|
|
168
|
-
- Independent: Yes
|
|
169
|
-
|
|
170
|
-
test_create_user_validation
|
|
171
|
-
- Assertions: 1 (minimum 2)
|
|
172
|
-
- Suggestion: Add assertion for error message
|
|
173
|
-
|
|
174
|
-
test_trivial
|
|
175
|
-
- Issue: assert True (trivial)
|
|
176
|
-
- Action: Remove or rewrite
|
|
177
|
-
|
|
178
|
-
Summary:
|
|
179
|
-
- Valid: 8/10
|
|
180
|
-
- Warnings: 1
|
|
181
|
-
- Invalid: 1
|
|
182
|
-
|
|
183
|
-
Recommendation: Fix 2 issues before continuing
|
|
184
|
-
```
|
|
185
|
-
|
|
186
|
-
## Auto-Fix Actions
|
|
187
|
-
|
|
188
|
-
When issues detected:
|
|
189
|
-
|
|
190
|
-
1. **Empty test** -> Generate test body
|
|
191
|
-
2. **Trivial assertion** -> Suggest meaningful assertion
|
|
192
|
-
3. **Low assertion count** -> Add more assertions
|
|
193
|
-
4. **Missing edge cases** -> Generate edge case tests
|
|
194
|
-
5. **Shared state** -> Refactor to fixtures
|
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
# Changelog
|
|
2
|
-
|
|
3
|
-
All notable changes to the smi-failure-log plugin will be documented in this file.
|
|
4
|
-
|
|
5
|
-
## [Unreleased]
|
|
6
|
-
|
|
7
|
-
### Changed
|
|
8
|
-
- Renamed from `smi-failure-log` to `failure-log` as part of ai-kit migration
|
|
9
|
-
- Moved from `plugins/smi-failure-log/` to `packs/failure-log/`
|
|
10
|
-
|
|
11
|
-
## [1.0.0] - 2024-12-20
|
|
12
|
-
|
|
13
|
-
### Added
|
|
14
|
-
- Initial stable release
|
|
15
|
-
- 2 commands: failure-add, failure-list
|
|
16
|
-
- 1 skill: failure-log-manager
|
|
17
|
-
- Automatic context injection of known mistakes
|
|
18
|
-
- Semi-automatic failure detection on Write/Edit
|
|
19
|
-
- Project-specific storage in `.claude/failure-log.local.md`
|
|
20
|
-
- Categories: imports, security, testing, architecture, conventions
|