Cross-language testing strategies and patterns. Triggers on: test pyramid, unit test, integration test, e2e test, TDD, BDD, test coverage, mocking strategy, test doubles, test isolation.
This skill is limited to using the following tools:
references/ci-testing.mdreferences/mocking-strategies.mdreferences/tdd-workflow.mdreferences/test-data-patterns.mdscripts/coverage-check.shUniversal testing strategies and patterns applicable across languages.
/\
/ \ E2E Tests (few, slow, expensive)
/ \ - Full system tests
/------\ - Real browser/API calls
/ \
/ Integ \ Integration Tests (some)
/ Tests \ - Service boundaries
/--------------\ - Database, APIs
/ \
/ Unit Tests \ Unit Tests (many, fast, cheap)
------------------ - Single function/class
- Mocked dependencies
Scope: Single function/method/class
Speed: Milliseconds
Dependencies: All mocked
When: Every code change
Coverage: 80%+ of codebase
Scope: Multiple components together
Speed: Seconds
Dependencies: Real databases, mocked external APIs
When: PR/merge, critical paths
Coverage: Key integration points
Scope: Full user journey
Speed: Minutes
Dependencies: Real system (or staging)
When: Pre-deploy, nightly
Coverage: Critical user flows only
test_<unit>_<scenario>_<expected>
Examples:
- test_calculate_total_with_discount_returns_reduced_price
- test_user_login_with_invalid_password_returns_401
- test_order_submit_when_out_of_stock_raises_error
def test_calculate_discount():
# Arrange - Set up test data and dependencies
cart = Cart()
cart.add_item(Item(price=100))
discount = Discount(percent=10)
# Act - Execute the code under test
total = cart.calculate_total(discount)
# Assert - Verify the results
assert total == 90
| Type | Purpose | Example |
|---|---|---|
| Stub | Returns canned data | stub.get_user.returns(fake_user) |
| Mock | Verifies interactions | mock.send_email.assert_called_once() |
| Spy | Records calls, uses real impl | spy.on(service, 'save') |
| Fake | Working simplified impl | FakeDatabase() instead of real DB |
| Dummy | Placeholder, never used | null object for required param |
Option 1: Transaction rollback (fast)
- Start transaction before test
- Rollback after test
Option 2: Truncate tables (medium)
- Clear all data between tests
Option 3: Separate database (slow)
- Each test gets fresh database
Option 1: Mock at boundary
- Replace HTTP client with mock
Option 2: Fake server
- WireMock, MSW, VCR cassettes
Option 3: Contract testing
- Pact, consumer-driven contracts
./references/tdd-workflow.md - Test-Driven Development cycle./references/mocking-strategies.md - When and how to mock./references/test-data-patterns.md - Fixtures, factories, builders./references/ci-testing.md - Testing in CI/CD pipelines./scripts/coverage-check.sh - Run coverage and fail if below threshold