Background Image
Table of Contents Table of Contents
Previous Page  282 / 478 Next Page
Information
Show Menu
Previous Page 282 / 478 Next Page
Page Background

In this one we’ve “rolled our own” wait—we iterate through all the current browser

windows, looking for one with a particular title. If we can’t find it, we do a short wait,

and try again, decrementing a retry counter.

This is such a common pattern in Selenium tests that the teamcreated anAPI for waiting

—it doesn’t quite handle all use cases though, so that’s why we had to roll our own the

first time around. When doing something simpler like waiting for an element with a

given ID to appear on the page, we can use the

WebDriverWait

class:

functional_tests/test_login.py (ch15l015).

from

selenium.webdriver.support.ui

import

WebDriverWait

[

...

]

def

wait_for_element_with_id

(

self

,

element_id

):

WebDriverWait

(

self

.

browser

,

timeout

=

30

)

.

until

(

lambda

b

:

b

.

find_element_by_id

(

element_id

)

)

This is what Selenium calls an “explicit wait”. If you remember, we already defined an

“implicit wait” in

FunctionalTest.setUp

. We set that to just three seconds, which is

fine in most cases, but when we’re waiting for an external service like Persona, we

sometimes need to bump that default timeout.

There are more examples in the

Selenium docs

, but I actually found reading the

source code

more instructive—there are good docstrings!

implicitly_wait

is unreliable, especially once JavaScript is in‐

volved. Prefer the “wait-for” pattern in your FT whenever you need

to check for asynchronous interactions on your pages. We’ll see this

again in

Chapter 20

.

And if we run the FT, it works!

$

python3 manage.py test functional_tests.test_login

Creating test database for alias 'default'...

Not Found: /favicon.ico

login view

sending to mozilla {'assertion': [...]

[...]

got b'{"audience":"localhost","expires":[...]

[...]

.

---------------------------------------------------------------------

Ran 1 test in 32.222s

OK

Destroying test database for alias 'default'...

254

|

Chapter 15: User Authentication, Integrating Third-Party Plugins, and Mocking with JavaScript