0
0
Selenium Javatesting~12 mins

Thread.sleep vs proper waits in Selenium Java - Framework Approaches Compared

Choose your learning style9 modes available
Framework Mode - Thread.sleep vs proper waits
Folder Structure of a Selenium Java Test Framework
  project-root/
  ├── src/
  │   ├── main/
  │   │   └── java/
  │   │       └── com/example/app/pages/       # Page Object classes
  │   └── test/
  │       └── java/
  │           └── com/example/app/tests/       # Test classes
  ├── src/test/resources/                       # Test data, config files
  ├── utils/                                    # Utility classes (e.g., wait helpers)
  ├── drivers/                                  # WebDriver executables
  ├── testng.xml                                # TestNG suite configuration
  └── pom.xml                                   # Maven build and dependencies
  
Test Framework Layers
  • Driver Layer: Manages WebDriver setup and teardown.
  • Page Objects: Encapsulate page elements and actions.
  • Tests: TestNG test classes that use page objects.
  • Utilities: Helper classes, including explicit wait methods.
  • Configuration: Environment settings, browser options, credentials.
Configuration Patterns

Use testng.xml or config.properties files to manage:

  • Browser type (Chrome, Firefox, etc.)
  • Base URLs for different environments (dev, staging, production)
  • Timeout values for waits
  • Credentials stored securely or injected at runtime

Example snippet from config.properties:

browser=chrome
baseUrl=https://example.com
implicitWait=10
explicitWait=15
  
Test Reporting and CI/CD Integration
  • Use TestNG reports for detailed test results.
  • Integrate with tools like Allure or ExtentReports for rich HTML reports.
  • Configure CI/CD pipelines (Jenkins, GitHub Actions) to run tests automatically on code changes.
  • Fail builds on test failures to ensure quality.
Thread.sleep() vs Explicit Waits: Code Examples

❌ Bad Practice: Thread.sleep() (Avoid This)

// In a Page Object or Test - FIXED WAIT, UNRELIABLE!
Thread.sleep(5000); // Waits 5 seconds regardless
loginButton.click();

Problems: Wastes time if element loads faster; fails if slower. Slow tests, no polling.

✅ Good Practice: Explicit Waits with ExpectedConditions

import org.openqa.selenium.support.ui.WebDriverWait;
import org.openqa.selenium.support.ui.ExpectedConditions;
import java.time.Duration;

WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(15));
wait.until(ExpectedConditions.elementToBeClickable(loginButton));
loginButton.click();

Benefits: Polls until condition met, faster & reliable.

🎯Reusable Utility Class (utils/WaitUtils.java)
package com.example.app.utils;

import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.By;
import org.openqa.selenium.support.ui.WebDriverWait;
import org.openqa.selenium.support.ui.ExpectedConditions;
import java.time.Duration;

public class WaitUtils {

    public static WebDriverWait getExplicitWait(WebDriver driver, long timeoutSeconds) {
        return new WebDriverWait(driver, Duration.ofSeconds(timeoutSeconds));
    }

    public static void waitForVisibility(WebDriver driver, WebElement element, long timeoutSeconds) {
        getExplicitWait(driver, timeoutSeconds)
            .until(ExpectedConditions.visibilityOf(element));
    }

    public static void waitForClickability(WebDriver driver, WebElement element, long timeoutSeconds) {
        getExplicitWait(driver, timeoutSeconds)
            .until(ExpectedConditions.elementToBeClickable(element));
    }

    public static void waitForPresence(WebDriver driver, By locator, long timeoutSeconds) {
        getExplicitWait(driver, timeoutSeconds)
            .until(ExpectedConditions.presenceOfElementLocated(locator));
    }
}
Usage in Page Object (src/main/java/com/example/app/pages/LoginPage.java)
package com.example.app.pages;

import com.example.app.utils.WaitUtils;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
import org.openqa.selenium.support.PageFactory;

public class LoginPage {
    private WebDriver driver;
    @FindBy(id = "username")
    private WebElement usernameField;
    @FindBy(id = "login-button")
    private WebElement loginButton;

    public LoginPage(WebDriver driver) {
        this.driver = driver;
        PageFactory.initElements(driver, this);
    }

    public void enterUsername(String username) {
        WaitUtils.waitForVisibility(driver, usernameField, 15);
        usernameField.sendKeys(username);
    }

    public void clickLogin() {
        WaitUtils.waitForClickability(driver, loginButton, 15);
        loginButton.click();
    }
}
Usage in Test Class (src/test/java/com/example/app/tests/LoginTest.java)
package com.example.app.tests;

import com.example.app.pages.LoginPage;
import org.testng.annotations.Test;

public class LoginTest extends BaseTest {

    @Test
    public void testValidLogin() {
        LoginPage loginPage = new LoginPage(driver);
        loginPage.enterUsername("testuser");
        loginPage.clickLogin();
        // Assertions...
    }
}
Best Practices for Waits in Selenium Java Framework
  • Avoid Thread.sleep(): It pauses the test for a fixed time, causing slow and unreliable tests.
  • Use Explicit Waits: Wait only as long as needed for a condition (element visible, clickable).
  • Implement Utility Methods: Create reusable wait helper methods in utils/ for cleaner tests.
  • Prefer ExpectedConditions: Use Selenium's built-in conditions for common waits.
  • Set Reasonable Timeouts: Configure timeouts in config files to balance speed and reliability.
  • FluentWait for Advanced: Customize polling frequency if needed.
Self Check Question

Where in this framework structure would you add a reusable explicit wait method to replace Thread.sleep()?

Answer (Click to Reveal)

utils/ - Utility classes (e.g., WaitUtils.java). This keeps waits reusable across Page Objects and Tests.

Key Result
Use explicit waits with reusable utility methods in the utils/ folder instead of Thread.sleep() for reliable, fast Selenium Java tests. Integrate with Page Objects and TestNG.