Current State
- 377 tests, 56.1% overall coverage
- 146 functions with 0% coverage
- Target: 70% coverage
Test file structure
Follow existing patterns:
- Tests go in `*_test.go` alongside source
- Use `testify/assert` for assertions
- Table-driven tests with subtests
- Mock PD client from `pkg/pd/mock.go`
- TDD: write tests first, verify fail, implement
HIGH PRIORITY — Core untested functions
pkg/pd/pd.go
| Function |
Line |
What to test |
| `NewConfig()` |
63 |
Init with mock client; error on bad team ID; error on bad policy |
| `AcknowledgeIncident()` |
129 |
Direct test (currently only tested via TUI commands) |
| `ReassignIncidents()` |
347 |
Success case; empty incidents; nil user |
| `ReEscalateIncidents()` |
372 |
Success case; nil policy; level=0 |
pkg/pd/ratelimit.go (12 untested wrappers)
| Method |
Tested? |
| GetIncidentWithContext |
Yes |
| ListIncidentAlertsWithContext |
Yes |
| ListIncidentsWithContext |
Yes |
| CreateIncidentNoteWithContext |
No |
| GetCurrentUserWithContext |
No |
| GetEscalationPolicyWithContext |
No |
| GetTeamWithContext |
No |
| ListMembersWithContext |
No |
| GetUserWithContext |
No |
| ListIncidentNotesWithContext |
No |
| ListOnCallsWithContext |
No |
| ManageIncidentsWithContext |
No |
Test pattern: verify each wrapper calls `limiter.Wait()` and delegates to inner client.
pkg/tui/commands.go
| Function |
Line |
What to test |
| `login()` |
500 |
Command construction; env vars; toolbox wrapping |
| `UserIsOnCall()` |
286 |
Critical for auto-ack; test with mock on-call data |
| `renderIncident()` |
213 |
Template rendering produces valid markdown |
| `runScheduledJobs()` |
946 |
Job frequency; lastRun tracking |
cmd/root.go
| Function |
Line |
What to test |
| `configureLogging()` |
244 |
Journal vs file vs stderr selection |
| `initConfig()` |
186 |
Viper config loading |
MEDIUM PRIORITY — TUI functions
| Function |
File |
What to test |
| `InitialModel()` |
model.go:107 |
Model creation with various configs |
| `switchInputFocusMode()` |
msgHandlers.go:492 |
Enter/Escape/key routing |
| `switchErrorFocusMode()` |
msgHandlers.go:618 |
Escape clears error |
| `removeCommentsFromBytes()` |
commands.go:819 |
Fixed bug — verify fix holds |
| `doIfIncidentSelected()` |
commands.go:933 |
Selected vs unselected |
LOW PRIORITY — Edge cases
- Empty API responses (nil incidents, nil alerts)
- Nil incident fields (nil Service, nil EscalationPolicy)
- Malformed config file (wrong types for keys)
- Rate limit exhaustion (429 after max retries)
- Network timeout (context deadline exceeded)
Files to create/modify
- `pkg/pd/pd_test.go` — NewConfig, Reassign, ReEscalate tests
- `pkg/pd/ratelimit_test.go` — 12 wrapper tests
- `pkg/tui/commands_test.go` — login, UserIsOnCall tests
- `cmd/root_test.go` — configureLogging tests
Current State
Test file structure
Follow existing patterns:
HIGH PRIORITY — Core untested functions
pkg/pd/pd.go
pkg/pd/ratelimit.go (12 untested wrappers)
Test pattern: verify each wrapper calls `limiter.Wait()` and delegates to inner client.
pkg/tui/commands.go
cmd/root.go
MEDIUM PRIORITY — TUI functions
LOW PRIORITY — Edge cases
Files to create/modify