91 lines
3.3 KiB
Markdown
91 lines
3.3 KiB
Markdown
# ani-web
|
||
|
||
Web front-end for anime streaming: search, browse, and stream anime in
|
||
the browser (hianime.at primary; anidb.app and anikototv.to as
|
||
fallbacks). Multi-user, with per-user watch history and HLS playback
|
||
proxied through the backend. Tuned for phone as much as desktop.
|
||
|
||

|
||
|
||
## Quick start
|
||
|
||
```sh
|
||
uv venv .venv
|
||
uv pip install --python .venv/bin/python -r requirements.txt
|
||
.venv/bin/python -m server.users add <you> # create your account (one-time)
|
||
./run.sh
|
||
```
|
||
|
||
Open it through your HTTPS proxy (or <http://localhost:8321> from the
|
||
host itself — browsers treat localhost as trusted). `run.sh` restarts
|
||
cleanly if the server is already running; logs go to `server.log`.
|
||
|
||
Accounts are CLI-created only (no self-signup):
|
||
|
||
```sh
|
||
.venv/bin/python -m server.users add <name> # add user (prompted password)
|
||
.venv/bin/python -m server.users rm <name> # remove user + their history
|
||
.venv/bin/python -m server.users list # list users
|
||
```
|
||
|
||
Passwords are PBKDF2-SHA256 in `server/data/aniweb.db` (SQLite, 0600);
|
||
sessions are signed 30-day `HttpOnly` `SameSite=Lax` cookies, `Secure`
|
||
via `run.sh`, so remote plain-HTTP can't hold a session — the HTTPS
|
||
proxy is the way in. See [SPEC.md](SPEC.md) for the rest.
|
||
|
||
## Features
|
||
|
||
- **History** — server-side and per-user: a new device picks up your
|
||
exact watch state after login. Entries show poster, progress, and a
|
||
per-entry delete.
|
||
|
||

|
||
|
||
- **Home** — continue-watching hero (poster, position, Resume) plus a
|
||
recently-played grid with progress bars.
|
||
|
||

|
||
|
||
- **Search** — poster-grid results from the active source; your last 8
|
||
searches (per user) in a live-filtering dropdown. Results open the
|
||
detail view (synopsis, season tabs, filler badges).
|
||
|
||

|
||
|
||
- **Player** — resume at the saved position, skip intro (MAL timings),
|
||
dub/sub toggle, playback speed, hide fillers, auto-next with a
|
||
5-second countdown, ✓ on completed episodes. Playback goes through a
|
||
backend HLS proxy (the CDN sends no CORS headers); segments are
|
||
pulled across parallel byte-range lanes so a slow connection doesn't
|
||
stall.
|
||
|
||

|
||
|
||
- **Stats** — `?stats`: watch minutes, episodes, streaks, sub/dub
|
||
split, weekday/per-day heatmaps, top-10 shows, top searches
|
||
(30–365 day windows).
|
||
|
||
## Layout
|
||
|
||
```
|
||
server/ FastAPI app (app.py), source providers (providers/: hianime,
|
||
anidb, anikoto) over shared HTTP + dispatch (upstream.py)
|
||
static/ front-end: index.html, login.html, app.js, hls.min.js (vendored)
|
||
tests/ pytest suite: hermetic default, live browser e2e opt-in
|
||
docs/img/ README screenshots
|
||
run.sh launch/restart the server (sets ANIWEB_SECURE=1)
|
||
SPEC.md design, verified anidb.app data flow, security + runbook notes
|
||
```
|
||
|
||
## Dev
|
||
|
||
- `.venv/bin/pytest tests/ -q` — hermetic suite against a throwaway
|
||
server (never touches real data). Live-upstream browser e2e is
|
||
opt-in: `ANIWEB_LIVE_TESTS=1 .venv/bin/pytest tests/ -q`
|
||
(needs playwright chromium).
|
||
- `ANI_SOURCE=anidb .venv/bin/python -m server.upstream` — live
|
||
self-check of the anidb fetchers (must be the `-m` form; plain
|
||
script execution breaks the providers' relative imports).
|
||
- Everything else (Cloudflare/impersonation, HLS proxy, CDN probe,
|
||
auth hardening, cache-busting): [SPEC.md](SPEC.md).
|