Initial commit
This commit is contained in:
commit
2683eae6b3
36 files changed
+7369
No files matched your search
@@ -0,0 +1,100 @@
|
||||
import assert from 'node:assert/strict'
|
||||
import { existsSync } from 'node:fs'
|
||||
import { mkdtemp, readFile, rm } from 'node:fs/promises'
|
||||
import os from 'node:os'
|
||||
import path from 'node:path'
|
||||
import test from 'node:test'
|
||||
import { getDocument } from 'pdfjs-dist/legacy/build/pdf.mjs'
|
||||
import { exportWikiToPdf } from '../src/exporter.js'
|
||||
import { closeBrowser } from '../src/pdf-renderer.js'
|
||||
import { startMockWiki } from './mock-wiki.js'
|
||||
|
||||
// The renderer keeps a Chromium instance alive between exports. Close it so
|
||||
// the test process can exit after the suite finishes.
|
||||
test.after(async () => {
|
||||
await closeBrowser()
|
||||
})
|
||||
|
||||
const chromiumPath = [
|
||||
process.env.CHROMIUM_PATH,
|
||||
'/usr/bin/chromium',
|
||||
'/usr/bin/chromium-browser',
|
||||
'/opt/google/chrome/chrome',
|
||||
'/Applications/Google Chrome.app/Contents/MacOS/Google Chrome',
|
||||
]
|
||||
.filter(Boolean)
|
||||
.find((candidate) => existsSync(candidate))
|
||||
|
||||
test(
|
||||
'exports a subtree to a PDF with working internal and external links',
|
||||
{ skip: chromiumPath ? false : 'No Chromium executable found for the smoke test.', timeout: 180_000 },
|
||||
async () => {
|
||||
const wiki = await startMockWiki()
|
||||
const tempDir = await mkdtemp(path.join(os.tmpdir(), 'wiki-print-test-'))
|
||||
|
||||
try {
|
||||
const result = await exportWikiToPdf({
|
||||
baseUrl: wiki.url,
|
||||
apiKey: 'test-key',
|
||||
startPage: 'docs',
|
||||
maxPages: 50,
|
||||
outputPath: path.join(tempDir, 'export.pdf'),
|
||||
})
|
||||
|
||||
assert.equal(result.pageCount, 5)
|
||||
assert.equal(result.locale, 'en')
|
||||
assert.equal(wiki.state.assetHits, 1, 'the page image should be fetched once for embedding')
|
||||
|
||||
const pdfData = new Uint8Array(await readFile(result.pdfPath))
|
||||
const pdf = await getDocument({
|
||||
data: pdfData,
|
||||
disableFontFace: true,
|
||||
useSystemFonts: true,
|
||||
}).promise
|
||||
|
||||
try {
|
||||
let text = ''
|
||||
const annotations = []
|
||||
for (let pageNumber = 1; pageNumber <= pdf.numPages; pageNumber += 1) {
|
||||
const page = await pdf.getPage(pageNumber)
|
||||
const content = await page.getTextContent()
|
||||
text += `\n${content.items.map((item) => item.str).join(' ')}`
|
||||
annotations.push(...(await page.getAnnotations()))
|
||||
}
|
||||
|
||||
assert.ok(pdf.numPages >= 3, `expected several PDF pages, got ${pdf.numPages}`)
|
||||
assert.match(text, /DOCS_MARKER/)
|
||||
assert.match(text, /INSTALL_MARKER/)
|
||||
assert.match(text, /LINUX_MARKER/)
|
||||
assert.match(text, /OTHER_MARKER/)
|
||||
assert.match(text, /FALLBACK_MARKER/)
|
||||
assert.doesNotMatch(text, /DRAFT_MARKER/)
|
||||
assert.doesNotMatch(text, /EXCLUDED_SIBLING_MARKER/)
|
||||
assert.doesNotMatch(text, /GUIDE_OUTSIDE_MARKER/)
|
||||
assert.doesNotMatch(text, /window\.evil/)
|
||||
|
||||
const links = annotations.filter((annotation) => annotation.subtype === 'Link')
|
||||
assert.ok(links.length > 0, 'expected link annotations in the PDF')
|
||||
assert.ok(
|
||||
links.some((link) => /example\.com/.test(link.url || link.unsafeUrl || '')),
|
||||
'expected the external link to remain a URL annotation',
|
||||
)
|
||||
assert.ok(
|
||||
links.some(
|
||||
(link) =>
|
||||
link.dest ||
|
||||
/^#/.test(link.url || '') ||
|
||||
/^#/.test(link.unsafeUrl || '') ||
|
||||
link.action === 'GoTo',
|
||||
),
|
||||
'expected internal wiki links to stay internal PDF links',
|
||||
)
|
||||
} finally {
|
||||
await pdf.destroy()
|
||||
}
|
||||
} finally {
|
||||
await wiki.close()
|
||||
await rm(tempDir, { recursive: true, force: true })
|
||||
}
|
||||
},
|
||||
)
|
||||
Reference in new issue
Block a user