diff --git a/apps/readest-app/src/__tests__/utils/toc-cfi-mapping.test.ts b/apps/readest-app/src/__tests__/utils/toc-cfi-mapping.test.ts
index e8901c81..8c64108f 100644
--- a/apps/readest-app/src/__tests__/utils/toc-cfi-mapping.test.ts
+++ b/apps/readest-app/src/__tests__/utils/toc-cfi-mapping.test.ts
@@ -1,10 +1,16 @@
import { describe, it, expect, beforeAll, vi } from 'vitest';
import { readFileSync } from 'fs';
import { resolve } from 'path';
-import { DocumentLoader } from '@/libs/document';
+import { DocumentLoader, CFI } from '@/libs/document';
import type { BookDoc, TOCItem } from '@/libs/document';
import { updateToc, findTocItemBS } from '@/utils/toc';
+// Simulates an annotation deep inside a section, past the chapter heading.
+// Section CFIs look like `epubcfi(/6/2)` and TOC item CFIs point at the heading
+// (e.g. `epubcfi(/6/2!/4/2[ch01])`), so a real annotation lives after that —
+// e.g. inside a
sibling, reached via `CFI.joinIndir`.
+const ANNOTATION_PATH = '/4/4/1:0';
+
// Polyfill CSS.escape for jsdom
if (typeof globalThis['CSS'] === 'undefined') {
(globalThis as Record)['CSS'] = {
@@ -82,8 +88,8 @@ describe('TOC-to-CFI mapping with fragment hrefs (#3688)', () => {
const firstSection = linearSections[0]!;
const lastSection = linearSections[linearSections.length - 1]!;
- const firstTocItem = findTocItemBS(toc, firstSection.cfi);
- const lastTocItem = findTocItemBS(toc, lastSection.cfi);
+ const firstTocItem = findTocItemBS(toc, CFI.joinIndir(firstSection.cfi, ANNOTATION_PATH));
+ const lastTocItem = findTocItemBS(toc, CFI.joinIndir(lastSection.cfi, ANNOTATION_PATH));
expect(firstTocItem).not.toBeNull();
expect(lastTocItem).not.toBeNull();
@@ -99,7 +105,7 @@ describe('TOC-to-CFI mapping with fragment hrefs (#3688)', () => {
const linearSections = sections.filter((s) => s.linear !== 'no' && s.cfi);
const midSection = linearSections[1]!;
- const midTocItem = findTocItemBS(toc, midSection.cfi);
+ const midTocItem = findTocItemBS(toc, CFI.joinIndir(midSection.cfi, ANNOTATION_PATH));
expect(midTocItem).not.toBeNull();
expect(midTocItem!.label).toBe('Chapter Two');
diff --git a/packages/foliate-js b/packages/foliate-js
index 2476b0da..317051ef 160000
--- a/packages/foliate-js
+++ b/packages/foliate-js
@@ -1 +1 @@
-Subproject commit 2476b0dabf5269884ee53ff2332536ae13a3531b
+Subproject commit 317051ef4d43f49dda84285e5e4b27ef5f93cf85