FA-11286 / Media playlist lifecycle / Open access
Play next queue: Consumes play-next requests in reverse insertion order · case 01
Consumes play-next requests in reverse insertion order and produces an incorrect media-control or presentation result.
ROOT CAUSE
Consumes play-next requests in reverse insertion order. The fixture suite isolates this decision from network delivery and codec details.
VERIFIED REPAIR
Consume the first enabled play-next queue occurrence before advancing the playlist. Queue plays do not move the playlist cursor; disabled queued occurrences are discarded. Return [selected ID or None,remaining queue,new playlist cursor]. Queue duplicates are independent requests.
Unsuccessful approach: The alternative still fails because it returns a queued occurrence without removing it.
Case contract
Consume the first enabled play-next queue occurrence before advancing the playlist. Queue plays do not move the playlist cursor; disabled queued occurrences are discarded. Return [selected ID or None,remaining queue,new playlist cursor]. Queue duplicates are independent requests.
Why this case matters
A deterministic in-memory media application model with explicit playlist, timeline or synchronization semantics. Does not implement codecs, transport protocols, rendering hardware or concurrent playback.
1 / The failure
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(playlist, cursor, queue, disabled):
pending=list(queue)
while pending:
candidate=pending.pop()
if candidate in disabled: continue
return [candidate,pending,cursor]
start=playlist.index(cursor) if cursor in playlist else -1
for candidate in playlist[start+1:]:
if candidate not in disabled:
return [candidate,pending,candidate]
return [None,pending,cursor]
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
check('queue has priority', solve(['a', 'b'], 'a', ['x', 'y'], []), ['x', ['y'], 'a'])
check('same track queued twice', solve(['a', 'b'], 'a', ['x', 'x', 'y'], []), ['x', ['x', 'y'], 'a'])
check('disabled queue discarded', solve(['a', 'b'], 'a', ['x', 'y'], ['x']), ['y', [], 'a'])
check('fallback advances cursor', solve(['a', 'b'], 'a', [], []), ['b', [], 'b'])
check('all queued disabled falls back', solve(['a', 'b'], 'a', ['x'], ['x']), ['b', [], 'b'])
check('end has no track', solve(['a'], 'a', [], []), [None, [], 'a'])
check('queue works without playlist', solve([], None, ['x'], []), ['x', [], None])
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| queue has priority | ['y', ['x'], 'a'] | ['x', ['y'], 'a'] | Failed |
| same track queued twice | ['y', ['x', 'x'], 'a'] | ['x', ['x', 'y'], 'a'] | Failed |
| disabled queue discarded | ['y', ['x'], 'a'] | ['y', [], 'a'] | Failed |
| fallback advances cursor | ['b', [], 'b'] | ['b', [], 'b'] | Passed |
| all queued disabled falls back | ['b', [], 'b'] | ['b', [], 'b'] | Passed |
| end has no track | [None, [], 'a'] | [None, [], 'a'] | Passed |
| queue works without playlist | ['x', [], None] | ['x', [], None] | Passed |
SHA-256 / f1df0f68e351204cdf5e2b388b6891ca706aa5127653f84e1486c446be72805f
2 / The unsuccessful fix
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(playlist, cursor, queue, disabled):
pending=list(queue)
while pending:
candidate=pending.pop(0)
if candidate in disabled: continue
return [candidate,[candidate]+pending,cursor]
start=playlist.index(cursor) if cursor in playlist else -1
for candidate in playlist[start+1:]:
if candidate not in disabled:
return [candidate,pending,candidate]
return [None,pending,cursor]
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
check('queue has priority', solve(['a', 'b'], 'a', ['x', 'y'], []), ['x', ['y'], 'a'])
check('same track queued twice', solve(['a', 'b'], 'a', ['x', 'x', 'y'], []), ['x', ['x', 'y'], 'a'])
check('disabled queue discarded', solve(['a', 'b'], 'a', ['x', 'y'], ['x']), ['y', [], 'a'])
check('fallback advances cursor', solve(['a', 'b'], 'a', [], []), ['b', [], 'b'])
check('all queued disabled falls back', solve(['a', 'b'], 'a', ['x'], ['x']), ['b', [], 'b'])
check('end has no track', solve(['a'], 'a', [], []), [None, [], 'a'])
check('queue works without playlist', solve([], None, ['x'], []), ['x', [], None])
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| queue has priority | ['x', ['x', 'y'], 'a'] | ['x', ['y'], 'a'] | Failed |
| same track queued twice | ['x', ['x', 'x', 'y'], 'a'] | ['x', ['x', 'y'], 'a'] | Failed |
| disabled queue discarded | ['y', ['y'], 'a'] | ['y', [], 'a'] | Failed |
| fallback advances cursor | ['b', [], 'b'] | ['b', [], 'b'] | Passed |
| all queued disabled falls back | ['b', [], 'b'] | ['b', [], 'b'] | Passed |
| end has no track | [None, [], 'a'] | [None, [], 'a'] | Passed |
| queue works without playlist | ['x', ['x'], None] | ['x', [], None] | Failed |
SHA-256 / f8631ad475a271b975717c3ba220a6aa507566561c5452c07a787cec6f7d83e2
3 / The verified repair
Exit 0"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(playlist, cursor, queue, disabled):
pending=list(queue)
while pending:
candidate=pending.pop(0)
if candidate in disabled: continue
return [candidate,pending,cursor]
start=playlist.index(cursor) if cursor in playlist else -1
for candidate in playlist[start+1:]:
if candidate not in disabled:
return [candidate,pending,candidate]
return [None,pending,cursor]
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
check('queue has priority', solve(['a', 'b'], 'a', ['x', 'y'], []), ['x', ['y'], 'a'])
check('same track queued twice', solve(['a', 'b'], 'a', ['x', 'x', 'y'], []), ['x', ['x', 'y'], 'a'])
check('disabled queue discarded', solve(['a', 'b'], 'a', ['x', 'y'], ['x']), ['y', [], 'a'])
check('fallback advances cursor', solve(['a', 'b'], 'a', [], []), ['b', [], 'b'])
check('all queued disabled falls back', solve(['a', 'b'], 'a', ['x'], ['x']), ['b', [], 'b'])
check('end has no track', solve(['a'], 'a', [], []), [None, [], 'a'])
check('queue works without playlist', solve([], None, ['x'], []), ['x', [], None])
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| queue has priority | ['x', ['y'], 'a'] | ['x', ['y'], 'a'] | Passed |
| same track queued twice | ['x', ['x', 'y'], 'a'] | ['x', ['x', 'y'], 'a'] | Passed |
| disabled queue discarded | ['y', [], 'a'] | ['y', [], 'a'] | Passed |
| fallback advances cursor | ['b', [], 'b'] | ['b', [], 'b'] | Passed |
| all queued disabled falls back | ['b', [], 'b'] | ['b', [], 'b'] | Passed |
| end has no track | [None, [], 'a'] | [None, [], 'a'] | Passed |
| queue works without playlist | ['x', [], None] | ['x', [], None] | Passed |
SHA-256 / 56916a6d2ba54f92ccbcfd620cd4015ac7afdeff5ebaea521ce8f88a3c45aaf1
Verification & scope
This reproducer isolates one failure mechanism. Results cover the supplied fixtures. Variants within a family share a test contract and should remain grouped when constructing evaluation splits. Related mechanisms with a shared evaluation_group must also remain together; these controlled models are not independent production incidents.
Observations recorded using Python 3.12.14 at 2026-09-29T14:38:46.637824+00:00.
Case digest / 705609813951638b0ecac9a88863625bfd8da472707061b68e7ff984d3eaf790