Tech Stack
Language
Framework
Reporting
Cicd
Table of Contents
- π Building a Robust Web UI Test Framework with Playwright and Python using POM(Page Object Model) design pattern
- Test on different browsers with the same code!
- Playwright automatically waits for elements to be actionable
- Capture everything that happens during the test
- Run your tests...
- Monitor or modify network requests
- Each context is isolated from others
- Without POM - Messy and hard to maintain π±
- With POM - Clean and organized π
- LoginPage can be used in countless tests
- Before UI change: LOGIN_BUTTON = "#loginButton"
- After UI change: Just update it once!
- Each page class has a clear responsibility
π Building a Robust Web UI Test Framework with Playwright and Python using POM(Page Object Model) design pattern
π― Introduction
Hello, fellow automation enthusiasts! π Ready to explore something exciting? Today, I'm taking you on a journey through my Playwright test automation framework that turns the often tedious task of UI testing into an adventure! Whether you're a seasoned test automation engineer or just getting started, this framework will give you superpowers to slay those testing dragons with style! β¨
Testing web applications can be challenging - flaky tests, difficult maintenance, and slow execution times can make it feel like you're fighting a never-ending battle. But fear not! With Playwright and a well-structured Page Object Model (POM) framework, we can turn those challenges into victories worth celebrating! π
π Why Playwright?
You might be wondering, "With so many automation tools out there (Selenium, Cypress, etc.), why choose Playwright?" Great question! Let me share why Playwright has become my magical weapon of choice:
1. π Multi-browser Support
Feature: Unlike some tools that are limited to specific browsers, Playwright gives you the power to test across Chromium, Firefox, and WebKit with the same code! It's like having three superheroes at your command.
# Test on different browsers with the same code!
browser_types = ['chromium', 'firefox', 'webkit']
2. β±οΈ Auto-waiting Magic
Feature: No more sleep statements or explicit waits! Playwright's auto-waiting mechanism is like having a sixth sense - it knows exactly when elements are ready for interaction:
# Playwright automatically waits for elements to be actionable
await page.click("button#submit") # It waits until the button is ready!
3. πΈ Built-in Tracing
Feature: When something goes wrong (and let's be honest, in testing, it will), Playwright gives you magical insight with its built-in tracing:
# Capture everything that happens during the test
context.tracing.start(screenshots=True, snapshots=True)
# Run your tests...
context.tracing.stop(path="trace.zip")
4. ποΈ Network Interception
Feature: Want to spy on what your application is doing behind the scenes? Playwright lets you intercept and modify network requests like a true testing ninja:
# Monitor or modify network requests
page.route("**/*.{png,jpg,jpeg}", lambda route: route.abort())
5. π Isolation by Default
Feature: Each test runs in its own browser context, like having a fresh browser for every test. No more cross-test contamination!
# Each context is isolated from others
context1 = browser.new_context()
context2 = browser.new_context() # Completely separate from context1
6. π Speed Demon
Feature: Playwright is FAST - much faster than Selenium for most operations, making your test runs feel like they're powered by rockets!
π§© Why Page Object Model (POM)?
So we've chosen Playwright as our magical automation tool, but how do we structure our tests to be maintainable, readable, and scalable? Enter the Page Object Model (POM) - a design pattern that will transform your automation experience! π
1. π§° Organized Chaos to Elegant Structure
Benefit: Have you ever seen a test script that looks like spaghetti code - locators, actions, and assertions all jumbled together? The POM pattern turns that chaos into an elegant structure:
# Without POM - Messy and hard to maintain π±
def test_login_without_pom():
page.fill("#username", "testuser")
page.fill("#password", "password123")
page.click("#loginButton")
assert page.locator(".welcome-message").is_visible()
# More messy code...
# With POM - Clean and organized π
def test_login_with_pom(page):
login_page = LoginPage(page)
dashboard = login_page.login("testuser", "password123")
dashboard.verify_welcome_message()
# Beautiful!
2. β»οΈ Reusability at Its Finest
Benefit: One of the most magical benefits of POM is the ability to reuse code across multiple tests. Why write the same login sequence 50 times when you can write it once?
# LoginPage can be used in countless tests
class LoginPage:
USERNAME_FIELD = "#username"
PASSWORD_FIELD = "#password"
LOGIN_BUTTON = "#loginButton"
def __init__(self, page):
self.page = page
def login(self, username, password):
self.page.fill(self.USERNAME_FIELD, username)
self.page.fill(self.PASSWORD_FIELD, password)
self.page.click(self.LOGIN_BUTTON)
return DashboardPage(self.page) # Return the next page object!
3. π οΈ Maintenance Made Easy
UI elements change all the time - it's just a fact of development life. With POM, when a locator changes, you only need to update it in ONE place:
# Before UI change: LOGIN_BUTTON = "#loginButton"
# After UI change: Just update it once!
LOGIN_BUTTON = "#new-login-btn" # Updated in one place, fixed everywhere!
4. π Readable Tests That Tell a Story
POM transforms your tests from cryptic code into readable stories that anyone on your team can understand:
def test_purchase_workflow(page):
# This reads like a user story! π
home_page = HomePage(page)
product_page = home_page.navigate_to_products()
product_page.add_item_to_cart("Magic Testing Wand")
cart_page = product_page.go_to_cart()
cart_page.verify_item_in_cart("Magic Testing Wand")
checkout_page = cart_page.proceed_to_checkout()
# The test continues...
5. π Separation of Concerns
POM follows the Single Responsibility Principle - each page object is responsible for only one part of the UI. This makes your code more organized, easier to debug, and more maintainable:
# Each page class has a clear responsibility
class HomePage: # Only responsible for home page actions
# Home page methods...
class ProductPage: # Only responsible for product page actions
# Product page methods...
class CartPage: # Only responsible for cart actions
# Cart page methods...
6. π§ͺ Better Test Coverage
With POM, adding new tests becomes so easy that you'll naturally expand your test coverage. What was once a chore becomes a breeze!
Combining the magical powers of Playwright with the structural elegance of POM creates an automation framework that's not just powerful, but also a joy to work with. It's like having a well-organized spellbook where each incantation is easy to find and cast! β¨