Phase 8: Documentation and deprecation warnings for identifier standardization
- Enhanced infrastructure.md with identifier convention table, format requirements, migration notes - Updated docs/README.md with series identifier convention section - Updated docs/api_reference.md with key-based API examples and notes - Added deprecation warnings to SerieList.get_by_folder() - Added deprecation warnings to anime.py folder fallback lookup - Added deprecation warnings to validate_series_key_or_folder() - All warnings include v3.0.0 removal timeline - All 1006 tests pass
This commit is contained in:
@@ -97,6 +97,42 @@ Production deployment instructions covering:
|
||||
- Status notifications
|
||||
- Error alerts
|
||||
|
||||
## Series Identifier Convention
|
||||
|
||||
### Understanding Series Identifiers
|
||||
|
||||
The application uses two identifiers for anime series:
|
||||
|
||||
| Identifier | Purpose | Example | Used For |
|
||||
| ---------- | ------------------------ | -------------------------- | ----------------- |
|
||||
| `key` | **Primary identifier** | `"attack-on-titan"` | All API lookups |
|
||||
| `folder` | Filesystem metadata only | `"Attack on Titan (2013)"` | Display purposes |
|
||||
|
||||
### Key Format
|
||||
|
||||
- Lowercase letters and numbers only
|
||||
- Words separated by hyphens (`-`)
|
||||
- No spaces, underscores, or uppercase letters
|
||||
- Examples: `"one-piece"`, `"86-eighty-six"`, `"re-zero"`
|
||||
|
||||
### Usage Guidelines
|
||||
|
||||
```python
|
||||
# ✅ Correct: Use 'key' for API operations
|
||||
GET /api/anime/attack-on-titan
|
||||
POST /api/queue/add {"serie_id": "attack-on-titan", ...}
|
||||
|
||||
# ❌ Deprecated: Folder-based lookups (backward compatibility only)
|
||||
GET /api/anime/Attack%20on%20Titan%20(2013) # Will work but deprecated
|
||||
```
|
||||
|
||||
### Backward Compatibility
|
||||
|
||||
For existing integrations, folder-based lookups are still supported but deprecated:
|
||||
- API endpoints check `key` first, then fall back to `folder`
|
||||
- New code should always use `key` as the identifier
|
||||
- Deprecation warnings will be added in future versions
|
||||
|
||||
## Documentation Examples
|
||||
|
||||
### API Usage Example
|
||||
@@ -285,8 +321,8 @@ docs/
|
||||
|
||||
## Document Info
|
||||
|
||||
- **Last Updated**: October 22, 2025
|
||||
- **Version**: 1.0.0
|
||||
- **Last Updated**: November 28, 2025
|
||||
- **Version**: 2.0.0
|
||||
- **Status**: Production Ready
|
||||
- **Maintainers**: Development Team
|
||||
|
||||
|
||||
@@ -421,12 +421,16 @@ Authorization: Bearer <token>
|
||||
|
||||
### Anime Endpoints
|
||||
|
||||
> **Note on Identifiers**: All anime endpoints use `key` as the primary series identifier (e.g., `"attack-on-titan"`).
|
||||
> The `folder` field is metadata only and should not be used for lookups.
|
||||
> For backward compatibility, folder-based lookups are supported but deprecated.
|
||||
|
||||
#### List Anime with Missing Episodes
|
||||
|
||||
Lists all anime series with missing episodes.
|
||||
|
||||
```http
|
||||
GET /api/v1/anime
|
||||
GET /api/anime
|
||||
Authorization: Bearer <token>
|
||||
```
|
||||
|
||||
@@ -442,14 +446,18 @@ Authorization: Bearer <token>
|
||||
```json
|
||||
[
|
||||
{
|
||||
"id": "aniworld_123",
|
||||
"title": "Attack on Titan",
|
||||
"missing_episodes": 5
|
||||
"key": "attack-on-titan",
|
||||
"name": "Attack on Titan",
|
||||
"folder": "Attack on Titan (2013)",
|
||||
"missing_episodes": 5,
|
||||
"link": "https://aniworld.to/anime/stream/attack-on-titan"
|
||||
},
|
||||
{
|
||||
"id": "aniworld_456",
|
||||
"title": "Demon Slayer",
|
||||
"missing_episodes": 2
|
||||
"key": "demon-slayer",
|
||||
"name": "Demon Slayer",
|
||||
"folder": "Demon Slayer (2019)",
|
||||
"missing_episodes": 2,
|
||||
"link": "https://aniworld.to/anime/stream/demon-slayer"
|
||||
}
|
||||
]
|
||||
```
|
||||
@@ -461,20 +469,23 @@ Authorization: Bearer <token>
|
||||
Retrieves detailed information for a specific anime series.
|
||||
|
||||
```http
|
||||
GET /api/v1/anime/{anime_id}
|
||||
GET /api/anime/{anime_id}
|
||||
Authorization: Bearer <token>
|
||||
```
|
||||
|
||||
**Path Parameters**:
|
||||
|
||||
- `anime_id` (string): Series `key` (preferred) or `folder` (deprecated)
|
||||
|
||||
**Response (200 OK)**:
|
||||
|
||||
```json
|
||||
{
|
||||
"id": "aniworld_123",
|
||||
"key": "attack-on-titan",
|
||||
"title": "Attack on Titan",
|
||||
"episodes": ["Season 1 Episode 1", "Season 1 Episode 2"],
|
||||
"description": "Anime description...",
|
||||
"total_episodes": 100,
|
||||
"downloaded_episodes": 95
|
||||
"folder": "Attack on Titan (2013)",
|
||||
"episodes": ["S01-E01", "S01-E02", "S02-E01"],
|
||||
"description": "Anime description..."
|
||||
}
|
||||
```
|
||||
|
||||
@@ -489,7 +500,7 @@ Authorization: Bearer <token>
|
||||
Rescans the local anime directory for new series and episodes.
|
||||
|
||||
```http
|
||||
POST /api/v1/anime/rescan
|
||||
POST /api/anime/rescan
|
||||
Authorization: Bearer <token>
|
||||
```
|
||||
|
||||
@@ -539,6 +550,9 @@ Authorization: Bearer <token>
|
||||
|
||||
### Download Queue Endpoints
|
||||
|
||||
> **Note on Identifiers**: Download queue operations use `serie_id` which should be the series `key` (e.g., `"attack-on-titan"`).
|
||||
> The `serie_folder` field is filesystem metadata and should not be used for identification.
|
||||
|
||||
#### Get Queue Status
|
||||
|
||||
Retrieves download queue status and statistics.
|
||||
@@ -577,13 +591,21 @@ Authorization: Bearer <token>
|
||||
Content-Type: application/json
|
||||
|
||||
{
|
||||
"anime_id": "aniworld_123",
|
||||
"serie_id": "attack-on-titan",
|
||||
"serie_folder": "Attack on Titan (2013)",
|
||||
"serie_name": "Attack on Titan",
|
||||
"episodes": ["S01E01", "S01E02"],
|
||||
"priority": "normal"
|
||||
"priority": 1
|
||||
}
|
||||
```
|
||||
|
||||
**Priority Values**: `low`, `normal`, `high`
|
||||
**Request Fields**:
|
||||
|
||||
- `serie_id` (string, required): Series `key` - primary identifier
|
||||
- `serie_folder` (string, optional): Filesystem folder name (metadata)
|
||||
- `serie_name` (string, required): Display name
|
||||
- `episodes` (array, required): List of episodes to download
|
||||
- `priority` (integer, optional): Priority level (default: 0)
|
||||
|
||||
**Response (201 Created)**:
|
||||
|
||||
@@ -592,7 +614,7 @@ Content-Type: application/json
|
||||
"success": true,
|
||||
"data": {
|
||||
"queue_item_id": "queue_456",
|
||||
"anime_id": "aniworld_123",
|
||||
"serie_id": "attack-on-titan",
|
||||
"status": "pending"
|
||||
}
|
||||
}
|
||||
@@ -682,18 +704,21 @@ Authorization: Bearer <token>
|
||||
|
||||
### WebSocket Endpoints
|
||||
|
||||
> **Note on Identifiers**: All WebSocket events include `key` as the primary series identifier.
|
||||
> The `folder` field is included as metadata but should not be used for identification.
|
||||
|
||||
#### Real-Time Progress Updates
|
||||
|
||||
Establishes WebSocket connection for real-time download progress updates.
|
||||
|
||||
```
|
||||
WS /ws/downloads
|
||||
WS /ws/connect
|
||||
```
|
||||
|
||||
**Connection**:
|
||||
|
||||
```javascript
|
||||
const ws = new WebSocket("ws://localhost:8000/ws/downloads");
|
||||
const ws = new WebSocket("ws://localhost:8000/ws/connect");
|
||||
|
||||
ws.onmessage = (event) => {
|
||||
const message = JSON.parse(event.data);
|
||||
@@ -701,6 +726,8 @@ ws.onmessage = (event) => {
|
||||
};
|
||||
```
|
||||
|
||||
**Rooms**: `downloads`, `download_progress`, `scan_progress`
|
||||
|
||||
**Message Types**:
|
||||
|
||||
**Download Started**:
|
||||
@@ -710,8 +737,9 @@ ws.onmessage = (event) => {
|
||||
"type": "download_started",
|
||||
"timestamp": "2025-10-22T12:00:00Z",
|
||||
"data": {
|
||||
"queue_item_id": "queue_456",
|
||||
"anime_title": "Attack on Titan",
|
||||
"download_id": "dl_456",
|
||||
"key": "attack-on-titan",
|
||||
"folder": "Attack on Titan (2013)",
|
||||
"episode": "S01E01"
|
||||
}
|
||||
}
|
||||
@@ -724,11 +752,12 @@ ws.onmessage = (event) => {
|
||||
"type": "download_progress",
|
||||
"timestamp": "2025-10-22T12:00:05Z",
|
||||
"data": {
|
||||
"queue_item_id": "queue_456",
|
||||
"progress_percent": 45,
|
||||
"downloaded_bytes": 500000000,
|
||||
"total_bytes": 1100000000,
|
||||
"speed_mbps": 5.5
|
||||
"download_id": "dl_456",
|
||||
"key": "attack-on-titan",
|
||||
"folder": "Attack on Titan (2013)",
|
||||
"percent": 45.2,
|
||||
"speed_mbps": 5.5,
|
||||
"eta_seconds": 180
|
||||
}
|
||||
}
|
||||
```
|
||||
@@ -737,11 +766,12 @@ ws.onmessage = (event) => {
|
||||
|
||||
```json
|
||||
{
|
||||
"type": "download_completed",
|
||||
"type": "download_complete",
|
||||
"timestamp": "2025-10-22T12:05:00Z",
|
||||
"data": {
|
||||
"queue_item_id": "queue_456",
|
||||
"total_time_seconds": 300,
|
||||
"download_id": "dl_456",
|
||||
"key": "attack-on-titan",
|
||||
"folder": "Attack on Titan (2013)",
|
||||
"file_path": "/path/to/anime/file.mkv"
|
||||
}
|
||||
}
|
||||
@@ -751,15 +781,17 @@ ws.onmessage = (event) => {
|
||||
|
||||
```json
|
||||
{
|
||||
"type": "download_error",
|
||||
"type": "download_failed",
|
||||
"timestamp": "2025-10-22T12:05:00Z",
|
||||
"data": {
|
||||
"queue_item_id": "queue_456",
|
||||
"error_message": "Connection timeout",
|
||||
"error_code": "PROVIDER_ERROR"
|
||||
"download_id": "dl_456",
|
||||
"key": "attack-on-titan",
|
||||
"folder": "Attack on Titan (2013)",
|
||||
"error": "Connection timeout"
|
||||
}
|
||||
}
|
||||
```
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
|
||||
Reference in New Issue
Block a user