7a49e2d507
The Telegram digest reported healthy weekly jobs as "never run yet": its maintenance section still globbed for cron-era per-script log filenames (clean-index-*.log etc.) that jobs run through pipeline_runner no longer write. It now reads job_runs, the scheduler's own record, so it reports the last success (age + summary snippet from that run's log), flags a newer failed or lock-skipped attempt on the same line, and distinguishes "never succeeded (last attempt: skipped, lock busy)" from genuinely never scheduled. Also matched the clear-bad-genres snippet grep to the script's current summary wording, and dropped the now-unused newest_log helper. The DB also showed WHY two jobs had never run: on Sunday the 08:30 strip-mb-tags run took 10m19s while holding the shared pipeline lock, so strip-watermark-art (08:35) and scrub-watermark-text (08:40) hit flock-style instant skip and lost their only slot of the week -- the 08:40 job missed by 19 seconds. Scheduled runs now wait up to 30 minutes for the lock (SCHEDULED_LOCK_WAIT_SECONDS) and only then record skipped_lock, so fixed-time blocks queue instead of starving; manual "Run now" keeps the instant skip since a person expects an immediate answer. Tests: scheduled-run queueing, lock-wait timeout, and manual instant-skip. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Tests
Unit and safety tests for the control-plane app and the dedup file-deleter.
They run against throwaway temp dirs and a temp SQLite database (set up in
conftest.py); they never touch a real library, your /config, or the network.
Running them
The runtime image doesn't ship pytest, so install it into a throwaway run of
the built image (which already has the app's own dependencies). Run as root so
pip can write into the image's venv, and keep pytest's cache off so it doesn't
create files in your working tree:
docker run --rm --user root -v "$PWD":/src -w /src -e PYTHONPATH=/src \
--entrypoint bash alembic:latest \
-c "pip install -q pytest && pytest -q -p no:cacheprovider"
Tests set their own temp ALEMBIC_CONFIG_DIR, MUSIC_DATA_DIR, and encryption
key (see conftest.py), so nothing here touches a real library or config.
Or, if you have a matching Python environment locally:
pip install -r requirements-dev.txt
PYTHONPATH=. pytest -q
What's covered
- Dedup safety (
test_dedup_gating.py):dedup-library.shdeletes only the paths confirmed via--only-paths, and keeps the higher-ranked (FLAC) copy. This is the most important test: the script deletes files. - Runner (
test_pipeline_runner.py): lock skip,use_lock=Falsebypass, success/failure/timeout recording, lock release. - Migrations (
test_db.py): schema version, idempotent re-run, FK-safe job-run pruning, stale-run reconciliation. - Credential rendering (
test_credential_service.py): config field substitution (including newline-injection safety), secret vs non-secret classification, cookie-expiry parsing. - Playlists (
test_playlist_service.py): cron round-trips, name validation, config render/delete. - Diagnostics (
test_diagnostics.py): the/healthand/setupchecks.