0
0
Testing Fundamentalstesting~15 mins

Authentication testing in Testing Fundamentals - Build an Automation Script

Choose your learning style9 modes available
Verify user login with valid and invalid credentials
Preconditions (1)
Step 1: Enter 'validuser@example.com' in the email input field
Step 2: Enter 'ValidPass123' in the password input field
Step 3: Click the 'Login' button
Step 4: Verify that the user is redirected to the dashboard page
Step 5: Log out to return to the login page
Step 6: Enter 'invaliduser@example.com' in the email input field
Step 7: Enter 'WrongPass' in the password input field
Step 8: Click the 'Login' button
Step 9: Verify that an error message 'Invalid email or password' is displayed
✅ Expected Result: User successfully logs in with valid credentials and sees the dashboard. User cannot log in with invalid credentials and sees the correct error message.
Automation Requirements - Selenium with Python
Assertions Needed:
Verify current URL is dashboard URL after valid login
Verify error message text after invalid login
Best Practices:
Use explicit waits to wait for elements to be visible or clickable
Use meaningful locators like By.ID or By.NAME
Separate test logic and locators for maintainability
Clean up by logging out after valid login test
Automated Solution
Testing Fundamentals
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
import unittest

class TestAuthentication(unittest.TestCase):
    def setUp(self):
        self.driver = webdriver.Chrome()
        self.driver.get('https://example.com/login')
        self.wait = WebDriverWait(self.driver, 10)

    def test_valid_and_invalid_login(self):
        driver = self.driver
        wait = self.wait

        # Valid login
        email_input = wait.until(EC.visibility_of_element_located((By.ID, 'email')))
        email_input.clear()
        email_input.send_keys('validuser@example.com')

        password_input = driver.find_element(By.ID, 'password')
        password_input.clear()
        password_input.send_keys('ValidPass123')

        login_button = driver.find_element(By.ID, 'login-button')
        login_button.click()

        # Wait for dashboard URL
        wait.until(EC.url_contains('/dashboard'))
        self.assertIn('/dashboard', driver.current_url, 'Dashboard URL not loaded after valid login')

        # Log out to return to login page
        logout_button = wait.until(EC.element_to_be_clickable((By.ID, 'logout-button')))
        logout_button.click()

        wait.until(EC.url_contains('/login'))

        # Invalid login
        email_input = wait.until(EC.visibility_of_element_located((By.ID, 'email')))
        email_input.clear()
        email_input.send_keys('invaliduser@example.com')

        password_input = driver.find_element(By.ID, 'password')
        password_input.clear()
        password_input.send_keys('WrongPass')

        login_button = driver.find_element(By.ID, 'login-button')
        login_button.click()

        # Verify error message
        error_message = wait.until(EC.visibility_of_element_located((By.ID, 'error-message')))
        self.assertEqual(error_message.text, 'Invalid email or password', 'Error message text mismatch')

    def tearDown(self):
        self.driver.quit()

if __name__ == '__main__':
    unittest.main()

The setUp method opens the browser and navigates to the login page before each test.

In test_valid_and_invalid_login, we first enter valid credentials and click login. We wait explicitly for the dashboard URL to load and assert the URL contains '/dashboard'.

Then we log out by clicking the logout button and wait to return to the login page.

Next, we enter invalid credentials and click login. We wait for the error message element to appear and assert its text matches the expected error.

The tearDown method closes the browser after the test finishes.

Explicit waits ensure the test waits for elements or page changes before interacting or asserting, making the test stable.

Using IDs for locators keeps selectors simple and reliable.

Common Mistakes - 4 Pitfalls
Using time.sleep() instead of explicit waits
Using brittle XPath locators that depend on page structure
Not clearing input fields before sending keys
Not verifying the correct page or element after login
Bonus Challenge

Now add data-driven testing with 3 different sets of credentials: one valid, two invalid.

Show Hint