v1.1.0-beta.056 - fix(security/correctness): reader/pages access gate, RAR ComicInfo, issue-dedup quality
๐ reader/pages missing per-library access gate (audit Medium #11)
- /api/reader/pages checked only that the path was under SOME library root, not that THIS user could access it โ so any authenticated user could enumerate the page-entry filenames of any archive in any library. Added the getServerSession โ getAccessibleLibraryPaths โ canAccessPath gate reader/image uses, and upgraded its loose startsWith containment to separator-safe isPathWithinRoots
๐ฆ parseComicInfo silently failed on RAR (audit Medium #15)
- It accepted .cbr/.rar then did new AdmZip() โ which throws on RAR โ and swallowed it, so RAR ComicInfo was never read. Made parseComicInfo honestly ZIP-only; CBR/RAR are handled by the CBZ conversion pipeline (unrar/unar) and parsed after. No outcome change, but no more silent throw
๐๏ธ Issue de-dup could delete the MATCHED record (audit Medium #16)
- library/series collapsed same-number issues by sorting on parseInt(metadataId), but an UNMATCHED row's id is unmatched_ โ NaN โ undefined order, so the matched record (numeric id + filePath) could be deleted for a placeholder (cascading to ReadProgress/Bookmark). Now ranks by quality: matched, then has-file, then higher numeric id
๐งช Tests
- reader/pages out-of-root + in-root-but-no-access 403s; extractor .cbr/.rar return null without attempting getEntries
โ Verification
- tsc clean; eslint . 0 errors; vitest 273 passed (+3)