testing
1
总安装量
1
周安装量
#52722
全站排名
安装命令
npx skills add https://github.com/bumgeunsong/daily-writing-friends --skill testing
Agent 安装分布
openclaw
1
claude-code
1
Skill 文档
Output-Based Testing for Pure Functions
Test pure functions with input/output assertions. Never unit test hooks, components, or side effects.
When to Use
- User asks to “write tests” or “add coverage”
- New business logic is being implemented
- TDD requested for new feature
- Coverage report shows untested utils/
Core Pattern
TESTABLE (Functional Core) â NOT UNIT TESTED (Imperative Shell)
ââââââââââââââââââââââââââââââââââââââââââââââââââââââââââââââââââââ
Pure functions in utils/ â React hooks (useX)
Calculations, transformations â Components (*.tsx)
Validators, formatters â API calls, Firebase operations
State machines, reducers â localStorage, Date.now(), Math.random()
Implementation
What to Test
// â
TESTABLE: Pure function
export const calculateStreak = (dates: Date[], today: Date): number => {
// Pure transformation: dates â number
};
// Test with simple input/output
describe('calculateStreak', () => {
it('returns 0 for empty dates', () => {
expect(calculateStreak([], new Date('2024-01-15'))).toBe(0);
});
it('returns consecutive days count', () => {
const dates = [new Date('2024-01-14'), new Date('2024-01-15')];
expect(calculateStreak(dates, new Date('2024-01-15'))).toBe(2);
});
});
What NOT to Test
// â DON'T TEST: Hook with side effects
export function useStreak(userId: string) {
const { data } = useQuery(['streak', userId], () => fetchStreak(userId));
return calculateStreak(data?.dates ?? [], new Date());
}
// â DON'T TEST: Component
const StreakBadge = ({ userId }) => {
const streak = useStreak(userId);
return <Badge>{streak} days</Badge>;
};
TDD Workflow
1. Write failing test for pure function
2. Implement pure function to pass test
3. Create thin hook/component that calls pure function
4. Skip unit tests for hook/component (E2E covers integration)
Test File Location
src/
âââ feature/
â âââ utils/
â â âââ calculations.ts # Pure functions
â â âââ calculations.test.ts # Tests here
â âââ hooks/
â â âââ useFeature.ts # NO unit tests
â âââ components/
â âââ Feature.tsx # NO unit tests
Common Mistakes
| Mistake | Symptom | Fix |
|---|---|---|
| Testing hooks | renderHook(), QueryClientProvider in test |
Extract logic to pure function |
| Mocking time | vi.useFakeTimers(), mockDate |
Inject timestamp as parameter |
| Mocking internals | vi.mock('../api/firebase') |
Test pure logic, not integration |
| Testing UI | render(), screen.getByText() |
Only E2E tests for UI |
Red Flags
Stop and refactor if your test file has:
vi.mock()for anything except external APIsrenderHook()orrender()from testing-libraryQueryClient,Provider, orwrappersetup- More than 5 lines of test setup
Naming Convention
describe('FeatureName', () => {
describe('when [condition]', () => {
it('[expected outcome]', () => {
// Arrange - Act - Assert (max 3-5 lines)
});
});
});