mirror of
https://github.com/zhw2590582/ArtPlayer.git
synced 2026-10-08 19:06:15 -08:00
82 lines
3.6 KiB
JavaScript
82 lines
3.6 KiB
JavaScript
import { hash } from '../../refactor/scripts/releases.mjs'
|
|
import { thumbnailCandidate, thumbnailHistorical } from '../helpers/thumbnail.js'
|
|
import { expect, test } from './fixtures.js'
|
|
|
|
const candidate = await thumbnailCandidate()
|
|
|
|
for (const implementation of [...thumbnailHistorical(), candidate]) {
|
|
test(`Thumbnail ${implementation.name}: destroy preserves falsy listener exceptions with real DOM cleanup`, async ({ page }, testInfo) => {
|
|
await page.goto('/test/player.html?core=candidate&chapter=published')
|
|
await page.addScriptTag({ content: implementation.code })
|
|
const result = await page.evaluate(() => {
|
|
return [undefined, null, false, 0, -0, '', Number.NaN].map((failure, index) => {
|
|
const input = document.createElement('input')
|
|
input.type = 'file'
|
|
document.body.append(input)
|
|
const tool = new window.ArtplayerToolThumbnail({ fileInput: input })
|
|
let notified = 0
|
|
let threw = false
|
|
let same = false
|
|
tool.on('destroy', () => {
|
|
notified++
|
|
throw failure
|
|
})
|
|
try {
|
|
tool.destroy()
|
|
}
|
|
catch (error) {
|
|
threw = true
|
|
same = Object.is(error, failure)
|
|
}
|
|
const videoConnected = tool.video.isConnected
|
|
input.remove()
|
|
return { index, threw, same, notified, videoConnected }
|
|
})
|
|
})
|
|
await testInfo.attach('thumbnail-cleanup-errors', { contentType: 'application/json', body: JSON.stringify({ implementation: implementation.name, sha256: hash(implementation.code), result }) })
|
|
expect(result).toEqual(Array.from({ length: 7 }, (_, index) => ({ index, threw: true, same: true, notified: 1, videoConnected: false })))
|
|
})
|
|
}
|
|
|
|
test('Thumbnail native browser event registry handles special names and nested once without changing DOM cleanup', async ({ page }, testInfo) => {
|
|
await page.goto('/test/player.html?core=candidate&chapter=published')
|
|
await page.addScriptTag({ content: candidate.code })
|
|
const result = await page.evaluate(() => {
|
|
const input = document.createElement('input')
|
|
input.type = 'file'
|
|
document.body.append(input)
|
|
const tool = new window.ArtplayerToolThumbnail({ fileInput: input })
|
|
const keys = []
|
|
for (const name of ['__proto__', 'constructor', 'toString', 'hasOwnProperty']) {
|
|
let calls = 0
|
|
tool.emit(name)
|
|
const prototype = Object.getPrototypeOf(tool.e)
|
|
tool.on(name, () => calls++).once(name, () => calls++)
|
|
tool.emit(name).emit(name).off(name)
|
|
keys.push({ name, calls, prototypePreserved: Object.getPrototypeOf(tool.e) === prototype, removed: !Object.hasOwn(tool.e, name) })
|
|
}
|
|
let nested = false
|
|
const seen = []
|
|
tool.on('custom', (value) => {
|
|
if (!nested) {
|
|
nested = true
|
|
tool.emit('custom', 'inner')
|
|
}
|
|
seen.push(`on:${value}`)
|
|
})
|
|
tool.once('custom', value => seen.push(`once:${value}`))
|
|
tool.emit('custom', 'outer')
|
|
const video = tool.video
|
|
tool.destroy()
|
|
tool.destroy()
|
|
input.remove()
|
|
return { keys, seen, videoConnected: video.isConnected, inputConnected: input.isConnected, processing: tool.processing }
|
|
})
|
|
expect(result.keys).toEqual(['__proto__', 'constructor', 'toString', 'hasOwnProperty'].map(name => ({ name, calls: 3, prototypePreserved: true, removed: true })))
|
|
expect(result.seen).toEqual(['on:inner', 'once:inner', 'on:outer'])
|
|
expect(result.videoConnected).toBe(false)
|
|
expect(result.inputConnected).toBe(false)
|
|
expect(result.processing).toBe(false)
|
|
await testInfo.attach('thumbnail-emitter', { contentType: 'application/json', body: JSON.stringify({ candidate: candidate.name, sha256: hash(candidate.code), result }) })
|
|
})
|