- Add --continue and --max-filesize to yt-dlp for download resilience
- Route thumbnail downloads through HTTP_PROXY
- Show per-video progress (i/N) with cancel for playlist downloads
- Run playlist asynchronously so cancel callbacks can be processed
- Guard handlePlaylistConfirm against concurrent active jobs
- Close Done channel in playlist entry lifecycle
- Add stepState TTL (30 min) to prevent stale states
- Wrap webhook server for graceful shutdown on SIGTERM
- Refactor formatBytes to loop-based implementation
- Show first line of stderr in user-facing error messages
- Fix format pointer reuse in playlist loop
- Add CreatedAt field to stepState for TTL tracking
- Add MaxFileSize and ProgressPrefix fields to DownloadJob
- Add in-memory LRU cache (200 entries, 30 min TTL) to yt-dlp Client for
GetMediaInfo and GetPlaylistInfo results, avoiding redundant yt-dlp calls
for the same URL within a session
- Add YouTube (/search) and YouTube Music (/music) search with paginated
results (5 per page), user selects a result to start the download flow
- Add SearchState type, new search.go handler, search results keyboard with
< > navigation and New Search button
- Add Search button to main menu keyboard
- Update help text with new commands