import * as CFI from '../epubcfi.js' const parser = new DOMParser() const XML = str => parser.parseFromString(str, 'application/xml') const XHTML = str => parser.parseFromString(str, 'application/xhtml+xml') { // example from EPUB CFI spec const opf = XML(` en `) const a = opf.getElementById('chap01ref') const b = CFI.toElement(opf, CFI.parse('/6/4[chap01ref]')[0]) const c = CFI.toElement(opf, CFI.parse('/6/4')[0]) console.assert(a === b) console.assert(a === c) } { // example from EPUB CFI spec const page = XHTML(`

xxxyyy0123456789

…

`) // the exact same page with some text nodes removed, CDATA & comment added, // and characters changed to entities const page2 = XHTML(`

xxxyyy4589

…

`) // the exact same page with nodes are to be ignored const page3 = XHTML(`

This is ignored!

Also ignored

xxxyyyNote: we put ignored text in this span but not the other ones because although the CFI library should ignore them, they won't be ignored by DOM Ranges, which will break the tests.0123456789

…

`) const filter = node => node.nodeType !== 1 ? NodeFilter.FILTER_ACCEPT : node.matches('.reject') ? NodeFilter.FILTER_REJECT : node.matches('.skip') ? NodeFilter.FILTER_SKIP : NodeFilter.FILTER_ACCEPT const test = (page, filter) => { for (const cfi of [ '/4[body01]/10[para05]/3:10', '/4[body01]/16[svgimg]', '/4[body01]/10[para05]/1:0', '/4[body01]/10[para05]/2/1:0', '/4[body01]/10[para05]/2/1:3', ]) { const range = CFI.toRange(page, CFI.parse(cfi), filter) const a = CFI.fromRange(range, filter) const b = `epubcfi(${cfi})` console.assert(a === b, `expected ${b}, got ${a}`) } for (let i = 0; i < 10; i++) { const cfi = `/4/10,/3:${i},/3:${i+1}` const range = CFI.toRange(page, CFI.parse(cfi), filter) const n = `${i}` console.assert(range.toString() === n, `expected ${n}, got ${range}`) } } test(page) test(page2) test(page, filter) test(page2, filter) test(page3, filter) } { // special characters in ID assertions const opf = XML(` `) const a = opf.getElementById('chap0]!/1ref^') const b = CFI.toElement(opf, CFI.parse('/6/4[chap0^]!/1ref^^]')[0]) console.assert(a === b) const page = XHTML(`

xxxyyy0123456789

…

`) for (const cfi of [ '/4[body0^]!/1^^]/10[para^]/0^,/5]/3:10', '/4[body0^]!/1^^]/16[s^]^[vgimg]', '/4[body0^]!/1^^]/10[para^]/0^,/5]/1:0', '/4[body0^]!/1^^]/10[para^]/0^,/5]/2/1:0', '/4[body0^]!/1^^]/10[para^]/0^,/5]/2/1:3', ]) { const range = CFI.toRange(page, CFI.parse(cfi)) const a = CFI.fromRange(range) const b = `epubcfi(${cfi})` console.assert(a === b, `expected ${b}, got ${a}`) } for (let i = 0; i < 10; i++) { const cfi = `/4[body0^]!/1^^]/10[para^]/0^,^/5],/3:${i},/3:${i+1}` const range = CFI.toRange(page, CFI.parse(cfi)) const n = `${i}` console.assert(range.toString() === n, `expected ${n}, got ${range}`) } } { for (const [a, b, c] of [ ['/6/4!/10', '/6/4!/10', 0], ['/6/4!/2/3:0', '/6/4!/2', 1], ['/6/4!/2/4/6/8/10/3:0', '/6/4!/4', -1], [ '/6/4[chap0^]!/1ref^^]!/4[body01^^]/10[para^]^,05^^]', '/6/4!/4/10', 0, ], [ '/6/4[chap0^]!/1ref^^]!/4[body01^^],/10[para^]^,05^^],/15:10[foo^]]', '/6/4!/4/12', -1, ], ]) { const x = CFI.compare(a, b) console.assert(x === c, `compare ${a} and ${b}, expected ${c}, got ${x}`) } }