ui5-test-runner
Version:
Standalone test runner for UI5
184 lines (174 loc) • 5 kB
JavaScript
const { start } = require('./browsers')
const { instrument } = require('./coverage')
const { globallyTimedOut } = require('./timeout')
const { save, generate } = require('./report')
const { getOutput } = require('./output')
const {
$statusProgressTotal,
$statusProgressCount,
$proxifiedUrls
} = require('./symbols')
const { UTRError } = require('./error')
const { parallelize } = require('./parallelize')
function task (job, method) {
return async (url, index, { length }) => {
if (job[$statusProgressCount] === undefined) {
job[$statusProgressCount] = 0
}
job[$statusProgressTotal] = length
const output = getOutput(job)
if (globallyTimedOut(job)) {
output.globalTimeout(url)
job.failed = true
job.timedOut = true
} else if (job.failFast && job.failed) {
output.failFast(url)
} else {
try {
await method(job, url)
} catch (error) {
job.failed = true
}
}
++job[$statusProgressCount]
}
}
async function probeUrl (job, url) {
const parsedUrl = new URL(url)
if (parsedUrl.port === '0') {
parsedUrl.port = job.port
url = parsedUrl.toString()
}
const output = getOutput(job)
try {
let scripts
if (job.browserCapabilities.scripts) {
scripts = [
'(function () { window[\'ui5-test-runner/probe\'] = true }())',
'post.js',
'qunit-redirect.js'
]
if (job.jest) {
scripts.push('jest2qunit.js')
}
}
await start(job, url, scripts)
} catch (error) {
output.startFailed(url, error)
throw error
}
}
async function runTestPage (job, url) {
const output = getOutput(job)
try {
let scripts
if (job.browserCapabilities.scripts) {
scripts = []
if (job.qunitBatchSize) {
scripts.push(
`(function () { window['ui5-test-runner/batch'] = ${job.qunitBatchSize} }())`
)
}
scripts.push(
'post.js',
'qunit-hooks.js'
)
if (job.jest) {
scripts.push('jest2qunit.js')
}
if (job.coverage && !job.coverageProxy) {
scripts.push(
'opa-iframe-coverage.js',
'ui5-coverage.js' // TODO detect if middleware exists before injecting this
)
}
}
if (job.coverageProxy) {
const { origin } = new URL(url)
const proxifiedUrl = url.replace(origin, `http://localhost:${job.port}`)
if (!job[$proxifiedUrls]) {
job[$proxifiedUrls] = {}
}
job[$proxifiedUrls][proxifiedUrl] = url
await start(job, proxifiedUrl, scripts)
job.qunitPages[url] = job.qunitPages[proxifiedUrl]
delete job.qunitPages[proxifiedUrl]
} else {
await start(job, url, scripts)
}
} catch (error) {
output.startFailed(url, error)
throw error
}
}
async function process (job) {
const output = getOutput(job)
job.start = new Date()
job.failed = false
await instrument(job)
await save(job)
job.testPageUrls = []
let probingRound = 0
const parallel = job.probeParallel || job.parallel
const confirmedTestPageUrls = []
job.status = 'Probing urls'
do {
++probingRound
if (probingRound >= 2) {
if (job.testPageUrls.length === 0) {
break
}
job.status = `Probing urls (${probingRound})`
job.url = job.testPageUrls.filter(url => !confirmedTestPageUrls.includes(url))
if (job.url.length) {
job.testPageUrls = []
} else {
job.testPageUrls = confirmedTestPageUrls
break
}
}
try {
await parallelize(task(job, probeUrl), job.url, parallel)
} catch (e) {
output.genericError(e)
job.failed = true
break
}
job.testPageUrls.forEach(url => {
if ((job.url.includes(url) && !confirmedTestPageUrls.includes(url)) ||
(url.includes('/resources/sap/ui/test/starter/Test.qunit.html?testsuite=') && url.includes('&test='))
) {
confirmedTestPageUrls.push(url)
getOutput(job).debug('probe', 'confirmed:', url)
}
})
getOutput(job).debug('probe', 'from', job.url.length, 'to', job.testPageUrls.length, 'confirmed', confirmedTestPageUrls.length)
} while (job.deepProbe)
/* istanbul ignore else */
if (!job.debugProbeOnly && !job.failed) {
if (job.testPageUrls.length !== 0) {
job.status = 'Executing test pages'
try {
await parallelize(task(job, runTestPage), job.testPageUrls, job.parallel)
} catch (e) {
output.genericError(e)
job.failed = true
}
} else if (Object.keys(job.qunitPages || []).length === 0) {
output.noTestPageFound()
job.failed = true
}
}
await generate(job)
}
module.exports = {
async execute (job) {
if (job.mode !== 'url') {
job.url = [`http://${job.localhost}:${job.port}/${job.testsuite}`]
} else if (!job.browserCapabilities.scripts) {
throw UTRError.BROWSER_MISS_SCRIPTS_CAPABILITY()
}
return process(job)
}
}