Skip to content

Commit

Permalink
Fix existing tests
Browse files Browse the repository at this point in the history
  • Loading branch information
yhatt committed Sep 15, 2024
1 parent 23700cb commit ac600fa
Show file tree
Hide file tree
Showing 14 changed files with 142 additions and 91 deletions.
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,7 @@
"@rollup/plugin-url": "^8.0.2",
"@tsconfig/node14": "^14.1.2",
"@types/cheerio": "^0.22.35",
"@types/dom-view-transitions": "^1.0.5",
"@types/express": "^4.17.21",
"@types/jest": "^29.5.13",
"@types/markdown-it": "^14.1.2",
Expand Down
12 changes: 2 additions & 10 deletions src/templates/bespoke/transition.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,6 @@ interface TransitionCallbackOption {
cond: (e: any) => boolean
}

interface ViewTransition {
finished: Promise<void>
ready: Promise<void>
skipTransition: () => void
updateCallbackDone: Promise<void>
}

export const transitionStyleId = '_tSId' as const

const transitionApply = '_tA' as const
Expand Down Expand Up @@ -47,7 +40,7 @@ const reducedKeyframes: MarpTransitionKeyframes = {
}

const bespokeTransition = (deck) => {
if (!document['startViewTransition']) return
if (!document.startViewTransition) return

const transitionDuringState = (
value?: boolean | ViewTransition
Expand Down Expand Up @@ -189,8 +182,7 @@ const bespokeTransition = (deck) => {
try {
transitionDuringState(true) // to prevent unexpected navigation

const transition: ViewTransition =
document['startViewTransition'](navigate)
const transition = document.startViewTransition(navigate)

transitionDuringState(transition)
transition.finished.finally(finalize)
Expand Down
10 changes: 8 additions & 2 deletions src/utils/puppeteer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import { findChromeInstallation } from './chrome-finder'
import { isInsideContainer } from './container'
import { findEdgeInstallation } from './edge-finder'
import { isWSL, resolveWindowsEnv } from './wsl'
import { nanoid } from 'nanoid'

let executablePath: string | undefined | false = false
let wslTmp: string | undefined
Expand Down Expand Up @@ -48,18 +49,23 @@ const isSnapBrowser = (executablePath: string | undefined) => {
return false
}

const puppeteerDataDirSuffix = nanoid(10)

export const generatePuppeteerDataDirPath = async (
name: string,
{ wslHost }: { wslHost?: boolean } = {}
): Promise<string> => {
const nameWithSuffix = `${name}-${puppeteerDataDirSuffix}`

const dataDir = await (async () => {
if ((await isWSL()) && wslHost) {
// In WSL environment, Marp CLI may use Chrome on Windows. If Chrome has
// located in host OS (Windows), we have to specify Windows path.
if (wslTmp === undefined) wslTmp = await resolveWindowsEnv('TMP')
if (wslTmp !== undefined) return path.win32.resolve(wslTmp, name)
if (wslTmp !== undefined)
return path.win32.resolve(wslTmp, nameWithSuffix)
}
return path.resolve(os.tmpdir(), name)
return path.resolve(os.tmpdir(), nameWithSuffix)
})()

// Ensure the data directory is created
Expand Down
2 changes: 1 addition & 1 deletion test/_browser/viewTransition.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ beforeEach(() => {

afterEach(() => {
if ('startViewTransition' in document) {
delete document.startViewTransition
delete (document as any).startViewTransition
}
})

Expand Down
2 changes: 1 addition & 1 deletion test/_configs/basic/md.md
Original file line number Diff line number Diff line change
@@ -1 +1 @@
<b>html</b>
<b>html<button>button</button></b>
6 changes: 5 additions & 1 deletion test/_files/themes/a.css
Original file line number Diff line number Diff line change
@@ -1 +1,5 @@
/* @theme a */
/** @theme a */

section {
--theme-a: true;
}
6 changes: 5 additions & 1 deletion test/_files/themes/b.css
Original file line number Diff line number Diff line change
@@ -1 +1,5 @@
/* @theme b */
/** @theme b */

section {
--theme-b: true;
}
6 changes: 5 additions & 1 deletion test/_files/themes/nested/c.css
Original file line number Diff line number Diff line change
@@ -1 +1,5 @@
/* @theme c */
/** @theme c */

section {
--theme-c: true;
}
19 changes: 13 additions & 6 deletions test/converter.ts
Original file line number Diff line number Diff line change
Expand Up @@ -138,14 +138,21 @@ describe('Converter', () => {
})

it("overrides html option by converter's html option", async () => {
const defaultHtml = (await instance().convert('<i><br></i>')).rendered
expect(defaultHtml.html).toContain('&lt;i&gt;<br />&lt;/i&gt;')
const htmlMd = '<i><br><button>test</button></i>'

const enabled = (await instance({ html: true }).convert(md)).rendered
expect(enabled.html).toContain('<i>Hello!</i>')
const defaultHtml = (await instance().convert(htmlMd)).rendered
expect(defaultHtml.html).toContain(
'<i><br />&lt;button&gt;test&lt;/button&gt;</i>'
)

const enabled = (await instance({ html: true }).convert(htmlMd)).rendered
expect(enabled.html).toContain('<i><br /><button>test</button></i>')

const disabled = (await instance({ html: false }).convert(md)).rendered
expect(disabled.html).toContain('&lt;i&gt;Hello!&lt;/i&gt;')
const disabled = (await instance({ html: false }).convert(htmlMd))
.rendered
expect(disabled.html).toContain(
'&lt;i&gt;&lt;br&gt;&lt;button&gt;test&lt;/button&gt;&lt;/i&gt;'
)
})

it('correctly applies overridden global directives even if enabled HTML option', async () => {
Expand Down
22 changes: 12 additions & 10 deletions test/marp-cli.ts
Original file line number Diff line number Diff line change
Expand Up @@ -357,7 +357,7 @@ describe('Marp CLI', () => {
expect(await marpCli(['--input-dir', files, '--theme', 'a'])).toBe(0)

for (const [, buffer] of writeFile.mock.calls) {
expect(buffer.toString()).toContain('/* @theme a */')
expect(buffer.toString()).toContain('--theme-a')
}
} finally {
info.mockRestore()
Expand Down Expand Up @@ -561,7 +561,7 @@ describe('Marp CLI', () => {
expect(await marpCli(args)).toBe(0)

const { css } = (await convert.mock.results[0].value).rendered
expect(css).toContain('/* @theme a */')
expect(css).toContain('--theme-a')

const converter: Converter = convert.mock.instances[0]
const { themeSet } = converter.options
Expand Down Expand Up @@ -630,7 +630,7 @@ describe('Marp CLI', () => {
expect(convert).toHaveBeenCalledTimes(1)

const { css } = (await convert.mock.results[0].value).rendered
expect(css).toContain('@theme a')
expect(css).toContain('--theme-a')
expect(observeSpy).toHaveBeenCalledWith(filePath, 'a')
})
})
Expand All @@ -646,7 +646,7 @@ describe('Marp CLI', () => {
expect(await marpCli([...baseArgs, '--theme', name])).toBe(0)
expect(convert).toHaveBeenCalledTimes(1)
expect((await convert.mock.results[0].value).rendered.css).toContain(
`@theme ${name}`
`--theme-${name}`
)
expect(observeSpy).toHaveBeenCalledWith(filePath, name)
}
Expand All @@ -664,7 +664,7 @@ describe('Marp CLI', () => {
expect(await marpCli([...baseArgs(themes), '--theme', name])).toBe(0)
expect(convert).toHaveBeenCalledTimes(1)
expect((await convert.mock.results[0].value).rendered.css).toContain(
`@theme ${name}`
`--theme-${name}`
)
expect(observeSpy).toHaveBeenCalledWith(filePath, name)
}
Expand Down Expand Up @@ -980,7 +980,7 @@ describe('Marp CLI', () => {
expect(await marpCli(['md.md'])).toBe(0)

const html = stdout.mock.calls[0][0].toString()
expect(html).toContain('<b>html</b>')
expect(html).toContain('<b>html<button>button</button></b>')
} finally {
stdout.mockRestore()
warn.mockRestore()
Expand All @@ -1002,9 +1002,11 @@ describe('Marp CLI', () => {

expect(await marpCli(['md.md', opt, '-o', '-'])).toBe(0)

// html option in a configuration file should not work
// html option in a configuration file should not work, and not allowed element should be escaped
const html = stdout.mock.calls[0][0].toString()
expect(html).toContain('&lt;b&gt;html&lt;/b&gt;')
expect(html).toContain(
'<b>html&lt;button&gt;button&lt;/button&gt;</b>'
)
}
} finally {
stdout.mockRestore()
Expand All @@ -1025,7 +1027,7 @@ describe('Marp CLI', () => {
expect(await marpCli(['md.md', '-o', '-'])).toBe(0)

const html = stdout.mock.calls[0][0].toString()
expect(html).toContain('@theme b')
expect(html).toContain('--theme-b')
} finally {
stdout.mockRestore()
warn.mockRestore()
Expand Down Expand Up @@ -1065,7 +1067,7 @@ describe('Marp CLI', () => {
)

const html = stdout.mock.calls[0][0].toString()
expect(html).toContain('@theme a')
expect(html).toContain('--theme-a')
} finally {
stdout.mockRestore()
warn.mockRestore()
Expand Down
24 changes: 19 additions & 5 deletions test/server.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import path from 'path'
import { ClientRequest } from 'node:http'
import path from 'node:path'
import Marp from '@marp-team/marp-core'
import { load } from 'cheerio'
import express from 'express'
import express, { type Express } from 'express'
import request from 'supertest'
import {
Converter,
Expand Down Expand Up @@ -105,7 +106,9 @@ describe('Server', () => {
})

describe('Routing', () => {
const setupServer = async (opts: Server.Options = {}): Promise<Server> => {
const setupServer = async (
opts: Server.Options = {}
): Promise<Server & { server: Express }> => {
const server: any = new Server(converter(), opts)

await server.setup() // Setup server without listening
Expand Down Expand Up @@ -264,11 +267,22 @@ describe('Server', () => {
})

describe('when the directory traversal attack is detected', () => {
it('returns 403', async () => {
it('returns 404', async () => {
const server = await setupServer()
const response = await request(server.server).get('/../../README.md')

expect(response.status).toBe(403)
// Current express is recognized directory traversal attack, and normalize request path to `/README.md`.
// So prevention logic of Marp CLI (returns 403) is not passed now.
// expect(response.status).toBe(403)
expect(response.status).toBe(404)
})

it('normalizes the request path that is trying directory traversal attack', async () => {
const server = await setupServer()
const response = await request(server.server).get('/../../4.txt')

expect((response.request.req as ClientRequest).path).toBe('/4.txt')
expect(response.status).toBe(200)
})
})
})
Expand Down
Loading

0 comments on commit ac600fa

Please sign in to comment.