fix(docs): Work Order 2 — correct stale paths (11 docs + 3 Bruno)

Fix all wrong-path artifacts identified by the audit:
- Kobo sync endpoints (init/bookmark/markup/sync-from-server/analytics): add
  missing :token device segment (6 doc files incl. kobo-protocol.md)
- Highlights/notes update+delete: add missing /:id media-item prefix
- media-items/download_media_item.md: removed (static /uploads route, not an
  API endpoint; info about the file route is recoverable from OPDS docs)
- Bruno: /libraries/visible -> /visibility, /collections/books missing id,
  /audio/0 -> track_index
- operations/troubleshooting.md: same /libraries/visible -> /visibility fix
- media-items/get_audio_track.md + get_audio_chapters.md: /audio/0 examples fixed
- Deleted monolithic docs/developer/api-reference.md (duplicate of split docs)
- Fixed 4 stale entries in docs/developer/api/api-reference.md (split index)

Audit re-run: orphan docs 0, orphan Bruno 6 (all scenario files with literal IDs).
This commit is contained in:
John O'Keefe committed 2026-10-24 14:44:19 -04:00
1 parent cc893f758e
commit 50282895f5
19 files changed
+29 -1831

No files matched your search

File diff suppressed because it is too large. Load diff
+5 -5
View File
@@ -256,11 +256,11 @@ See [KOReader Sync](koreader/) and [Sync Protocol](sync/koreader-protocol.md)
See [Kobo Sync](kobo/) and [Sync Protocol](sync/kobo-protocol.md)
- POST /api/sync/kobo/markup - Sync markup highlights
- POST /api/sync/kobo/bookmark - Sync bookmarks
- POST /api/sync/kobo/v1/analytics/gettests - Analytics endpoint
- GET /api/sync/kobo/v1/initialization - Initialize Kobo sync
- POST /api/sync/kobo/sync-from-server - Push content to device
- POST /api/sync/kobo/:token/markup - Sync markup highlights
- POST /api/sync/kobo/:token/bookmark - Sync bookmarks
- POST /api/sync/kobo/:token/v1/analytics/gettests - Analytics endpoint
- GET /api/sync/kobo/:token/v1/initialization - Initialize Kobo sync
- POST /api/sync/kobo/:token/sync-from-server - Push content to device
## WebSocket
@@ -2,7 +2,7 @@
Delete a highlight.
**Endpoint**: `DELETE /api/media-items/highlights/{highlight_id}`
**Endpoint**: `DELETE /api/media-items/:id/highlights/:highlightId`
**Auth**: Required
## Path Parameters
@@ -2,7 +2,7 @@
Update an existing highlight.
**Endpoint**: `PUT /api/media-items/highlights/{highlight_id}`
**Endpoint**: `PUT /api/media-items/:id/highlights/:highlightId`
**Auth**: Required
**Content-Type**: `application/json`
@@ -4,7 +4,7 @@
Kobo analytics endpoint (device compatibility).
**Endpoint**: `POST /api/sync/kobo/v1/analytics/gettests`
**Endpoint**: `POST /api/sync/kobo/:token/v1/analytics/gettests`
**Auth**: Required (Device authentication)
## Device Authentication
+1 -1
View File
@@ -4,7 +4,7 @@
Sync bookmarks from Kobo device.
**Endpoint**: `POST /api/sync/kobo/bookmark`
**Endpoint**: `POST /api/sync/kobo/:token/bookmark`
**Auth**: Required (Device authentication)
## Device Authentication
+2 -2
View File
@@ -4,7 +4,7 @@
Initialize Kobo device sync.
**Endpoint**: `GET /api/sync/kobo/v1/initialization`
**Endpoint**: `GET /api/sync/kobo/:token/v1/initialization`
**Auth**: Required (Device authentication)
## Device Authentication
@@ -22,7 +22,7 @@ This endpoint requires device authentication (not user JWT). Kobo devices authen
### Example Request
```http
GET /api/sync/kobo/v1/initialization
GET /api/sync/kobo/:token/v1/initialization
X-Device-ID: 550e8400-e29b-41d4-a716-446655440000
X-Device-Key: device-auth-key
```
+1 -1
View File
@@ -4,7 +4,7 @@
Sync markup highlights and annotations from Kobo device.
**Endpoint**: `POST /api/sync/kobo/markup`
**Endpoint**: `POST /api/sync/kobo/:token/markup`
**Auth**: Required (Device authentication)
## Device Authentication
+1 -1
View File
@@ -4,7 +4,7 @@
Push content and metadata to Kobo device.
**Endpoint**: `POST /api/sync/kobo/sync-from-server`
**Endpoint**: `POST /api/sync/kobo/:token/sync-from-server`
**Auth**: Required (Device authentication)
## Device Authentication
@@ -1,48 +0,0 @@
# Download Media Item
Download a media item file (EPUB, PDF, etc.) from the Bookhoard server.
Book files are served by the authenticated file route, the same one the web reader uses. Build the URL from the media item's `library_id` and relative `file_path` (both returned by the media item list/get endpoints):
**Endpoint**: `GET /uploads/library-{library_id}/{file_path}`
**Auth**: Required (JWT - Bearer header or session cookie)
The `file_path` segments are URL-escaped individually; slashes are preserved. `cover_image_path` uses the same route.
## Path Parameters
| Parameter | Type | Required | Description |
| ----------- | ------ | -------- | ------------------------------------ |
| library_id | string | Yes | Library UUID (the item's library) |
| file_path | string | Yes | The item's relative `file_path` |
## Response
**Success (200 OK)**: Binary file data
**Response Headers**:
- `Content-Type`: MIME type by file extension (`application/epub+zip`, `application/pdf`, …; `application/octet-stream` fallback)
- `Cache-Control`: `public, max-age=86400`
## Error Responses
| Code | Description |
| ---- | --------------------------- |
| 400 | Invalid library ID or path |
| 401 | Missing/invalid token |
| 404 | File not found on disk |
## Example
```bash
curl -O -H "Authorization: Bearer $TOKEN" \
"http://localhost:8765/uploads/library/550e8400-.../books/1984.epub"
```
(URL shape: `/uploads/library-{uuid}/{escaped-relative-path}`.)
## Notes
- **Do not rely on `GET /api/media-items/:id/download`** — it appears in older docs but is **not registered**; `MediaHandler.DownloadBook` exists as dead code. Use the file route above.
- OPDS-capable devices may alternatively use the device-authenticated `GET /opds/devices/{deviceId}/download/{bookId}`, which supports on-the-fly format conversion (epub, kepub, pdf, cbz).
@@ -23,7 +23,7 @@ which file model produced them.
"tracks": [
{
"index": 0,
"url": "/api/media-items/{id}/audio/0",
"url": "/api/media-items/{id}/audio/{trackIndex}",
"title": "01 First",
"path": "Author/Title/01 First.mp3",
"start": 0.0,
@@ -40,5 +40,5 @@ answers **403** on every track (same gate as the download endpoint).
```bash
curl -H "Authorization: Bearer $TOKEN" \
-H "Range: bytes=0-1023" \
"http://localhost:8765/api/media-items/550e8400-.../audio/0"
"http://localhost:8765/api/media-items/550e8400-.../audio/{track_index}"
```
+1 -1
View File
@@ -2,7 +2,7 @@
Delete a note.
**Endpoint**: `DELETE /api/media-items/notes/{note_id}`
**Endpoint**: `DELETE /api/media-items/:id/notes/:noteId`
**Auth**: Required
## Path Parameters
+1 -1
View File
@@ -2,7 +2,7 @@
Update an existing note.
**Endpoint**: `PUT /api/media-items/notes/{note_id}`
**Endpoint**: `PUT /api/media-items/:id/notes/:noteId`
**Auth**: Required
**Content-Type**: `application/json`
+2 -2
View File
@@ -6,7 +6,7 @@ Kobo uses a proprietary sync protocol with JSON payloads.
## Kobo Markup Sync
**Endpoint**: `POST /api/sync/kobo/markup`
**Endpoint**: `POST /api/sync/kobo/:token/markup`
**Auth**: Device token required
**Content-Type**: `application/json`
@@ -33,7 +33,7 @@ Kobo uses a proprietary sync protocol with JSON payloads.
### Example Request
```http
POST /api/sync/kobo/markup
POST /api/sync/kobo/:token/markup
Authorization: Bearer device-token
x-kobo-device: {"DeviceId":"device-id","Model":"Kobo Clara"}
Content-Type: application/json