Add interactive ebook search & selection

Introduce interactive ebook support: adds two API endpoints to search (interactive-search-ebook) and create/select ebook requests (select-ebook), plus server-side handlers to route Anna's Archive (direct) and indexer (torrent/NZB) downloads. Frontend: extend RequestActionsDropdown and InteractiveTorrentSearchModal to support an "ebook" search mode and selection flow, and add hooks (useInteractiveSearchEbook / useSelectEbook). Settings: add ebook_auto_grab_enabled with UI toggle and enforce disabling when no ebook sources are enabled; settings GET/PUT updated to persist the flag (default = true to preserve behavior). Documentation updated (scheduler, ebook-sidecar, settings pages) and ranking algorithm docs/tests extended to cover ebook-related normalization and matching cases. Includes logging and ranking integration for indexer results and normalization for Anna's Archive handling.
This commit is contained in:
kikootwo
2026-02-02 19:59:58 -05:00
parent c913be5ca2
commit 1afab5d47f
19 changed files with 1339 additions and 115 deletions
+2 -2
View File
@@ -18,10 +18,10 @@ Manages recurring/scheduled jobs providing automated tasks (Plex scans, Audible
1. **plex_library_scan** - Default: every 6 hours, full library scan, disabled by default (enable after setup)
2. **plex_recently_added_check** - Default: every 5 minutes, lightweight polling of top 10 recently added items, enabled by default
3. **audible_refresh** - Default: daily midnight, fetches 200 popular + 200 new releases, stores with rankings, disabled by default
4. **retry_missing_torrents** - Default: daily midnight, re-searches 'awaiting_search' status (limit 50), enabled by default
4. **retry_missing_torrents** - Default: daily midnight, re-searches 'awaiting_search' status (limit 50), handles both audiobook and ebook requests, enabled by default
5. **retry_failed_imports** - Default: every 6 hours, re-attempts 'awaiting_import' status (limit 50), enabled by default
6. **cleanup_seeded_torrents** - Default: every 30 mins, deletes torrents after seeding requirements met, respects `seeding_time_minutes` config (0 = never), enabled by default
7. **monitor_rss_feeds** - Default: every 15 mins, checks RSS feeds from enabled indexers, matches against 'awaiting_search' requests (limit 100), triggers search jobs for matches, enabled by default
7. **monitor_rss_feeds** - Default: every 15 mins, checks RSS feeds from enabled indexers, matches against 'awaiting_search' requests (audiobook and ebook, limit 100), triggers appropriate search jobs for matches, enabled by default
## Architecture: Bull + Cron
@@ -65,6 +65,9 @@ Ebooks are first-class citizens in RMAB, with their own request type, tracking,
| Key | Default | Options | Description |
|-----|---------|---------|-------------|
| `ebook_sidecar_preferred_format` | `epub` | `epub, pdf, mobi, azw3, any` | Preferred format |
| `ebook_auto_grab_enabled` | `true` | `true, false` | Auto-create ebook requests after audiobook downloads |
*Note: Auto-grab is automatically disabled if no ebook sources are enabled. Manual fetch via admin buttons still works.*
## Database Schema
+14 -1
View File
@@ -1,7 +1,7 @@
# Intelligent Ranking Algorithm
**Status:** ✅ Implemented | Comprehensive edge case test coverage
**Tests:** tests/utils/ranking-algorithm.test.ts (73 test cases)
**Tests:** tests/utils/ranking-algorithm.test.ts (80+ test cases)
Evaluates and scores torrents to automatically select best audiobook download.
@@ -19,6 +19,7 @@ Evaluates and scores torrents to automatically select best audiobook download.
-**Author presence check (10 tests)**
-**Context-aware filtering (3 tests)**
-**API compatibility (2 tests)**
-**CamelCase and punctuation separator handling (7 tests)**
**Tested edge cases prevent regressions from previous tweaks:**
- "We Are Legion (We Are Bob)" matching with/without subtitle
@@ -35,6 +36,18 @@ Evaluates and scores torrents to automatically select best audiobook download.
**1. Title/Author Match (60 pts max) - MOST IMPORTANT**
**Pre-Processing: Text Normalization**
- All titles and author names are normalized before matching
- **CamelCase splitting:** `"TheCorrespondent"``"the correspondent"`
- **Punctuation to spaces:** `"Twelve.Months-Jim"``"twelve months jim"`
- **Preserves apostrophes:** `"O'Brien"` remains `"o'brien"`
- Handles common indexer naming patterns (NZB, torrent scene releases)
**Examples of normalization:**
- `"VirginaEvans TheCorrespondent"``"virgina evans the correspondent"`
- `"Twelve.Months-Jim.Butcher"``"twelve months jim butcher"`
- `"Author_Name-Book.Title.2024"``"author name book title 2024"`
**Multi-Stage Matching:**
**Stage 1: Word Coverage Filter (MANDATORY)**
+3
View File
@@ -90,6 +90,7 @@ src/app/admin/settings/
3. **General Settings Section** (visible when any source enabled)
- Preferred format: EPUB (recommended), PDF, MOBI, AZW3, Any
- Auto-grab toggle: Automatically create ebook requests after audiobook downloads
**Configuration Keys:**
| Key | Default | Description |
@@ -97,6 +98,7 @@ src/app/admin/settings/
| `ebook_annas_archive_enabled` | `false` | Enable Anna's Archive |
| `ebook_indexer_search_enabled` | `false` | Enable Indexer Search via Prowlarr |
| `ebook_sidecar_preferred_format` | `epub` | Preferred format |
| `ebook_auto_grab_enabled` | `true` | Auto-create ebook requests after audiobook downloads |
| `ebook_sidecar_base_url` | `https://annas-archive.li` | Anna's Archive mirror |
| `ebook_sidecar_flaresolverr_url` | `` | FlareSolverr URL |
@@ -104,6 +106,7 @@ src/app/admin/settings/
- If Anna's Archive enabled → Searches Anna's Archive first
- If Indexer Search enabled → Falls back to indexer search if Anna's Archive fails/disabled
- If both disabled → Ebook downloads completely off
- If auto-grab disabled → Manual "Fetch Ebook" button only (admin buttons still work)
## Indexer Categories (Tabbed)