feat(books): add read-aloud delivery policies and preserve sync

Add original and text-only EPUB delivery choices across Kobo, KOReader,
OPDS, web downloads and email while keeping source files unchanged.
Persist server defaults, device overrides and captured artifact identities
so retries and guided replacement retain the selected rendition.

Preserve saved progress across first opens, replacement resets and stale
updates, and project annotations against the copy delivered to each device.
Handle XML resource references, large inodes, retry backoff and background
worker state correctly. Consolidate the schema changes into one migration
and retain released-client request and response compatibility.

Verify with the full server and client checks, delivery and sync HTTP suites,
independent code reviews, and live KOReader download/settings/reader proof.

Fixes #1496
Closes #1603
Closes #1714
Fixes #1723
Ref #1633
Ref #1508
Ref #1621
Ref #1136
This commit is contained in:
neon
2026-10-11 03:11:27 +00:00
parent 7bb51a7a0b
commit cc50b55eeb
149 changed files with 30116 additions and 675 deletions
+21
View File
@@ -16,6 +16,27 @@ const SHARED_AUTH_TYPE_PATHS = Object.freeze(["packages/types/src/auth.ts", "pac
const SHARED_TYPES_PATHS = Object.freeze(["packages/types/src/**"]);
export const E2E_SUITES = Object.freeze({
"read-aloud-delivery": {
id: "read-aloud-delivery",
name: "Read-aloud Delivery",
timeout: 30,
lane: "full",
description: "Variant byte stability, profile isolation, Kobo artifacts and replacement, and released-client settings semantics",
vitestTarget: "test/read-aloud-delivery.e2e-spec.ts",
junitOutput: `${TEST_RESULTS_DIR}/read-aloud-delivery-e2e-junit.xml`,
prepareDedicatedDatabase: true,
useDedicatedDatabase: true,
changedPaths: [
"server/src/modules/book/delivery*",
"server/src/modules/kobo/**",
"server/src/modules/koreader/**",
"server/src/modules/opds/**",
"server/src/modules/email/**",
"server/test/read-aloud-delivery.e2e-spec.ts",
...SHARED_TYPES_PATHS,
...SHARED_DB_AND_HELPER_PATHS,
],
},
"guard-mechanics": {
id: "guard-mechanics",
name: "Guard Mechanics",