@@ -76,10 +76,12 @@ export class AbstractExtendedWebDriver extends AbstractWebDriver {
76
76
* `ElementFinder` will be unwrapped to their underlying `WebElement` instance
77
77
*
78
78
* @private
79
- * @param {Object } to
80
- * @param {Object } from
81
- * @param {string } fnName
82
- * @param {function= } setupFn
79
+ * @param {Object } to The object to copy a function to
80
+ * @param {string|Object } from Where to get the function from. If an object, the object containing
81
+ * the function to copy over. If a string, the name of a property on `to` which is an object
82
+ * containing the function.
83
+ * @param {string } fnName The name of the function to copy
84
+ * @param {function= } setupFn An optional function to run before the copied function
83
85
*/
84
86
function ptorMixin ( to : any , from : any , fnName : string , setupFn ?: Function ) {
85
87
to [ fnName ] = function ( ) {
@@ -91,7 +93,8 @@ function ptorMixin(to: any, from: any, fnName: string, setupFn?: Function) {
91
93
if ( setupFn ) {
92
94
setupFn ( ) ;
93
95
}
94
- return from [ fnName ] . apply ( from , arguments ) ;
96
+ let fromObj = typeof from === 'string' ? to [ from ] : from ;
97
+ return fromObj [ fnName ] . apply ( fromObj , arguments ) ;
95
98
} ;
96
99
} ;
97
100
@@ -236,9 +239,11 @@ export class ProtractorBrowser extends AbstractExtendedWebDriver {
236
239
params : any ;
237
240
238
241
/**
239
- * Set by the runner.
242
+ * Resolved when the browser is ready for use
243
+ *
244
+ * Set partially by `setDriver_()`, partially by the runner.
240
245
*
241
- * @type {q. Promise } Done when the new browser is ready for use
246
+ * @type {webdriver.promise. Promise }
242
247
*/
243
248
ready : wdpromise . Promise < any > ;
244
249
@@ -306,31 +311,24 @@ export class ProtractorBrowser extends AbstractExtendedWebDriver {
306
311
webdriverInstance : WebDriver , opt_baseUrl ?: string , opt_rootElement ?: string ,
307
312
opt_untrackOutstandingTimeouts ?: boolean , opt_blockingProxyUrl ?: string ) {
308
313
super ( ) ;
314
+ this . setDriver_ ( webdriverInstance ) ;
315
+
309
316
// These functions should delegate to the webdriver instance, but should
310
317
// wait for Angular to sync up before performing the action. This does not
311
318
// include functions which are overridden by protractor below.
312
319
let methodsToSync = [ 'getCurrentUrl' , 'getPageSource' , 'getTitle' ] ;
313
- let extendWDInstance : ExtendedWebDriver ;
314
- try {
315
- extendWDInstance = extendWD ( webdriverInstance ) ;
316
- } catch ( e ) {
317
- // Probably not a driver that can be extended (e.g. gotten using
318
- // `directConnect: true` in the config)
319
- extendWDInstance = webdriverInstance as ExtendedWebDriver ;
320
- }
321
320
322
321
// Mix all other driver functionality into Protractor.
323
322
Object . getOwnPropertyNames ( WebDriver . prototype ) . forEach ( method => {
324
- if ( ! this [ method ] && typeof ( extendWDInstance as any ) [ method ] === 'function' ) {
323
+ if ( ! this [ method ] && typeof ( this . driver as any ) [ method ] === 'function' ) {
325
324
if ( methodsToSync . indexOf ( method ) !== - 1 ) {
326
- ptorMixin ( this , extendWDInstance , method , this . waitForAngular . bind ( this ) ) ;
325
+ ptorMixin ( this , 'driver' , method , this . waitForAngular . bind ( this ) ) ;
327
326
} else {
328
- ptorMixin ( this , extendWDInstance , method ) ;
327
+ ptorMixin ( this , 'driver' , method ) ;
329
328
}
330
329
}
331
330
} ) ;
332
331
333
- this . driver = extendWDInstance ;
334
332
if ( opt_blockingProxyUrl ) {
335
333
logger . info ( 'Starting BP client for ' + opt_blockingProxyUrl ) ;
336
334
this . bpClient = new BPClient ( opt_blockingProxyUrl ) ;
@@ -343,7 +341,6 @@ export class ProtractorBrowser extends AbstractExtendedWebDriver {
343
341
this . ignoreSynchronization = false ;
344
342
this . getPageTimeout = DEFAULT_GET_PAGE_TIMEOUT ;
345
343
this . params = { } ;
346
- this . ready = null ;
347
344
this . plugins_ = new Plugins ( { } ) ;
348
345
this . resetUrl = DEFAULT_RESET_URL ;
349
346
this . debugHelper = new DebugHelper ( this ) ;
@@ -365,7 +362,33 @@ export class ProtractorBrowser extends AbstractExtendedWebDriver {
365
362
ng12Hybrid_ = ng12Hybrid ;
366
363
}
367
364
} ) ;
368
- this . driver . getCapabilities ( ) . then ( ( caps : Capabilities ) => {
365
+ this . trackOutstandingTimeouts_ = ! opt_untrackOutstandingTimeouts ;
366
+ this . mockModules_ = [ ] ;
367
+ this . addBaseMockModules_ ( ) ;
368
+
369
+ // set up expected conditions
370
+ this . ExpectedConditions = new ProtractorExpectedConditions ( this ) ;
371
+ }
372
+
373
+ /**
374
+ * Sets the `WebDriver` instance which `ProtractorBrowser` wraps around
375
+ *
376
+ * @param {WebDriver } webdriverInstance The WebDriver instance to wrap around
377
+ */
378
+ setDriver_ ( webdriverInstance : WebDriver ) {
379
+ // First extend the driver
380
+ let extendWDInstance : ExtendedWebDriver ;
381
+ try {
382
+ extendWDInstance = extendWD ( webdriverInstance ) ;
383
+ } catch ( e ) {
384
+ // Probably not a driver that can be extended (e.g. gotten using
385
+ // `directConnect: true` in the config)
386
+ extendWDInstance = webdriverInstance as ExtendedWebDriver ;
387
+ }
388
+
389
+ this . driver = extendWDInstance ;
390
+
391
+ this . ready = this . driver . getCapabilities ( ) . then ( ( caps ) => {
369
392
// Internet Explorer does not accept data URLs, which are the default
370
393
// reset URL for Protractor.
371
394
// Safari accepts data urls, but SafariDriver fails after one is used.
@@ -376,13 +399,6 @@ export class ProtractorBrowser extends AbstractExtendedWebDriver {
376
399
this . resetUrl = 'about:blank' ;
377
400
}
378
401
} ) ;
379
-
380
- this . trackOutstandingTimeouts_ = ! opt_untrackOutstandingTimeouts ;
381
- this . mockModules_ = [ ] ;
382
- this . addBaseMockModules_ ( ) ;
383
-
384
- // set up expected conditions
385
- this . ExpectedConditions = new ProtractorExpectedConditions ( this ) ;
386
402
}
387
403
388
404
/**
@@ -434,7 +450,17 @@ export class ProtractorBrowser extends AbstractExtendedWebDriver {
434
450
/**
435
451
* Restart the browser instance.
436
452
*
453
+ * Replaces a browser's `.driver` property, so if you've saved a reference directly to
454
+ * `browser.driver`, make sure to update it.
455
+ *
456
+ * Behaves slightly differently depending on if the webdriver control flow is enabled. If the
457
+ * control flow is enabled, `browser.driver` is synchronously replaced. If the control flow is
458
+ * disabled, `browser.driver` is replaced asynchronously after the old driver quits.
459
+ *
437
460
* Set by the runner.
461
+ *
462
+ * @returns {webdriver.promise.Promise.<void> } A promise which resolves once the browser has
463
+ * restarted.
438
464
*/
439
465
restart ( ) {
440
466
return ;
0 commit comments