diff --git a/lib/FrameManager.js b/lib/FrameManager.js index 3f26fb9d025..051f2ce398b 100644 --- a/lib/FrameManager.js +++ b/lib/FrameManager.js @@ -173,10 +173,10 @@ class FrameManager extends EventEmitter { } /** - * @return {boolean} + * @return {?string} */ - isMainFrameLoadingFailed() { - return !!this._mainFrame._loadingFailed; + unreachableMainFrameURL() { + return this._mainFrame._unreachableURL || null; } } @@ -477,7 +477,7 @@ class Frame { _navigated(framePayload) { this._name = framePayload.name; this._url = framePayload.url; - this._loadingFailed = !!framePayload.unreachableUrl; + this._unreachableURL = framePayload.unreachableUrl; } _detach() { diff --git a/lib/NavigatorWatcher.js b/lib/NavigatorWatcher.js index f76e0086d18..f6e92ea34d5 100644 --- a/lib/NavigatorWatcher.js +++ b/lib/NavigatorWatcher.js @@ -20,16 +20,14 @@ class NavigatorWatcher { /** * @param {!Puppeteer.Session} client * @param {string} frameId - * @param {boolean} ignoreHTTPSErrors * @param {!Object=} options */ - constructor(client, frameId, ignoreHTTPSErrors, options = {}) { + constructor(client, frameId, options = {}) { console.assert(options.networkIdleTimeout === undefined, 'ERROR: networkIdleTimeout option is no longer supported.'); console.assert(options.networkIdleInflight === undefined, 'ERROR: networkIdleInflight option is no longer supported.'); console.assert(options.waitUntil !== 'networkidle', 'ERROR: "networkidle" option is no longer supported. Use "networkidle2" instead'); this._client = client; this._frameId = frameId; - this._ignoreHTTPSErrors = ignoreHTTPSErrors; this._timeout = typeof options.timeout === 'number' ? options.timeout : 30000; let waitUntil = ['load']; if (Array.isArray(options.waitUntil)) @@ -56,13 +54,6 @@ class NavigatorWatcher { navigationPromises.push(watchdog); } - if (!this._ignoreHTTPSErrors) { - const certificateError = new Promise(fulfill => { - this._eventListeners.push(helper.addEventListener(this._client, 'Security.certificateError', fulfill)); - }).then(error => 'SSL Certificate error: ' + error.errorType); - navigationPromises.push(certificateError); - } - this._eventListeners.push(helper.addEventListener(this._client, 'Page.lifecycleEvent', this._onLifecycleEvent.bind(this))); const pendingEventsFired = new Promise(fulfill => this._pendingEventsCallback = fulfill); navigationPromises.push(pendingEventsFired); diff --git a/lib/Page.js b/lib/Page.js index 6f56f9f9ad4..27a7e21bb4d 100644 --- a/lib/Page.js +++ b/lib/Page.js @@ -457,9 +457,9 @@ class Page extends EventEmitter { */ async goto(url, options) { const mainFrame = this._frameManager.mainFrame(); - const watcher = new NavigatorWatcher(this._client, mainFrame._id, this._ignoreHTTPSErrors, options); - const responses = new Map(); - const listener = helper.addEventListener(this._networkManager, NetworkManager.Events.Response, response => responses.set(response.url, response)); + const watcher = new NavigatorWatcher(this._client, mainFrame._id, options); + const requests = new Map(); + const listener = helper.addEventListener(this._networkManager, NetworkManager.Events.Request, request => requests.set(request.url, request)); const navigationPromise = watcher.waitForNavigation(); const referrer = this._networkManager.extraHTTPHeaders()['referer']; @@ -475,9 +475,14 @@ class Page extends EventEmitter { helper.removeEventListeners([listener]); if (error) throw error; - if (this._frameManager.isMainFrameLoadingFailed()) - throw new Error('Failed to navigate: ' + url); - return responses.get(this.mainFrame().url()) || null; + const unreachableURL = this._frameManager.unreachableMainFrameURL(); + if (unreachableURL) { + const request = requests.get(unreachableURL) || null; + const failure = request ? request.failure() : null; + throw new Error('Failed to navigate: ' + url + (failure ? ' ' + failure.errorText : '')); + } + const request = requests.get(this.mainFrame().url()); + return request ? request.response() : null; } /** @@ -498,7 +503,7 @@ class Page extends EventEmitter { */ async waitForNavigation(options) { const mainFrame = this._frameManager.mainFrame(); - const watcher = new NavigatorWatcher(this._client, mainFrame._id, this._ignoreHTTPSErrors, options); + const watcher = new NavigatorWatcher(this._client, mainFrame._id, options); const responses = new Map(); const listener = helper.addEventListener(this._networkManager, NetworkManager.Events.Response, response => responses.set(response.url, response)); diff --git a/test/test.js b/test/test.js index 5f98ee573db..68fc73ecd00 100644 --- a/test/test.js +++ b/test/test.js @@ -89,7 +89,7 @@ afterAll(SX(async function() { describe('Puppeteer', function() { describe('Puppeteer.launch', function() { - xit('should support ignoreHTTPSErrors option', SX(async function() { + it('should support ignoreHTTPSErrors option', SX(async function() { const options = Object.assign({ignoreHTTPSErrors: true}, defaultBrowserOptions); const browser = await puppeteer.launch(options); const page = await browser.newPage(); @@ -909,7 +909,14 @@ describe('Page', function() { page.on('requestfailed', request => expect(request).toBeTruthy()); let error = null; await page.goto(HTTPS_PREFIX + '/empty.html').catch(e => error = e); - expect(error.message).toContain('SSL Certificate error'); + expect(error.message).toContain('net::ERR_INSECURE_RESPONSE'); + })); + it('should fail when navigating to bad SSL after redirects', SX(async function() { + server.setRedirect('/redirect/1.html', '/redirect/2.html'); + server.setRedirect('/redirect/2.html', '/empty.html'); + let error = null; + await page.goto(HTTPS_PREFIX + '/redirect/1.html').catch(e => error = e); + expect(error.message).toContain('net::ERR_INSECURE_RESPONSE'); })); it('should throw if networkidle is passed as an option', SX(async function() { let error = null;