fix: a first watch state and a first Watch later survive two requests at once

The first checkpoint of an item and the final flush beside it both read no
state and both inserted; the loser failed on uq_plex_user_item. Two first saves
each made a Watch later list. Both are created by an ON CONFLICT DO NOTHING
insert and then read; a partial unique index holds one Watch later per user, and
the migration folds an existing second list into the first. Plex keeps one
per-item state map (rollup.item_state_map).
This commit is contained in:
2026-10-20 00:45:22 +02:00
parent b376373af5
commit 3a5212cd8a
11 changed files with 215 additions and 40 deletions
+2 -2
View File
@@ -100,7 +100,7 @@ def show_detail(
raise not_found("show")
seasons = queries.seasons(db, sh)
eps = queries.episodes(db, sh)
states = queries.states(db, user, [e.id for e in eps])
states = rollup.item_state_map(db, user, [e.id for e in eps])
by_season: dict[int | None, list] = {}
all_cards: list[dict] = [] # every episode, in season/episode order → show-level rollup
for e in eps:
@@ -247,7 +247,7 @@ def _collection_strips(db: Session, it: "PlexItem", user_id: int, lang: str) ->
for col in ordered:
rk = col.rating_key
members = queries.library_movies_in(db, it.library_id, rk, lang, limit=60)
states = queries.states(db, user_id, [m.id for m in members])
states = rollup.item_state_map(db, user_id, [m.id for m in members])
out.append(
{
"id": rk,
+2 -2
View File
@@ -9,7 +9,7 @@ from sqlalchemy.orm import Session
from app.auth import current_user
from app.db import get_db
from app.models import User
from app.plex import queries, service
from app.plex import queries, rollup, service
from app.plex.cards import display_title, leaf_card, norm_lang
from app.refusal import refused
from app.routes._common import not_found
@@ -99,7 +99,7 @@ def playlist_detail(
lang = norm_lang(lang)
pl = _own_playlist(db, user, pid)
items = queries.playlist_items(db, pl.id)
states = queries.states(db, user, [it.id for it in items])
states = rollup.item_state_map(db, user, [it.id for it in items])
shows = queries.shows_by_ids(db, {it.show_id for it in items if it.show_id})
cards = [
leaf_card(