diff options
Diffstat (limited to 'CLAUDE.md')
| -rw-r--r-- | CLAUDE.md | 29 |
1 files changed, 25 insertions, 4 deletions
@@ -41,8 +41,14 @@ in that literal order: 6. Run the full quality gate before committing. **If production code was written before or without a preceding failing test**, discard the diff and -redo it test-first. Do not backfill tests onto existing code — a test written against working code -confirms what the code does, not what it should do. +redo it test-first. Do not backfill tests onto existing code *as a substitute for that* — a test +written against working code confirms what the code does, not what it should do, so it cannot stand +in for a red step. + +The one case it is right: **pinning behaviour before moving it.** A characterisation test written +against the old location, confirmed green, then re-run after the move is what makes a refactor +provably behaviour-preserving — the "keeping it green" in step 5 needs a green to keep. Write it in +that order and say so; written afterwards it only proves the new code agrees with itself. **Scoping exception:** pure resource/config/manifest changes with no unit-testable behaviour don't get a red step; the static-analysis gate covers those. @@ -115,7 +121,9 @@ claims three separate times across these repos. **Phase 1 is complete.** Subscribe (share sheet, pasted URL, OPML import), refresh, download, queue, play, variable speed, sleep timer, retention, unsubscribe, Android Auto with a browsable -library and voice search. 207 unit tests plus instrumented tests covering the media browse tree. +library and voice search, with instrumented tests covering the media browse tree. (Counts are +deliberately not recorded here -- they went stale at 207 while the suite reached nine hundred. +`gradle-test` and `go-verify` report the current ones.) **Since Phase 2**, in response to a round of Peter's feedback: yt-dlp sources play (they are fetched first), playback errors are surfaced instead of being swallowed, anything queued is @@ -549,7 +557,11 @@ by default and correct; it is simply waiting for a publisher who marks breaks. playing episode's screen, and steps aside on that screen. Speed is a chip (`SpeedChoices.OFFERED` is 1.0/1.1/1.25/2.0); a show stored at 1.5 or 1.75 keeps playing at it, the chip just names it. Secondary actions and chapters are in the `⋮` menu, whose contents `EpisodeMenu` decides, and - the description shows ~two lines (`DescriptionPreview`) with the rest on tap. + the description shows about ten lines (`DescriptionPreview.PREVIEW_LINES`, with a character + budget beside it) and the rest on tap. It was two until 2026-11-01: that limit existed to + stop long notes pushing the transport off-screen, and the merge put the notes *below* the + transport, so the reason had already gone. What it actually did was cut at 140 characters + and leave the bottom three-fifths of the screen empty. Do not reinstate it. - **Framework adapters are excluded from coverage, as of 2026-09-26.** The gate had been overridden eight times, every one a class whose whole body is a call into ExoPlayer, Media3, @@ -615,6 +627,15 @@ by default and correct; it is simply waiting for a publisher who marks breaks. error colour through the dimming, because a feed failing to refresh looks exactly like a feed with nothing new. +- **Anything the app says out loud lives in a named file of its own, and is tested.** Not in the + composable that renders it: `SkipSummary`, `RuleSummary`, `FoundBySummary`, `WaitingForServerText`, + `RejectedTokenText`, `DescriptionPreview`, `SpeedChoices`, `TimeText` (`formatClock` for a + position, `formatDuration` for a length) and `EpisodeLabels` (`progressLabel`, the one line under + every episode title). Screens are excluded from coverage and verified on hardware, so wording left + inside one is wording nothing checks -- and a shared formatter inside a view means editing the + now-playing bar to change the transcript gutter, which is where `formatClock` actually was until + 2026-11-02. A new user-visible string either joins one of these or brings its own file. + - **What the skip detection has worked out is visible**, per show in the settings sheet and per episode on its detail screen. `SkipSummary` owns the wording and is tested, because the distinction that matters -- confirmed-and-acting versus still-gathering -- is the whole point, |
