README: storage is SQLite (aniweb.db), not JSON files; CDN serves a
single quality (no ABR) — replaced the wrong 1080/720/360 claim;
document the 16-lane parallel fetch, intro-skip, episode names,
buffering UI, /api/cdn + background probe, the ?v= cache-busting rule,
and the client self-report diagnostics.
SPEC: same single-rendition correction (2 places).
PLAN: marked complete (all items shipped; deferred list was stale).
- middleware re-verifies the username against users.json per request:
deleted accounts' signed cookies are rejected immediately
- set_cookie/delete_cookie honor the Secure flag; run.sh sets
ANIWEB_SECURE=1 so sessions only work through the HTTPS proxy
- server/users.py replaces credentials.py: users.json (0600), PBKDF2,
one-time migration of the legacy single password to user admin
(history.json -> history/admin.json)
- accounts are CLI-managed only: python -m server.users add|rm|list
(no self-signup on an internet-exposed app); /signup route removed,
login page back to username + password
- per-user 30-day signed session cookie (payload carries the
username), per-user lockout, GET /api/me, POST /account/delete
- per-user watch history: server/data/history/<user>.json; ANIWEB_DATA
env override for the data dir
- header chip: logged-in user, logout, delete account
- tests/: throwaway-server suite (port 8399, temp data dir) — 9 HTTP
tests + 2 Playwright browser tests (login UI, real video playback
behind auth); runs via python tests/run.py