ios-testing-strategy
/ios-testing-strategy
Prowadzi krok po kroku przez dodawanie testów do istniejącego kodu Swift i iOS, zarówno nieprzetestowanego kodu legacy, jak i nowej pracy w TDD.
- Autor
- apexbymanish ↗
- Repozytorium
- claude-ai-agents-ios ↗
- Licencja
- MIT
- Ostatnia zmiana repozytorium
- 01.09.2026
Ocena i bezpieczeństwo
- Pliki w paczce
- 1
- Skrypty
- 0
- Komentarze HTML
- 0
- Adresy URL w SKILL.md
- 0
Brak sygnałów. Repozytorium zmienione 01.09.2026, bez odwołań do wycofanych modeli i API.
MIT, otwarta: można używać i zmieniać, z zachowaniem informacji o autorze.
Co robi i kiedy
Prowadzi krok po kroku przez dodawanie testów do istniejącego kodu Swift i iOS, zarówno nieprzetestowanego kodu legacy, jak i nowej pracy w TDD.
Wyzwalacze z opisu
Oryginalny opis (EN)
Step-by-step procedure for adding tests to existing Swift/iOS code, whether untested legacy code or new TDD work. Use when asked to "add test coverage", "write tests for this", "make this testable", or when starting TDD on new Swift code.
Jak działa
- 1. Identify the seams
- 2. Write a test double, not a framework
- 3. Write the test against behavior, not implementation
- 4. Verify red before green
- 5. Prioritize by risk, not by percentage
- 6. What NOT to test
Podgląd SKILL.md
---
name: ios-testing-strategy
description: Step-by-step procedure for adding tests to existing Swift/iOS code, whether untested legacy code or new TDD work. Use when asked to "add test coverage", "write tests for this", "make this testable", or when starting TDD on new Swift code.
---
# iOS Testing Strategy
A concrete procedure, not just principles. Follow these steps in order.
## 1. Identify the seams
Before writing a single test, find (or create) the seams that let you
substitute real dependencies with test doubles:
- Networking, persistence (Core Data/SwiftData contexts), date/time,
and any singleton (`.shared`) are the usual suspects.
- If the code under test reaches a singleton directly, introduce a
protocol and inject it — don't test through the singleton.
```swift
protocol UserRepository {
func fetchUser(id: String) async throws -> User
}
final class LiveUserRepository: UserRepository { /* real network call */ }
final class ProfileViewModel {
private let repository: UserRepository
init(repository: UserRepository) { self.repository = repository }
}
```
If the class under test currently hardcodes `LiveUserRepository()`
internally, that's the first fix: add the initializer parameter above
(default it to the live implementation so call sites don't all need to
change at once).
## 2. Write a test double, not a framework
A hand-written struct/class conforming to the protocol is almost always
enough. Reach for a mocking library only if the project already has one.
```swift
final class StubUserRepository: UserRepository {
var result: Result<User, Error> = .success(.mock)
func fetchUser(id: String) async throws -> User { try result.get() }
}
```
## 3. Write the test against behavior, not implementation
Assert on outputs and observable state changes, not on which private
methods got called.
```swift
@Test func profileLoadShowsFetchedUserName() async throws {
let repository = StubUserRepository()
repository.result = .success(User(id: "1", name: "Ada"))
let viewModel = ProfileViewModel(repository: repository)
await viewModel.load(id: "1")
#expect(viewModel.displayName == "Ada")
}
```
Use Swift Testing (`@Test`, `#expect`) for new code in projects on Swift
5.10+ / Xcode 16+. Use XCTest for projects that haven't adopted Swift
Testing yet — check the existing test target before picking one; don't
mix frameworks in the same target without a reason.
## 4. Verify red before green
Before implementing the fix/feature, run the test and confirm it fails
for the *expected* reason (not a compile error, not a setup bug):
Run: `xcodebuild test -scheme <Scheme> -destination 'platform=iOS Simulator,name=iPhone 16' -only-testing:<Target>/<TestClass>/<testName>`
Then implement the minimal code to pass, and re-run the same command to
confirm green.
## 5. Prioritize by risk, not by percentage
Coverage percentage is a lagging indicator. Prioritize, in order:
1. Business logic with branching (pricing, eligibility, state machines).
2. Anything that has broken in production before.
3. Public API of a module other code depends on.
4. Pure UI layout code is usually not worth unit testing — that's what
`ios-ui-test-engineer` and snapshot tests are for.
## 6. What NOT to test
- Don't test that a SwiftUI `View`'s `body` produces particular view
types — that's an implementation detail and breaks on every refactor.
- Don't test third-party framework behavior (e.g. that `URLSession`
actually makes a network call) — test that *your code* calls it
correctly, via the seam from step 1.
- Don't write a test for a private method by making it internal/public
just to reach it — test through the public behavior that uses it.
Wersje
W bazie nie ma innych skilli o nazwie ios-testing-strategy.
Migawka bazy z 28.10.2026 · wersja paczki 10d57c1cbf1c (skrót SHA-256 całej paczki)
Pobrania w ostatnich 30 dniach: 0 · ranking
Zgłoś problem z tym skillem: szkodliwa treść, błędny opis albo prośba autora o usunięcie.
Podobne skille
- 100test-generator
Generuje szablony testów jednostkowych, integracyjnych i UI w Swift Testing oraz XCTest dla aplikacji iOS i macOS. - 90testing
Wspiera TDD i testowanie aplikacji iOS i macOS: testy charakteryzujące, kontrakty testowe, snapshoty, infrastrukturę testów oraz deterministyczne bramki jakości z coverage ratchet i mutation testing. - 100tdd-testing
Prowadzi TDD na platformie DEVS dla kodu w lib i stores, z pisaniem testów i pokryciem. - 100tdd
Buduje zachowanie test-first przy każdym kroku, przy dodawaniu testów do istniejącego kodu i oceny, czy test zasługuje na miejsce. - 100write-tests
Pisze testy jednostkowe i integracyjne dla istniejącego kodu, także w podejściu TDD, gdy brakuje testów. - 90Swift Unit Testing Skill
Projektuje i pisze testy jednostkowe w Swift Testing, z XCTest do testów UI i starych zestawów, obejmując mocki, asynchroniczność i TDD.