Skip to content

Commit

Permalink
Refactor resolution of browser manager configuration
Browse files Browse the repository at this point in the history
  • Loading branch information
yhatt committed Sep 25, 2024
1 parent cfd5e4b commit 8a1e878
Show file tree
Hide file tree
Showing 3 changed files with 65 additions and 52 deletions.
36 changes: 20 additions & 16 deletions src/config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,9 @@ import path from 'node:path'
import chalk from 'chalk'
import { cosmiconfig, cosmiconfigSync } from 'cosmiconfig'
import { osLocale } from 'os-locale'
import { BrowserManager } from './browser/manager'
import type { BrowserManagerConfig } from './browser/manager'
import { info, warn, error as cliError } from './cli'
import { ConverterOption, ConvertType } from './converter'
import { ConvertType, type ConverterOption } from './converter'
import { ResolvableEngine, ResolvedEngine } from './engine'
import { keywordsAsArray } from './engine/meta-plugin'
import { error, isError } from './error'
Expand Down Expand Up @@ -116,7 +116,23 @@ export class MarpCLIConfig {

private constructor() {} // eslint-disable-line @typescript-eslint/no-empty-function

async converterOption(): Promise<ConverterOption> {
browserManagerOption() {
const timeout = (() => {
// TODO: Resolve timeout from args and configuration file
if (process.env.PUPPETEER_TIMEOUT) {
const envTimeout = Number.parseInt(process.env.PUPPETEER_TIMEOUT, 10)
if (!Number.isNaN(envTimeout)) return envTimeout
}
return undefined
})()

return {
protocol: 'cdp',
timeout,
} as const satisfies BrowserManagerConfig
}

async converterOption() {
const inputDir = await this.inputDir()
const server = this.args.server ?? this.conf.server ?? false
const output = (() => {
Expand Down Expand Up @@ -255,19 +271,7 @@ export class MarpCLIConfig {
return scale
})()

const browserManager = new BrowserManager({
protocol: 'cdp',
timeout: (() => {
if (process.env.PUPPETEER_TIMEOUT) {
const envTimeout = Number.parseInt(process.env.PUPPETEER_TIMEOUT, 10)
if (!Number.isNaN(envTimeout)) return envTimeout
}
return undefined
})(),
})

return {
browserManager,
imageScale,
inputDir,
output,
Expand Down Expand Up @@ -298,7 +302,7 @@ export class MarpCLIConfig {
options: this.conf.options || {},
pages: !!(this.args.images || this.conf.images),
watch: (this.args.watch ?? this.conf.watch) || preview || server || false,
}
} as const satisfies Partial<ConverterOption>
}

get files() {
Expand Down
11 changes: 8 additions & 3 deletions src/marp-cli.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import chalk from 'chalk'
import type { BrowserManager } from './browser/manager'
import { BrowserManager } from './browser/manager'
import * as cli from './cli'
import { fromArguments } from './config'
import { Converter, ConvertedCallback, ConvertType } from './converter'
Expand Down Expand Up @@ -296,10 +296,15 @@ export const marpCli = async (
const config = await fromArguments(args)
if (args.version) return await version(config)

// Initialize browser manager
browserManager = new BrowserManager(config.browserManagerOption())

// Initialize converter
const converter = new Converter(await config.converterOption())
const converter = new Converter({
...(await config.converterOption()),
browserManager,
})
const cvtOpts = converter.options
browserManager = cvtOpts.browserManager

// Find target markdown files
const finder = async (): Promise<File[]> => {
Expand Down
70 changes: 37 additions & 33 deletions test/converter.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { imageSize } from 'image-size'
import { PDFDocument, PDFDict, PDFName, PDFHexString, PDFNumber } from 'pdf-lib'
import { TimeoutError } from 'puppeteer-core'
import { fromBuffer as yauzlFromBuffer } from 'yauzl'
import { BrowserManager } from '../src/browser/manager'
import { Converter, ConvertType, ConverterOption } from '../src/converter'
import { CLIError } from '../src/error'
import { File, FileType } from '../src/file'
Expand All @@ -19,7 +20,7 @@ import { WatchNotifier } from '../src/watcher'

const { CdpPage } = require('puppeteer-core/lib/cjs/puppeteer/cdp/Page') // eslint-disable-line @typescript-eslint/no-require-imports -- Puppeteer's internal module

const puppeteerTimeoutMs = 60000
const timeout = 60000

let mkdirSpy: jest.SpiedFunction<typeof fs.promises.mkdir>

Expand All @@ -30,18 +31,27 @@ beforeEach(() => {
})

afterEach(() => mkdirSpy.mockRestore())
afterAll(() => Converter.closeBrowser())

describe('Converter', () => {
const onePath = path.resolve(__dirname, '_files/1.md')
const twoPath = path.resolve(__dirname, '_files/2.mdown')
const threePath = path.resolve(__dirname, '_files/3.markdown')

let browserManager: BrowserManager
let themeSet: ThemeSet
beforeEach(async () => (themeSet = await ThemeSet.initialize([])))

beforeEach(async () => {
browserManager = new BrowserManager({ timeout })
themeSet = await ThemeSet.initialize([])
})

afterEach(async () => {
await browserManager.dispose()
})

const instance = (opts: Partial<ConverterOption> = {}) =>
new Converter({
browserManager,
themeSet,
allowLocalFiles: false,
engine: Marp,
Expand All @@ -57,8 +67,11 @@ describe('Converter', () => {
})

describe('#constructor', () => {
it('assigns initial options to options member', () => {
it('assigns initial options to options member', async () => {
await using browserManager = new BrowserManager({ timeout: 12345 })

const options = {
browserManager,
themeSet,
allowLocalFiles: true,
engine: Marp,
Expand Down Expand Up @@ -88,17 +101,6 @@ describe('Converter', () => {
})
})

describe('get #puppeteerTimeout', () => {
it('returns specified timeout', () => {
expect(instance({ puppeteerTimeout: 1000 }).puppeteerTimeout).toBe(1000)
expect(instance({ puppeteerTimeout: 0 }).puppeteerTimeout).toBe(0)
})

it('returns the default timeout 30000ms if not specified', () => {
expect(instance().puppeteerTimeout).toBe(30000)
})
})

describe('#convert', () => {
const md = '# <i>Hello!</i>'
const dummyFile = new File(process.cwd())
Expand Down Expand Up @@ -555,7 +557,7 @@ describe('Converter', () => {
expect(ret.newFile?.path).toBe('test.pdf')
expect(ret.newFile?.buffer).toBe(pdf)
},
puppeteerTimeoutMs
timeout
)

describe('with meta global directives', () => {
Expand All @@ -581,7 +583,7 @@ describe('Converter', () => {
expect(pdf.getAuthor()).toBe('author')
expect(pdf.getKeywords()).toBe('a; b; c')
},
puppeteerTimeoutMs
timeout
)
})

Expand Down Expand Up @@ -624,7 +626,7 @@ describe('Converter', () => {
warn.mockRestore()
}
},
puppeteerTimeoutMs
timeout
)
})

Expand All @@ -651,7 +653,7 @@ describe('Converter', () => {
PDFHexString.fromText('presenter note')
)
},
puppeteerTimeoutMs
timeout
)

it('sets a comment author to notes if set author global directive', async () => {
Expand Down Expand Up @@ -788,7 +790,7 @@ describe('Converter', () => {
]
`)
},
puppeteerTimeoutMs
timeout
)
})

Expand Down Expand Up @@ -833,7 +835,7 @@ describe('Converter', () => {
]
`)
},
puppeteerTimeoutMs
timeout
)
})

Expand Down Expand Up @@ -898,19 +900,21 @@ describe('Converter', () => {
]
`)
},
puppeteerTimeoutMs
timeout
)
})
})

describe('with custom puppeteer timeout', () => {
describe('with custom timeout set by browser manager', () => {
it('follows setting timeout', async () => {
;(fs as any).__mockWriteFile()

await using browserManager = new BrowserManager({ timeout: 1 })

await expect(
pdfInstance({
browserManager,
output: 'test.pdf',
puppeteerTimeout: 1,
}).convertFile(new File(onePath))
).rejects.toThrow(TimeoutError)
})
Expand Down Expand Up @@ -990,7 +994,7 @@ describe('Converter', () => {
const meta = await getPptxDocProps(pptx)
expect(meta['dc:creator']).toBe('Created by Marp')
},
puppeteerTimeoutMs
timeout
)

describe('with meta global directives', () => {
Expand Down Expand Up @@ -1020,7 +1024,7 @@ describe('Converter', () => {
expect.objectContaining({ deviceScaleFactor: 1 })
)
},
puppeteerTimeoutMs
timeout
)
})
})
Expand Down Expand Up @@ -1050,7 +1054,7 @@ describe('Converter', () => {
expect(width).toBe(1280)
expect(height).toBe(720)
},
puppeteerTimeoutMs
timeout
)

describe('with 4:3 size global directive for Marp Core', () => {
Expand All @@ -1069,7 +1073,7 @@ describe('Converter', () => {
expect(width).toBe(960)
expect(height).toBe(720)
},
puppeteerTimeoutMs
timeout
)
})

Expand All @@ -1090,7 +1094,7 @@ describe('Converter', () => {
expect(width).toBe(640)
expect(height).toBe(360)
},
puppeteerTimeoutMs
timeout
)
})
})
Expand Down Expand Up @@ -1121,7 +1125,7 @@ describe('Converter', () => {
expect(width).toBe(1280)
expect(height).toBe(720)
},
puppeteerTimeoutMs
timeout
)

describe('with 4:3 size global directive for Marp Core', () => {
Expand All @@ -1141,7 +1145,7 @@ describe('Converter', () => {
expect(width).toBe(960)
expect(height).toBe(720)
},
puppeteerTimeoutMs
timeout
)
})

Expand All @@ -1162,7 +1166,7 @@ describe('Converter', () => {
expect(width).toBe(640)
expect(height).toBe(360)
},
puppeteerTimeoutMs
timeout
)
})
})
Expand All @@ -1189,7 +1193,7 @@ describe('Converter', () => {
expect(write.mock.calls[0][0]).toBe('c.001.png')
expect(write.mock.calls[1][0]).toBe('c.002.png')
},
puppeteerTimeoutMs
timeout
)
})

Expand Down

0 comments on commit 8a1e878

Please sign in to comment.