PR Gates / Docs update reminder (pull_request) Successful in 18s
PR Gates / CI image pin matches docker/ci (pull_request) Successful in 18s
review-verdict/h10 Awaiting review verdict for edf8be4
PR Gates / decisions lifecycle (pull_request) Successful in 20s
Review verdict / Set review-verdict status (pull_request) Successful in 3s
PR Gates / Script tests (pytest) (pull_request) Failing after 38s
Build ErsatzTV Image / Build & test (.NET) (pull_request) Successful in 8m13s
Build ErsatzTV Image / API docs in sync (OpenAPI + endpoint index) (pull_request) Successful in 9s
Build ErsatzTV Image / Formatting (changed .cs conform to .editorconfig) (pull_request) Successful in 24s
Build ErsatzTV Image / EF migration integrity (SQLite + MySql) (pull_request) Successful in 16m40s
Build ErsatzTV Image / Functional E2E (curl + UI contracts) (pull_request) Successful in 17m20s
Build ErsatzTV Image / Build & push image (amd64) (pull_request) Has been skipped
Re-review of the previous fix commit found that two tests added to close round-1 findings could not fail. Both verified before fixing: 1. Missing_But_Named_Custom_Playout_Item_Watermark_Should_Not_Fall_Through gave the channel-level fallback the SAME missing custom path as the playout-item watermark, so a wrongly-widened guard would have fallen through to a fallback that also resolved to None -- the assertion held either way. The fallback is now an independently resolvable ChannelLogo whose cached file exists, so a fall-through returns it and fails the test. Added the matching positive control (blank -> falls through and DOES return that logo), so the pair shows the guard distinguishes blank from unresolvable instead of both landing on None. 2. Deco_With_One_Valid_And_One_Missing_Watermark... asserted a filtered list length while the routing claim the decision record cited it for lives in FFmpegLibraryProcessService.CanUseFFmpegNativeWatermark, which the test never called. It now calls the real predicate. Also, three wrong claims of my own: 3. The Resource arm comment said "nothing in the app writes a Resource watermark to the database". False -- CreateWatermarkHandler and UpdateWatermarkHandler persist whatever ImageSource the request names, so a Resource watermark IS creatable through the API, always with Image = null. That is precisely why the new null guard is load-bearing, so the comment was arguing for its own removal. 4. "One resolver and no per-caller policy" contradicted the surviving playout-item blank-Custom fall-through documented a few lines later. Reworded in both the record and the XML docs: one resolver, and exactly one piece of per-caller policy which lives in the CALLER. 5. The record's "12 of 18 new tests fail pre-fix" was stale. Re-measured against the final fixture: 19 of 29. The other 10 pass both ways by design because they pin preserved behavior, which the record now says explicitly rather than leaving the gap to be read as weakness. Removed the vacuous generated-URL test rather than keeping it with an honest comment -- an empty list trivially contains no URL, so it implied coverage it never had. Its assertion is folded into the sibling test that has a real arrangement. Gates: 2772 tests green across 5 projects, dotnet format exit 0, no BOMs, decisions-validate OK, live-E2E re-run against this binary (0 changed pixels, nameplate absent, warning emitted). refs #510