Phase 3 DoD reached end to end: `artemis run spotify_play query="Rolling
Stones Honky Tonk"` played the right song in 13 steps / 35.3s, with playback
paused first so the pass proves the row tap started it.
Two things stopped it before that, both found on the real phone:
- The playback check asserted on an on-screen "Pause" label that Spotify
never shows: its transport button keeps the label "Play" while music is
playing. The recipe now ends with a `playing` step that reads the app's
media session (state PLAYING) and confirms the track title contains the
query words. A failure reports the state and the track it found.
- tap_row pressed the wrong row. Once a track is loaded its row carries a
`Paused` state indicator, and counting that content description as row text
dropped the top hit below an identical duplicate further down, so the tap
went to y=1443 instead of y=878. Rows are now scored on their title and
subtitle only (state lives in content descriptions), and scores within
rowScoreTolerance are treated as equal so the higher row wins, because
Spotify already ranks by relevance.
internal/ui/rows_test.go reproduces that results screen, including the state
indicator and the duplicate row.
docs/phase-3-spotify-recipe.md records the successful run, the independent
media-session and audio-output reads, and the failure that preceded it.