feat: Complete watchlist & auto-download system with UI

Implement comprehensive watchlist system with automatic episode detection
and downloading. Features include per-user watchlists, scheduler-based
periodic checks, and a modern web UI.

**Backend Components:**
- WatchlistManager: JSON-based storage with multi-tenant support
- EpisodeChecker: Detects and downloads new episodes automatically
- AutoDownloadScheduler: APScheduler-based periodic task execution
- Complete REST API for CRUD operations and scheduler control

**Frontend Components:**
- Modern watchlist page with dark theme and animations
- Real-time status updates and progress tracking
- Scheduler controls with next-run display
- Add anime directly from search results

**Models & Configuration:**
- WatchlistItem with status, quality, and auto-download settings
- WatchlistSettings for global configuration
- Per-user statistics and provider tracking

**API Endpoints:**
- GET/POST /api/watchlist - List and add items
- PUT/DELETE /api/watchlist/{id} - Update and delete
- POST /api/watchlist/{id}/check - Manual check trigger
- POST /api/watchlist/check-all - Check all due items
- GET/PUT /api/watchlist/settings - Global settings
- GET /api/watchlist/stats - Statistics
- GET/POST /api/watchlist/scheduler/* - Scheduler control

**Configuration Files:**
- config/watchlist.json - User watchlist data
- config/watchlist_settings.json - Global settings

Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
root
2026-02-24 09:13:22 +00:00
parent c6be191699
commit da5403a307
17 changed files with 1733 additions and 259 deletions
+87 -1
View File
@@ -281,7 +281,54 @@ The downloaders are organized into three categories with separate base classes:
- Provides enriched metadata (synopsis, genres, ratings, poster images)
- Used as fallback when provider metadata is incomplete
### 10. Pydantic Models (`app/models/`)
### 10. Watchlist & Auto-Download System
**WatchlistManager** (`app/watchlist.py`):
- JSON-based storage in `config/watchlist.json`
- Per-user watchlist management (multi-tenant)
- CRUD operations for tracked anime
- Statistics and queries
- Settings management in `config/watchlist_settings.json`
**EpisodeChecker** (`app/episode_checker.py`):
- Checks for new episodes for anime in watchlist
- Downloads episodes automatically when detected
- Integrates with existing downloaders
- Handles errors and retries
- Lazy initialization to avoid circular imports
**AutoDownloadScheduler** (`app/auto_download_scheduler.py`):
- APScheduler-based periodic checking
- Configurable intervals (1-168 hours)
- Start/stop control via API
- Next run tracking
- Background task execution
**Watchlist Models** (`app/models/watchlist.py`):
- `WatchlistItem` - Tracked anime with settings
- `WatchlistStatus` - ACTIVE, PAUSED, COMPLETED, ARCHIVED
- `QualityPreference` - AUTO, 1080p, 720p, 480p
- `WatchlistSettings` - Global configuration
- `AutoDownloadResult` - Operation results
**Watchlist Endpoints:**
- `GET /api/watchlist` - List user's watchlist (with status filter)
- `POST /api/watchlist` - Add anime to watchlist
- `GET /api/watchlist/{item_id}` - Get specific item
- `PUT /api/watchlist/{item_id}` - Update watchlist item
- `DELETE /api/watchlist/{item_id}` - Remove from watchlist
- `POST /api/watchlist/{item_id}/check` - Check specific anime
- `POST /api/watchlist/check-all` - Check all due items
- `POST /api/watchlist/{item_id}/pause` - Pause tracking
- `POST /api/watchlist/{item_id}/resume` - Resume tracking
- `GET /api/watchlist/settings` - Get global settings
- `PUT /api/watchlist/settings` - Update settings
- `GET /api/watchlist/stats` - Get watchlist statistics
- `GET /api/watchlist/scheduler/status` - Get scheduler status
- `POST /api/watchlist/scheduler/start` - Start scheduler
- `POST /api/watchlist/scheduler/stop` - Stop scheduler
### 11. Pydantic Models (`app/models/`)
- **`__init__.py`** - Core models:
- `DownloadStatus` - Enum for task states (PENDING, DOWNLOADING, PAUSED, COMPLETED, FAILED, CANCELLED)
- `HostType` - Enum for file host types (RAPIDFILE, UNFICHIER, DOODSTREAM, OTHER)
@@ -294,6 +341,17 @@ The downloaders are organized into three categories with separate base classes:
- `SonarrEventType` - Enum for event types (Grab, Download, Rename, Delete, Test)
- `SonarrMapping` - Mapping between Sonarr series and anime providers
- `SonarrConfig` - Webhook configuration (enabled, secret, auto-download, etc.)
- **`auth.py`** - Authentication models:
- `UserCreate` - User registration request
- `UserLogin` - Login request
- `User` - User profile
- `Token` - JWT token response
- **`watchlist.py`** - Watchlist models:
- `WatchlistItem` - Tracked anime item
- `WatchlistItemCreate` - Create request
- `WatchlistItemUpdate` - Update request
- `WatchlistStatus` - Status enum
- `WatchlistSettings` - Global settings
## Test Structure
@@ -521,6 +579,8 @@ JWT_SECRET_KEY=change-me-in-production # JWT signing key for auth
- `config/users.json` - User authentication database (created automatically)
- `config/sonarr.json` - Sonarr webhook configuration (created automatically)
- `config/sonarr_mappings.json` - Sonarr to anime provider mappings (created automatically)
- `config/watchlist.json` - User watchlist items (created automatically)
- `config/watchlist_settings.json` - Watchlist global settings (created automatically)
- `config/.gitkeep` - Ensures config directory is tracked in git
- Example files: `config/sonarr.example.json`, `config/sonarr_mappings.example.json`
@@ -530,6 +590,27 @@ JWT_SECRET_KEY=change-me-in-production # JWT signing key for auth
- `docs/SONARR_INTEGRATION.md` - Complete Sonarr setup guide
- `docs/SONARR_IMPLEMENTATION.md` - Technical implementation summary
- `docs/IMPROVEMENTS_2024-01-24.md` - Recent security and quality improvements
- `docs/WATCHLIST_AUTO_DOWNLOAD.md` - Watchlist system documentation
## Security
**Filename Sanitization (`app/utils.py`):**
- `sanitize_filename()` - Removes dangerous characters (`\ / : * ? " < > |`)
- `is_safe_filename()` - Validates against path traversal patterns
- Used throughout the codebase for all file operations
- Prevents `../../../etc/passwd` style attacks
- Limits filename length to 255 characters
**CORS Configuration:**
- Restricted origins (not `*`) in production
- Specific allowed methods (GET, POST, PUT, DELETE, PATCH, OPTIONS)
- Configured in `main.py` via environment variables
**Authentication:**
- JWT token-based authentication with 7-day expiration
- bcrypt password hashing with passlib
- Passwords truncated to 72 bytes (bcrypt limitation)
- Credentials stored in `config/users.json`
## Key Implementation Details
@@ -570,9 +651,14 @@ JWT_SECRET_KEY=change-me-in-production # JWT signing key for auth
- beautifulsoup4, lxml - HTML parsing
- aiofiles - Async file operations
- jieba - Chinese text segmentation for fuzzy search
- passlib[bcrypt] - Password hashing
- python-jose[cryptography] - JWT token handling
- apscheduler - Task scheduling for auto-download
**Testing:**
- pytest - Test framework
- pytest-asyncio - Async test support
- pytest-cov - Coverage reporting
- pytest-mock - Mocking support
- pytest-timeout - Test timeout handling
- pytest-html - HTML test reports