typescript-testing

Applies Vitest test design and quality standards. Provides coverage requirements and mock usage guides. Use when writing unit tests.

$ Installieren

git clone https://github.com/shinpr/ai-coding-project-boilerplate /tmp/ai-coding-project-boilerplate && cp -r /tmp/ai-coding-project-boilerplate/.claude/skills-en/typescript-testing ~/.claude/skills/ai-coding-project-boilerplate

// tip: Run this command in your terminal to install the skill


name: typescript-testing description: Applies Vitest test design and quality standards. Provides coverage requirements and mock usage guides. Use when writing unit tests.

TypeScript Testing Rules

Test Framework

  • Vitest: This project uses Vitest
  • Test imports: import { describe, it, expect, beforeEach, vi } from 'vitest'
  • Mock creation: Use vi.mock()

Basic Testing Policy

Quality Requirements

  • Coverage: Unit test coverage must be 70% or higher
  • Independence: Each test can run independently without depending on other tests
  • Reproducibility: Tests are environment-independent and always return the same results
  • Readability: Test code maintains the same quality as production code

Coverage Requirements

Mandatory: Unit test coverage must be 70% or higher Metrics: Statements, Branches, Functions, Lines

Test Types and Scope

  1. Unit Tests

    • Verify behavior of individual functions or classes
    • Mock all external dependencies
    • Most numerous, implemented with fine granularity
  2. Integration Tests

    • Verify coordination between multiple components
    • Use actual dependencies (DB, API, etc.)
    • Verify major functional flows
  3. Cross-functional Verification in E2E Tests

    • Mandatory verification of impact on existing features when adding new features
    • Cover integration points with "High" and "Medium" impact levels from Design Doc's "Integration Point Map"
    • Verification pattern: Existing feature operation -> Enable new feature -> Verify continuity of existing features
    • Success criteria: No change in response content, processing time within 5 seconds
    • Designed for automatic execution in CI/CD pipelines

Test Implementation Conventions

Directory Structure

src/
└── application/
    └── services/
        ├── __tests__/
        │   ├── service.test.ts      # Unit tests
        │   └── service.int.test.ts  # Integration tests
        └── service.ts

Naming Conventions

  • Test files: {target-file-name}.test.ts
  • Integration test files: {target-file-name}.int.test.ts
  • Test suites: Names describing target features or situations
  • Test cases: Names describing expected behavior

Test Code Quality Rules

Recommended: Keep all tests always active

  • Merit: Guarantees test suite completeness
  • Practice: Fix problematic tests and activate them

Avoid: test.skip() or commenting out

  • Reason: Creates test gaps and incomplete quality checks
  • Solution: Completely delete unnecessary tests

Test Quality Criteria

Boundary and Error Case Coverage

Include boundary values and error cases alongside happy paths.

it('returns 0 for empty array', () => expect(calc([])).toBe(0))
it('throws on negative price', () => expect(() => calc([{price: -1}])).toThrow())

Literal Expected Values

Use literal values for assertions. Do not replicate implementation logic. Valid test: Expected value != Mock return value (implementation transforms/processes data)

expect(calcTax(100)).toBe(10)  // not: 100 * TAX_RATE

Result-Based Verification

Verify results, not invocation order or count.

expect(mock).toHaveBeenCalledWith('a')  // not: toHaveBeenNthCalledWith

Meaningful Assertions

Each test must include at least one verification.

it('creates user', async () => {
  const user = await createUser({name: 'test'})
  expect(user.id).toBeDefined()
})

Appropriate Mock Scope

Mock only direct external I/O dependencies. Use real implementations for indirect dependencies.

vi.mock('./database')  // external I/O only

Property-based Testing (fast-check)

Use fast-check when verifying invariants or properties.

import fc from 'fast-check'

it('reverses twice equals original', () => {
  fc.assert(fc.property(fc.array(fc.integer()), (arr) => {
    return JSON.stringify(arr.reverse().reverse()) === JSON.stringify(arr)
  }))
})

Usage condition: Use when Property annotations are assigned to ACs in Design Doc.

Mock Type Safety Enforcement

Minimal Type Definition Requirements

// Only required parts
type TestRepo = Pick<Repository, 'find' | 'save'>
const mock: TestRepo = { find: vi.fn(), save: vi.fn() }

// Only when absolutely necessary, with clear justification
const sdkMock = {
  call: vi.fn()
} as unknown as ExternalSDK // Complex external SDK type structure

Basic Vitest Example

import { describe, it, expect, vi } from 'vitest'

vi.mock('./userService', () => ({
  getUserById: vi.fn(),
  updateUser: vi.fn()
}))

describe('ComponentName', () => {
  it('should follow AAA pattern', () => {
    const input = 'test'
    const result = someFunction(input)
    expect(result).toBe('expected')
  })
})

Repository

shinpr
shinpr
Author
shinpr/ai-coding-project-boilerplate/.claude/skills-en/typescript-testing
147
Stars
15
Forks
Updated5d ago
Added6d ago