</>

Technology

Page Object Model

Difficulty

Intermediate

Interview Question

How do you implement Extent Reports in a Selenium TestNG framework?

Answer

Extent Reports in Selenium TestNG

Dependency (pom.xml)

XML
<dependency>
    <groupId>com.aventstack</groupId>
    <artifactId>extentreports</artifactId>
    <version>5.1.1</version>
</dependency>

ExtentManager — Singleton Report Instance

Java
// utils/ExtentManager.java
public class ExtentManager {
    private static ExtentReports extent;

    public static ExtentReports getInstance() {
        if (extent == null) {
            ExtentSparkReporter spark = new ExtentSparkReporter("test-output/ExtentReport.html");
            spark.config().setDocumentTitle("AutomateQA Test Report");
            spark.config().setReportName("Regression Suite");
            spark.config().setTheme(Theme.DARK);

            extent = new ExtentReports();
            extent.attachReporter(spark);
            extent.setSystemInfo("OS",      System.getProperty("os.name"));
            extent.setSystemInfo("Browser", ConfigReader.getBrowser());
            extent.setSystemInfo("Env",     ConfigReader.getBaseUrl());
        }
        return extent;
    }
}

TestNG Listener

Java
// listeners/TestListener.java
public class TestListener implements ITestListener, ISuiteListener {
    private static ExtentReports        extent = ExtentManager.getInstance();
    private static ThreadLocal<ExtentTest> test = new ThreadLocal<>();

    @Override
    public void onTestStart(ITestResult result) {
        String testName = result.getMethod().getMethodName();
        String desc     = result.getMethod().getDescription();

        ExtentTest extentTest = extent.createTest(testName, desc);
        // Add categories from TestNG groups
        for (String group : result.getMethod().getGroups()) {
            extentTest.assignCategory(group);
        }
        test.set(extentTest);
    }

    @Override
    public void onTestSuccess(ITestResult result) {
        test.get().pass("✅ Test PASSED");
    }

    @Override
    public void onTestFailure(ITestResult result) {
        test.get().fail(result.getThrowable());

        // Attach screenshot
        String path = ScreenshotUtil.capture(result.getName());
        test.get().addScreenCaptureFromPath(path, "Failure Screenshot");
    }

    @Override
    public void onTestSkipped(ITestResult result) {
        test.get().skip("⚠️ Test SKIPPED: " + result.getThrowable().getMessage());
    }

    @Override
    public void onFinish(ISuite suite) {
        extent.flush();   // write HTML file
        System.out.println("Report: test-output/ExtentReport.html");
    }
}

Register Listener in testng.xml

XML
<suite name="Suite">
    <listeners>
        <listener class-name="com.automateqa.listeners.TestListener"/>
    </listeners>

    <test name="Regression">
        <classes>
            <class name="com.automateqa.tests.LoginTest"/>
            <class name="com.automateqa.tests.DashboardTest"/>
        </classes>
    </test>
</suite>

ScreenshotUtil

Java
// utils/ScreenshotUtil.java
public class ScreenshotUtil {
    public static String capture(String testName) {
        File src = ((TakesScreenshot) DriverManager.getDriver())
                       .getScreenshotAs(OutputType.FILE);
        String dir  = "test-output/screenshots/";
        String name = testName + "_" + LocalDateTime.now()
                          .format(DateTimeFormatter.ofPattern("yyyyMMdd_HHmmss")) + ".png";
        String path = dir + name;
        try {
            new File(dir).mkdirs();
            FileUtils.copyFile(src, new File(path));
        } catch (IOException e) {
            e.printStackTrace();
        }
        return path;
    }
}

Log Within Tests (Optional)

Java
// In any test — log steps to the Extent report
@Test
public void testLogin() {
    ExtentTestLogger.log("Navigating to login page");
    loginPage.visit();

    ExtentTestLogger.log("Entering credentials");
    loginPage.login("alice@test.com", "Pass@123");

    ExtentTestLogger.log("Verifying dashboard");
    Assert.assertTrue(dashPage.isLoaded());
}

// Where ExtentTestLogger accesses ThreadLocal test:
public class ExtentTestLogger {
    public static void log(String msg) {
        TestListener.getCurrentTest().info(msg);
    }
}

Follow AutomateQA

Related Topics