docs(api): document the KOReader resolve endpoint

Add koreader/resolve_book.md for GET /api/sync/koreader/resolve, list
the endpoint in the API reference, and describe the resolve-then-pull-
then-push linking flow in the KOReader protocol page — including why a
device pushing to bootstrap its identity creates progress conflicts for
books already mid-read from other sources.
This commit is contained in:
2026-08-22 09:57:44 -04:00
parent 6859f81144
commit 91c8be8562
3 changed files with 86 additions and 0 deletions
+1
View File
@@ -237,6 +237,7 @@ See [OPDS Feeds](opds/)
See [KOReader Sync](koreader/) and [Sync Protocol](sync/koreader-protocol.md)
- POST /api/sync/koreader/progress - Sync reading progress
- GET /api/sync/koreader/resolve?sha256={hash} - Resolve a book UUID by file SHA-256
- GET /api/sync/koreader/metadata/:uuid - Get book metadata
- GET /api/sync/koreader/library - Get device library
- POST /api/sync/koreader/bookmarks - Sync bookmarks
@@ -0,0 +1,50 @@
# Resolve Book
Map a book's file SHA-256 to its Bookhoard UUID without touching progress
state. Used by devices to link a freshly downloaded book before their first
pull, so the device's first-page position is never pushed (which would
conflict with server-side progress for books already mid-read).
**Endpoint**: `GET /api/sync/koreader/resolve`
**Auth**: Required (Device authentication)
## Query Parameters
| Parameter | Type | Required | Description |
| --------- | ------ | -------- | ------------------------------------ |
| sha256 | string | Yes | File content hash (64 hex characters) |
Resolution is format-aware: the hash is checked against both
`media_items.file_sha256` and `media_item_formats.file_sha256`, so a
converted file (KEPUB/PDF) matches its media item too.
## Device Authentication
This endpoint requires device authentication (not user JWT). Devices
authenticate using their device credentials.
### Example Request
```http
GET /api/sync/koreader/resolve?sha256=e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
Authorization: Bearer {device_token}
```
## Response (200 OK)
```json
{
"book_uuid": "550e8400-e29b-41d4-a716-446655440000",
"sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",
"title": "Book Title",
"author": "Author Name"
}
```
## Error Responses
| Code | Description |
| ---- | -------------------------------------------- |
| 400 | Missing or malformed `sha256` parameter |
| 401 | Device authentication failed |
| 404 | No book in the library matches the given hash |
@@ -94,6 +94,41 @@ hash differs from the primary format's hash.
}
```
## Book Resolution (UUID lookup)
**Endpoint**: `GET /api/sync/koreader/resolve?sha256={hash}`
**Auth**: Device token required
Read-only lookup mapping a file SHA-256 to the book's UUID (format-aware,
same `BookResolver` path as the progress push). Devices call this on the
first open of a newly downloaded book to learn the UUID **before** their
first pull. Full details: [Resolve Book](../koreader/resolve_book.md).
This matters for conflict avoidance: a device that pushes to bootstrap its
identity transmits its current (first-page) position, which the server
treats as a real progress update — overwriting/conflicting with genuine
mid-read progress from other sources. Resolve, then pull, then push.
### Example Request
```http
GET /api/sync/koreader/resolve?sha256=e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
Authorization: Bearer device-token
```
### Response (200 OK)
```json
{
"book_uuid": "book-uuid",
"sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855",
"title": "Book Title",
"author": "Author Name"
}
```
404 when no book in the library matches the hash.
## KOReader Metadata Fetch
**Endpoint**: `GET /api/sync/koreader/metadata/{book_uuid}`