In one of my tests I need to assert message in browser dialog. I created dialog handler in test
page.on('dialog', BasePage.dialog_handle)
page
is default playwright fixture.
The handler itself is
def dialog_handle(dialog):
message = dialog.message
dialog.dismiss()
Here is full example of the test with dialog on the page
from playwright.sync_api import Page
def dialog_handle(dialog):
message = dialog.message
dialog.dismiss()
def test_dialog(page):
page.goto('https://dialog.antonzimaiev.repl.co')
page.on('dialog', dialog_handle)
page.get_by_role("button", name="Диалог Alert").click()
How can I retrieve dialog.message to assert it using pytest?
This can be solved with some scoping readjustments:
from playwright.sync_api import sync_playwright # 1.37.0
def test_dialog(page):
dialog_message = None
def handle_dialog(dialog):
nonlocal dialog_message
# assert here
print(dialog.message) # => Hello from Open Solutions 🙂
# or save the message in the enclosing scope...
dialog_message = dialog.message
dialog.dismiss()
page.goto("https://dialog.antonzimaiev.repl.co")
page.once("dialog", handle_dialog)
page.get_by_role("button", name="Диалог Alert").click()
# ... and assert here
print(dialog_message) # => Hello from Open Solutions 🙂
if __name__ == "__main__":
with sync_playwright() as p:
browser = p.chromium.launch(headless=True)
page = browser.new_page()
test_dialog(page)
There's nothing special about pytest per se here--you can drop the test_dialog
function body right into a pytest test case and use assertions from that, or any other testing library you like.
Race conditions aren't an issue here since the dialog blocks the script after the .click()
operation until it's dismissed.
This pattern can be factored to be reusable across tests or in a POM, if that's a concern. For example:
def accept_dialog(page, trigger_dialog):
dialog_message = None
def handle_dialog(dialog):
nonlocal dialog_message
dialog_message = dialog.message
dialog.dismiss()
page.once("dialog", handle_dialog)
trigger_dialog()
return dialog_message
def test_dialog(page):
page.goto("https://dialog.antonzimaiev.repl.co")
dialog_message = accept_dialog(
page,
lambda: page.get_by_role("button", name="Диалог Alert").click()
)
print(dialog_message) # => Hello from Open Solutions 🙂