@playwright/test
Advanced tools
Comparing version 1.12.0-next-1622757040000 to 1.12.0-next-1622928816000
@@ -21,6 +21,6 @@ { | ||
"name": "webkit", | ||
"revision": "1490", | ||
"revision": "1492", | ||
"installByDefault": true, | ||
"revisionOverrides": { | ||
"mac10.14": "1444" | ||
"mac10.14": "1445" | ||
} | ||
@@ -27,0 +27,0 @@ }, |
@@ -40,3 +40,3 @@ "use strict"; | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
exports.test = void 0; | ||
exports.__baseTest = exports.test = void 0; | ||
const fs = __importStar(require("fs")); | ||
@@ -46,3 +46,4 @@ const folio = __importStar(require("folio")); | ||
exports.test = folio.test.extend({ | ||
browserName: ['chromium', { scope: 'worker' }], | ||
defaultBrowserType: ['chromium', { scope: 'worker' }], | ||
browserName: [({ defaultBrowserType }, use) => use(defaultBrowserType), { scope: 'worker' }], | ||
playwright: [require('../inprocess'), { scope: 'worker' }], | ||
@@ -89,4 +90,4 @@ headless: [undefined, { scope: 'worker' }], | ||
contextOptions: {}, | ||
context: async ({ browserName, browser, screenshot, video, acceptDownloads, bypassCSP, colorScheme, deviceScaleFactor, extraHTTPHeaders, hasTouch, geolocation, httpCredentials, ignoreHTTPSErrors, isMobile, javaScriptEnabled, locale, offline, permissions, proxy, storageState, viewport, timezoneId, userAgent, contextOptions }, use, testInfo) => { | ||
testInfo.snapshotSuffix = browserName + '-' + process.platform; | ||
context: async ({ browser, screenshot, video, acceptDownloads, bypassCSP, colorScheme, deviceScaleFactor, extraHTTPHeaders, hasTouch, geolocation, httpCredentials, ignoreHTTPSErrors, isMobile, javaScriptEnabled, locale, offline, permissions, proxy, storageState, viewport, timezoneId, userAgent, contextOptions }, use, testInfo) => { | ||
testInfo.snapshotSuffix = process.platform; | ||
if (process.env.PWDEBUG) | ||
@@ -166,2 +167,3 @@ testInfo.setTimeout(0); | ||
exports.default = exports.test; | ||
exports.__baseTest = folio.test; | ||
//# sourceMappingURL=fixtures.js.map |
@@ -47,3 +47,3 @@ "use strict"; | ||
preserveOutput: process.env.CI ? 'failures-only' : 'always', | ||
reporter: [defaultReporter], | ||
reporter: [[defaultReporter]], | ||
timeout: defaultTimeout, | ||
@@ -105,14 +105,12 @@ updateSnapshots: process.env.CI ? 'none' : 'missing', | ||
async function runTests(Runner, args, opts) { | ||
if (opts.browser) { | ||
const browserOpt = opts.browser.toLowerCase(); | ||
if (!['all', 'chromium', 'firefox', 'webkit'].includes(browserOpt)) | ||
throw new Error(`Unsupported browser "${opts.browser}", must be one of "all", "chromium", "firefox" or "webkit"`); | ||
const browserNames = browserOpt === 'all' ? ['chromium', 'firefox', 'webkit'] : [browserOpt]; | ||
defaultConfig.projects = browserNames.map(browserName => { | ||
return { | ||
name: browserName, | ||
use: { browserName }, | ||
}; | ||
}); | ||
} | ||
const browserOpt = opts.browser ? opts.browser.toLowerCase() : 'chromium'; | ||
if (!['all', 'chromium', 'firefox', 'webkit'].includes(browserOpt)) | ||
throw new Error(`Unsupported browser "${opts.browser}", must be one of "all", "chromium", "firefox" or "webkit"`); | ||
const browserNames = browserOpt === 'all' ? ['chromium', 'firefox', 'webkit'] : [browserOpt]; | ||
defaultConfig.projects = browserNames.map(browserName => { | ||
return { | ||
name: browserName, | ||
use: { browserName }, | ||
}; | ||
}); | ||
const overrides = overridesFromOptions(opts); | ||
@@ -181,5 +179,3 @@ if (opts.headed) | ||
retries: options.retries ? parseInt(options.retries, 10) : undefined, | ||
reporter: (options.reporter && options.reporter.length) ? options.reporter.split(',').map((r) => { | ||
return builtinReporters.includes(r) ? r : { require: r }; | ||
}) : undefined, | ||
reporter: (options.reporter && options.reporter.length) ? options.reporter.split(',').map((r) => [r]) : undefined, | ||
shard: shardPair ? { current: shardPair[0] - 1, total: shardPair[1] } : undefined, | ||
@@ -186,0 +182,0 @@ timeout: isDebuggerAttached ? 0 : (options.timeout ? parseInt(options.timeout, 10) : undefined), |
@@ -65,2 +65,4 @@ "use strict"; | ||
this._session.on('Target.detachedFromTarget', this._onDetachedFromTarget.bind(this)); | ||
this._session.on('Browser.downloadWillBegin', this._onDownloadWillBegin.bind(this)); | ||
this._session.on('Browser.downloadProgress', this._onDownloadProgress.bind(this)); | ||
} | ||
@@ -185,2 +187,28 @@ static async connect(transport, options, devtools) { | ||
} | ||
_findOwningPage(frameId) { | ||
for (const crPage of this._crPages.values()) { | ||
const frame = crPage._page._frameManager.frame(frameId); | ||
if (frame) | ||
return crPage; | ||
} | ||
return null; | ||
} | ||
_onDownloadWillBegin(payload) { | ||
const page = this._findOwningPage(payload.frameId); | ||
utils_1.assert(page, 'Download started in unknown page: ' + JSON.stringify(payload)); | ||
page.willBeginDownload(); | ||
let originPage = page._initializedPage; | ||
// If it's a new window download, report it on the opener page. | ||
if (!originPage && page._opener) | ||
originPage = page._opener._initializedPage; | ||
if (!originPage) | ||
return; | ||
this._downloadCreated(originPage, payload.guid, payload.url, payload.suggestedFilename); | ||
} | ||
_onDownloadProgress(payload) { | ||
if (payload.state === 'completed') | ||
this._downloadFinished(payload.guid, ''); | ||
if (payload.state === 'canceled') | ||
this._downloadFinished(payload.guid, 'canceled'); | ||
} | ||
async _closePage(crPage) { | ||
@@ -253,7 +281,8 @@ await this._session.send('Target.closeTarget', { targetId: crPage._targetId }); | ||
const promises = [super._initialize()]; | ||
if (this._browser.options.name !== 'electron') { | ||
if (this._browser.options.name !== 'electron' && this._browser.options.name !== 'clank') { | ||
promises.push(this._browser._session.send('Browser.setDownloadBehavior', { | ||
behavior: this._options.acceptDownloads ? 'allowAndName' : 'deny', | ||
browserContextId: this._browserContextId, | ||
downloadPath: this._browser.options.downloadsPath | ||
downloadPath: this._browser.options.downloadsPath, | ||
eventsEnabled: true, | ||
})); | ||
@@ -260,0 +289,0 @@ } |
@@ -148,2 +148,5 @@ "use strict"; | ||
} | ||
willBeginDownload() { | ||
this._mainFrameSession._willBeginDownload(); | ||
} | ||
async pageOrError() { | ||
@@ -367,4 +370,2 @@ return this._pagePromise; | ||
helper_1.helper.addEventListener(this._client, 'Inspector.targetCrashed', event => this._onTargetCrashed()), | ||
helper_1.helper.addEventListener(this._client, 'Page.downloadWillBegin', event => this._onDownloadWillBegin(event)), | ||
helper_1.helper.addEventListener(this._client, 'Page.downloadProgress', event => this._onDownloadProgress(event)), | ||
helper_1.helper.addEventListener(this._client, 'Page.screencastFrame', event => this._onScreencastFrame(event)), | ||
@@ -733,5 +734,4 @@ helper_1.helper.addEventListener(this._client, 'Page.windowOpen', event => this._onWindowOpen(event)), | ||
} | ||
_onDownloadWillBegin(payload) { | ||
let originPage = this._crPage._initializedPage; | ||
// If it's a new window download, report it on the opener page. | ||
_willBeginDownload() { | ||
const originPage = this._crPage._initializedPage; | ||
if (!originPage) { | ||
@@ -741,15 +741,4 @@ // Resume the page creation with an error. The page will automatically close right | ||
this._firstNonInitialNavigationCommittedReject(new Error('Starting new page download')); | ||
if (this._crPage._opener) | ||
originPage = this._crPage._opener._initializedPage; | ||
} | ||
if (!originPage) | ||
return; | ||
this._crPage._browserContext._browser._downloadCreated(originPage, payload.guid, payload.url, payload.suggestedFilename); | ||
} | ||
_onDownloadProgress(payload) { | ||
if (payload.state === 'completed') | ||
this._crPage._browserContext._browser._downloadFinished(payload.guid, ''); | ||
if (payload.state === 'canceled') | ||
this._crPage._browserContext._browser._downloadFinished(payload.guid, 'canceled'); | ||
} | ||
_onScreencastFrame(payload) { | ||
@@ -756,0 +745,0 @@ this._client.send('Page.screencastFrameAck', { sessionId: payload.sessionId }).catch(() => { }); |
@@ -90,3 +90,3 @@ "use strict"; | ||
// Something went wrong -> bail out, our snapshots are best-efforty. | ||
if (!data) | ||
if (!data || !this._started) | ||
return; | ||
@@ -93,0 +93,0 @@ const snapshot = { |
@@ -19,3 +19,3 @@ "use strict"; | ||
exports.metadataToCallLog = void 0; | ||
function metadataToCallLog(metadata, status, snapshots) { | ||
function metadataToCallLog(metadata, status) { | ||
var _a, _b; | ||
@@ -42,7 +42,2 @@ const title = metadata.apiName || metadata.method; | ||
duration, | ||
snapshots: { | ||
before: showBeforeSnapshot(metadata) && snapshots.has(`before@${metadata.id}`), | ||
action: showActionSnapshot(metadata) && snapshots.has(`action@${metadata.id}`), | ||
after: showAfterSnapshot(metadata) && snapshots.has(`after@${metadata.id}`), | ||
} | ||
}; | ||
@@ -52,11 +47,2 @@ return callLog; | ||
exports.metadataToCallLog = metadataToCallLog; | ||
function showBeforeSnapshot(metadata) { | ||
return metadata.method === 'close'; | ||
} | ||
function showActionSnapshot(metadata) { | ||
return ['click', 'dblclick', 'check', 'uncheck', 'fill', 'press'].includes(metadata.method); | ||
} | ||
function showAfterSnapshot(metadata) { | ||
return ['goto', 'click', 'dblclick', 'dblclick', 'check', 'uncheck', 'fill', 'press'].includes(metadata.method); | ||
} | ||
//# sourceMappingURL=recorderUtils.js.map |
@@ -53,3 +53,2 @@ "use strict"; | ||
const utils_2 = require("../../utils/utils"); | ||
const inMemorySnapshotter_1 = require("../snapshot/inMemorySnapshotter"); | ||
const recorderUtils_1 = require("./recorder/recorderUtils"); | ||
@@ -69,3 +68,2 @@ const debugger_1 = require("./debugger"); | ||
this._userSources = new Map(); | ||
this._snapshots = new Set(); | ||
this._allMetadatas = new Map(); | ||
@@ -122,3 +120,2 @@ this._context = context; | ||
this._generator = generator; | ||
this._snapshotter = new inMemorySnapshotter_1.InMemorySnapshotter(context); | ||
} | ||
@@ -141,3 +138,3 @@ static showInspector(context) { | ||
recorderApp.once('close', () => { | ||
this._snapshotter.dispose().catch(() => { }); | ||
this._debugger.resume(false); | ||
this._recorderApp = null; | ||
@@ -156,9 +153,2 @@ }); | ||
} | ||
if (data.event === 'callLogHovered') { | ||
this._hoveredSnapshot = undefined; | ||
if (this._debugger.isPaused() && data.params.callLogId) | ||
this._hoveredSnapshot = data.params; | ||
this._refreshOverlay(); | ||
return; | ||
} | ||
if (data.event === 'step') { | ||
@@ -201,16 +191,8 @@ this._debugger.resume(true); | ||
await this._context.exposeBinding('_playwrightRecorderState', false, source => { | ||
let snapshotUrl; | ||
let actionSelector = this._highlightedSelector; | ||
let actionPoint; | ||
if (this._hoveredSnapshot) { | ||
const metadata = this._allMetadatas.get(this._hoveredSnapshot.callLogId); | ||
snapshotUrl = `${metadata.pageId}?name=${this._hoveredSnapshot.phase}@${this._hoveredSnapshot.callLogId}`; | ||
actionPoint = this._hoveredSnapshot.phase === 'action' ? metadata === null || metadata === void 0 ? void 0 : metadata.point : undefined; | ||
} | ||
else { | ||
for (const [metadata, sdkObject] of this._currentCallsMetadata) { | ||
if (source.page === sdkObject.attribution.page) { | ||
actionPoint = metadata.point || actionPoint; | ||
actionSelector = actionSelector || metadata.params.selector; | ||
} | ||
for (const [metadata, sdkObject] of this._currentCallsMetadata) { | ||
if (source.page === sdkObject.attribution.page) { | ||
actionPoint = metadata.point || actionPoint; | ||
actionSelector = actionSelector || metadata.params.selector; | ||
} | ||
@@ -222,3 +204,2 @@ } | ||
actionSelector, | ||
snapshotUrl, | ||
}; | ||
@@ -236,4 +217,3 @@ return uiState; | ||
}, 'main'); | ||
const snapshotBaseUrl = await this._snapshotter.initialize() + '/snapshot/'; | ||
await this._context.extendInjectedScript('utility', recorderSource.source, { isUnderTest: utils_2.isUnderTest(), snapshotBaseUrl }); | ||
await this._context.extendInjectedScript('utility', recorderSource.source, { isUnderTest: utils_2.isUnderTest() }); | ||
await this._context.extendInjectedScript('main', consoleApiSource.source); | ||
@@ -246,2 +226,3 @@ if (this._debugger.isPaused()) | ||
_pausedStateChanged() { | ||
var _a; | ||
// If we are called upon page.pause, we don't have metadatas, populate them. | ||
@@ -252,3 +233,3 @@ for (const { metadata, sdkObject } of this._debugger.pausedDetails()) { | ||
} | ||
this._recorderApp.setPaused(this._debugger.isPaused()); | ||
(_a = this._recorderApp) === null || _a === void 0 ? void 0 : _a.setPaused(this._debugger.isPaused()); | ||
this._updateUserSources(); | ||
@@ -381,9 +362,2 @@ this.updateCallLog([...this._currentCallsMetadata.keys()]); | ||
} | ||
_captureSnapshot(sdkObject, metadata, phase) { | ||
if (sdkObject.attribution.page) { | ||
const snapshotName = `${phase}@${metadata.id}`; | ||
this._snapshots.add(snapshotName); | ||
this._snapshotter.captureSnapshot(sdkObject.attribution.page, snapshotName); | ||
} | ||
} | ||
async onBeforeCall(sdkObject, metadata) { | ||
@@ -393,3 +367,2 @@ var _a; | ||
return; | ||
this._captureSnapshot(sdkObject, metadata, 'before'); | ||
this._currentCallsMetadata.set(metadata, sdkObject); | ||
@@ -407,3 +380,2 @@ this._allMetadatas.set(metadata.id, metadata); | ||
return; | ||
this._captureSnapshot(sdkObject, metadata, 'after'); | ||
if (!metadata.error) | ||
@@ -448,5 +420,2 @@ this._currentCallsMetadata.delete(metadata); | ||
async onBeforeInputAction(sdkObject, metadata) { | ||
if (this._mode === 'recording') | ||
return; | ||
this._captureSnapshot(sdkObject, metadata, 'action'); | ||
} | ||
@@ -469,3 +438,3 @@ async onCallLog(logName, message, sdkObject, metadata) { | ||
status = 'paused'; | ||
logs.push(recorderUtils_1.metadataToCallLog(metadata, status, this._snapshots)); | ||
logs.push(recorderUtils_1.metadataToCallLog(metadata, status)); | ||
} | ||
@@ -472,0 +441,0 @@ (_a = this._recorderApp) === null || _a === void 0 ? void 0 : _a.updateCallLogs(logs); |
@@ -43,2 +43,3 @@ "use strict"; | ||
await this._snapshotter.stop(); | ||
await this._writeArtifactChain; | ||
} | ||
@@ -45,0 +46,0 @@ async dispose() { |
@@ -45,4 +45,2 @@ "use strict"; | ||
// context + page must be the first events added, this method can't have awaits before them. | ||
if (!this._tracesDir) | ||
throw new Error('Tracing directory is not specified when launching the browser'); | ||
if (this._started) | ||
@@ -72,3 +70,2 @@ throw new Error('Tracing has already been started'); | ||
this._started = false; | ||
await this._snapshotter.stop(); | ||
this._context.instrumentation.removeListener(this); | ||
@@ -80,2 +77,3 @@ helper_1.helper.removeEventListeners(this._eventListeners); | ||
page.setScreencastOptions(null); | ||
await this._snapshotter.stop(); | ||
// Ensure all writes are finished. | ||
@@ -88,17 +86,20 @@ await this._appendEventChain; | ||
async export() { | ||
if (!this._traceFile) | ||
throw new Error('Tracing directory is not specified when launching the browser'); | ||
if (!this._traceFile || this._started) | ||
throw new Error('Must start and stop tracing before exporting'); | ||
const zipFile = new yazl_1.default.ZipFile(); | ||
zipFile.addFile(this._traceFile, 'trace.trace'); | ||
const zipFileName = this._traceFile + '.zip'; | ||
this._traceFile = undefined; | ||
for (const sha1 of this._sha1s) | ||
zipFile.addFile(path_1.default.join(this._resourcesDir, sha1), path_1.default.join('resources', sha1)); | ||
zipFile.end(); | ||
await new Promise(f => { | ||
zipFile.outputStream.pipe(fs_1.default.createWriteStream(zipFileName)).on('close', f); | ||
const failedPromise = new Promise((_, reject) => zipFile.on('error', reject)); | ||
const succeededPromise = new Promise(async (fulfill) => { | ||
zipFile.addFile(this._traceFile, 'trace.trace'); | ||
const zipFileName = this._traceFile + '.zip'; | ||
for (const sha1 of this._sha1s) | ||
zipFile.addFile(path_1.default.join(this._resourcesDir, sha1), path_1.default.join('resources', sha1)); | ||
zipFile.end(); | ||
await new Promise(f => { | ||
zipFile.outputStream.pipe(fs_1.default.createWriteStream(zipFileName)).on('close', f); | ||
}); | ||
const artifact = new artifact_1.Artifact(this._context, zipFileName); | ||
artifact.reportFinished(); | ||
fulfill(artifact); | ||
}); | ||
const artifact = new artifact_1.Artifact(this._context, zipFileName); | ||
artifact.reportFinished(); | ||
return artifact; | ||
return Promise.race([failedPromise, succeededPromise]); | ||
} | ||
@@ -157,2 +158,4 @@ async _captureSnapshot(name, sdkObject, metadata, element) { | ||
_appendTraceEvent(event) { | ||
if (!this._started) | ||
return; | ||
const visit = (object) => { | ||
@@ -159,0 +162,0 @@ if (Array.isArray(object)) { |
@@ -46,2 +46,3 @@ "use strict"; | ||
'playwright-webkit', | ||
path_1.default.join('@playwright', 'test'), | ||
].map(packageName => path_1.default.sep + path_1.default.join(packageName, 'lib')); | ||
@@ -48,0 +49,0 @@ function captureStackTrace() { |
{ | ||
"name": "@playwright/test", | ||
"version": "1.12.0-next-1622757040000", | ||
"version": "1.12.0-next-1622928816000", | ||
"description": "Playwright Test Runner", | ||
@@ -43,4 +43,4 @@ "repository": "github:Microsoft/playwright", | ||
"yazl": "^2.5.1", | ||
"folio": "=0.4.0-alpha26" | ||
"folio": "=0.4.0-alpha28" | ||
} | ||
} |
@@ -75,2 +75,3 @@ /** | ||
browserName: BrowserName; | ||
defaultBrowserType: BrowserName; | ||
@@ -77,0 +78,0 @@ /** |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is too big to display
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
7440399
127752
21
Updatedfolio@=0.4.0-alpha28