JUnit get tests results at AfterClass - java

I need to run tests classes and show the results in screen, following this structure, but just after running all.
#RunWith(Suite.class)
#Suite.SuiteClasses({
LoginTest.class,
LogoutTest.class
})
public class AllTests {
protected static WebDriver driver;
#BeforeClass
public static void beforeClass() throws Exception {
driver = Selenium.getDriver();
driver.navigate().to(Property.SITE_ADDRESS);
driver.manage().window().maximize();
}
#AfterClass
public static void afterClass() throws Exception {
String resultString = "";
Result result = JUnitCore.runClasses(AllTests.class);
for (Failure fail : result.getFailures()) {
resultString += result.getClass() +": "+ fail.toString()+"\n";
}
if (result.wasSuccessful()) {
resultString += result.getClass() +": "+ result + "\n";
}
JFrame frame = new JFrame("Results");
JOptionPane.showMessageDialog(frame, resultString, "Title", JOptionPane.INFORMATION_MESSAGE);
driver.quit();
}
My #AfterClass is re-running my test classes, is there any other solution?

Related

How to test sublinks on a page in Selenium

How to test sub links on a page in Selenium. I have an events page. Then from that events page i collect all the different events links. Then i want to recursively run tests on those links.
I have attached an image of the page. The green text are all links. So i collected the href values of all these. After that I have some tests to run on those pages. I have a test class called EventsPageTest for the main page. The test class for the sub pages is called SingleEventsPageTest. How do I transfer the href values from the main class to the other class. Or is there any other method I need to follow.
I searched the internet so much but was of no use.
Any help would be appreciated.
Thanks
EventsPageTest
package test;
import pages.EventsPageObjects;
#Listeners(listeners.TestListener.class)
public class EventsPageTest {
private static ExtentHtmlReporter htmlReporter;
private static ExtentReports extent;
private static ExtentTest test;
static WebDriver driver = null;
private static EventsPageObjects eventsPage;
public MutableCapabilities capabilities;
static Set<String> eventsLinks = new HashSet<String>();
String url;
#BeforeSuite
public void setUp() {
// initialize the HtmlReporter
htmlReporter = new ExtentHtmlReporter("extentReportsEventsPage.html");
// initialize ExtentReports and attach the HtmlReporter
extent = new ExtentReports();
// attach only HtmlReporter
extent.attachReporter(htmlReporter);
}
#BeforeTest
public void setUpTest() throws IOException{
WebDriverManager.chromedriver().setup();
driver = new ChromeDriver();
url = "abc.com";
driver.get(url);
System.out.println("Inside setUpTest");
//Create eventsPageObject
eventsPage = new EventsPageObjects(driver);
}
#Test(alwaysRun=true)
public void collectEventsLinks() throws InterruptedException, IOException {
test = extent.createTest("Collect all Events Links on a page","Test to Collect all Events Links on a page ");
test.log(Status.INFO, "Starting Test Case");
List<WebElement> links = driver.findElements(By.tagName("a"));
for (int i = 0; i<links.size(); i++) {
if(Pattern.matches("^https://"+ TestRunner.url +"/events/[^/]+[^\\s]$", links.get(i).getAttribute("href")))
eventsLinks.add((links.get(i).getAttribute("href")));
}
test.log(Status.INFO, "Finished Test Case");
}
#AfterTest(alwaysRun = true)
public void tearDownTest() {
//close browser
driver.close();
driver.quit();
}
#DataProvider(name="getURLS")
#AfterTest
public Object[] getURLS() {
System.out.println("Inside get Urls");
System.out.println("getURLS : " + eventsLinks.size());
Object[] objArray = eventsLinks.toArray();
System.out.println(eventsLinks.size());
return objArray;
}
#AfterSuite
public void tearDown() {
extent.flush();
}
}
SingleEventsPageTest
package test;
#Listeners(listeners.TestListener.class)
public class SingleEventsPageTest{
private static ExtentHtmlReporter htmlReporter;
private static ExtentReports extent;
private static ExtentTest test;
static WebDriver driver;
private static SingleEventsPageObjects singleEventsPage;
static List<Object> eventsURLS = new ArrayList<Object>();
#BeforeSuite
public void setUp() {
PropertiesFile.getProperties();
// initialize the HtmlReporter
htmlReporter = new ExtentHtmlReporter("extentReportsSingleEventsPage.html");
// initialize ExtentReports and attach the HtmlReporter
extent = new ExtentReports();
// attach only HtmlReporter
extent.attachReporter(htmlReporter);
}
#BeforeTest
public void setUpTest() throws IOException{
WebDriverManager.chromedriver().setup();
driver = new ChromeDriver();
//Create eventsPageObject
singleEventsPage = new SingleEventsPageObjects(driver);
}
#Test(dataProvider="getURLS",dataProviderClass=EventsPageTest.class,alwaysRun=true)
public void findIfEventsTitleExists(String url) throws InterruptedException, IOException {
driver.get(url);
System.out.println("Inside findIfEventsTitleExists : " + driver.getCurrentUrl());
test = extent.createTest("Events Title Exists","Test to verify if the Events Title exists after opening the page");
test.log(Status.INFO, "Starting Test Case");
test.log(Status.INFO, "Checking If the URL points to the events page else navigate to that");
Assert.assertEquals(true,singleEventsPage.findIfEventsTitleExists());
test.log(Status.INFO, "Finished Test Case");
}
#Test(dataProvider="getURLS",dataProviderClass=EventsPageTest.class,alwaysRun=true)
public void verifyIfEventDescriptionExists(String url) throws InterruptedException, IOException {
driver.get(url);
test = extent.createTest("Events description Exists","Test to verify if the Events description exists");
test.log(Status.INFO, "Starting Test Case");
test.log(Status.INFO, "Checking If the URL points to the events page else navigate to that");
if(singleEventsPage.getCurrentUrl() != url)
singleEventsPage.navigateTo(url);
test.log(Status.INFO, "Checking If the Page Sub Title Exists");
Assert.assertEquals(true,singleEventsPage.checkIfElementExists(singleEventsPage.getEventDesc()));
test.log(Status.INFO, "Finished Test Case");
}
#AfterTest(alwaysRun = true)
public void tearDownTest() {
//close browser
driver.close();
driver.quit();
}
#AfterSuite
public void tearDown() {
extent.flush();
}
}
It would be good if you could post your code here. You can try to store them in one class as List, then pass them to another.
I am not sure how your framework is working now. I am thinking of something like this. Please post more code here.
class EventsPageTest {
public List<T> getAllHref() {
// return List
}
}
class SingleEventsPage {
#Test
public void someTest () {
EventsPageTest eventsPageTest = new EventsPageTest();
List<T> hrefs = eventsPageTest.getAllHref();
}
}
Hope this helps

Skipped test is not logged as Skipped in ExtentReport4

I got 2 tests: addNewVideo and deleteRecentVideo where the second one depends on first one. After first fails, second gets ignored and it's not running. After opening my Extent Report, it looks like this:
I'm expecting to have 2 tests - 1 failed, 1 skipped, but it's not showing properly on the report.
ExtentListener.class
import com.aventstack.extentreports.*;
import com.aventstack.extentreports.markuputils.*;
import org.testng.*;
import java.util.*;
import static constants.FileResources.REPORT_DIR;
public class ExtentListener implements ITestListener {
private static Date d = new Date();
private static String fileName = String.format("%s%s%s%s", d.toString().replaceAll("[: ]", "_"), "_", System.getenv("env"), ".html");
private static ExtentReports extent = ExtentManager.createInstance(REPORT_DIR + fileName);
public static ThreadLocal<ExtentTest> testReport = new ThreadLocal<>();
#Override
public void onTestStart(ITestResult result) {
ExtentTest test = extent.createTest(result.getTestClass().getName() + "." + result.getMethod().getMethodName());
test.assignCategory(result.getTestClass().getName());
testReport.set(test);
}
#Override
public void onTestSuccess(ITestResult result) {
String methodName = result.getMethod().getMethodName();
String logText = methodName + " PASSED";
Markup m = MarkupHelper.createLabel(logText, ExtentColor.GREEN);
testReport.get().pass(m);
}
#Override
public void onTestFailure(ITestResult result) {
String methodName = result.getMethod().getMethodName();
String excepionMessage = Arrays.toString(result.getThrowable().getStackTrace());
testReport.get().fail("<details>" + "<summary>" + "<b>" + "<font color=" + "red>" + "Exception occured: Expand to check details"
+ "</font>" + "</b >" + "</summary>" + excepionMessage.replaceAll(",", "<br>") + "</details>" + " \n");
String failureLog = methodName + " FAILED";
Markup m = MarkupHelper.createLabel(failureLog, ExtentColor.RED);
testReport.get().log(Status.FAIL, m);
}
#Override
public void onTestSkipped(ITestResult result) {
String methodName = result.getMethod().getMethodName();
String logText = "<b>" + methodName + " SKIPPED" + "</b>";
Markup m = MarkupHelper.createLabel(logText, ExtentColor.ORANGE);
testReport.get().skip(m);
}
#Override
public void onTestFailedButWithinSuccessPercentage(ITestResult result) {
}
#Override
public void onStart(ITestContext context) {
}
#Override
public void onFinish(ITestContext context) {
if (extent != null) {
extent.flush();
}
}
}
I've tried implementing IInvokedMethodListener but no success.
Is there any way to show skipped tests properly on ExtentReport4?
Guys I also faced this issue and below code worked for me.
Define the testListener like this and then call this testListener class in your Baseclass by using #listeners(TestListeners.class) before Baseclass starts.
Note : I have used Spark Extentreport
public class TestListeners implements ITestListener {
#override
public void onTestSkipped(ITestResult result) {
Baseclass.extenttest = Baseclass.extent.createTest(result.getMethod().getDescription()).assignCategory("SkipedTest");
Baseclass.extenttest .log(Status.SKIP, result.getThrowable());
Baseclass.extenttest .log(Status.SKIP, result.getMethod().getDescription());
Baseclass.extenttest .log(Status.SKIP, MarkupHelper.createLabel(result.getName(), ExtentColor.YELLOW));
Baseclass.extent.flush();
}
}
In your test class define #Test like below
#Test(description = "Test Case name", dependsOnMethods = { "Name of method on which it depends" })
I tried IInvokeMethodListener2 once again, but it's just a workaround.
If method from dependsOnMethods failed, the test method was not executed at all, therefore it was not logged as skipped. My solution is to tag dependant methods as description and check before invocation if it contains any failed method from test class.
public class MethodListener implements IInvokedMethodListener2 {
#Override
public void beforeInvocation(IInvokedMethod method, ITestResult testResult, ITestContext context) {
List<String> failed = context
.getFailedTests()
.getAllMethods()
.stream()
.map(ITestNGMethod::getMethodName)
.collect(Collectors.toList());
boolean isSkippable = false;
if (failed.size() > 0 && method.getTestMethod().getDescription() != null) {
List<String> methodNames = Arrays.asList(method.getTestMethod().getDescription().split(";"));
isSkippable = failed
.stream()
.anyMatch(methodNames::contains);
}
if (isSkippable) {
throw new SkipException("Skipping " + method.getTestMethod().getMethodName());
}
}
#Override
public void afterInvocation(IInvokedMethod method, ITestResult testResult, ITestContext context) {
}
#Override
public void beforeInvocation(IInvokedMethod method, ITestResult testResult) {
}
#Override
public void afterInvocation(IInvokedMethod method, ITestResult testResult) {
}
}
#Listeners({MethodListener.class, ExtentListener.class})
public class SampleTest extends TestsBase {
#Test(priority = 1)
public void pass() {
System.out.println("pass");
}
#Test(priority = 2)
public void fail1() {
System.out.println("fail1");
Assert.fail();
}
#Test(priority = 3)
public void fail2() {
System.out.println("fail2");
Assert.fail();
}
#Test(priority = 4)
public void fail3() {
System.out.println("fail3");
Assert.fail();
}
#Test(priority = 5)
public void fail4() {
System.out.println("fail4");
Assert.fail();
}
#Test(priority = 6, description = "pass;fail2")
public void skip1() {
System.out.println("skip1");
}
#Test(priority = 7, description = "pass;fail3")
public void skip2() {
System.out.println("skip2");
}
}

How to do JUnit test from only one GUI?

I wrote some JUnit test cases at Winium which is nearly same as Selenium for Calculator. My problem is with every test a new calculator.exe is started but I want to do all the test for the same calculator.exe but I also want to seperate the JUnit test. Below you can see my code:
public class calculatorTest {
#Test
public void additionTest() throws MalformedURLException, InterruptedException {
DesktopOptions option = new DesktopOptions();
option.setApplicationPath("C:\\Windows\\System32\\calc.exe");
WiniumDriver driver = new WiniumDriver(new URL("http://localhost:9999") , option);
Thread.sleep(2000);
driver.findElement(By.name("Seven")).click();
driver.findElement(By.name("Plus")).click();
driver.findElement(By.name("Eight")).click();
driver.findElement(By.name("Equals")).click();
String output = driver.findElement(By.id("CalculatorResults")).getAttribute("Name");
System.out.println("Result is " + output);
assertEquals("Display is 15", output);
}
#Test
public void subtractionTest() throws MalformedURLException, InterruptedException {
DesktopOptions option = new DesktopOptions();
option.setApplicationPath("C:\\Windows\\System32\\calc.exe");
WiniumDriver driver = new WiniumDriver(new URL("http://localhost:9999") , option);
Thread.sleep(2000);
driver.findElement(By.name("Nine")).click();
driver.findElement(By.name("Minus")).click();
driver.findElement(By.name("Eight")).click();
driver.findElement(By.name("Equals")).click();
String output = driver.findElement(By.id("CalculatorResults")).getAttribute("Name");
System.out.println("Result is " + output);
}
You can add a configuration method to your test class, which is a part of JUnit
#BeforeClass
public void openCalculator() {
DesktopOptions option = new DesktopOptions();
option.setApplicationPath("C:\\Windows\\System32\\calc.exe");
WiniumDriver driver = new WiniumDriver(new URL("http://localhost:9999") , option);
Thread.sleep(2000);
}

Print Test Result in JUnit

Currently I am making the test case repeat 2 times, so how do I print the results as 2 separate results.
I tried using the built-in function to create the text, however, it does now show either "Success" or "Failure".
Currently I have this code:
public class UnitTestRunner {
static JUnitCore junitCore;
static Class<?> testClasses;
public static void main(String[] args) {
System.out.println("Running Junit Test Suite.");
Result result = JUnitCore.runClasses(TestSuite.class);
for (Failure failure : result.getFailures()) {
System.out.println(failure.toString());
}
System.out.println("Successful: " + result.wasSuccessful() +
" ran " + result.getRunCount() + " tests");
}
}
This code is working correctly, but I do not know how to implement this into JUnit.
Can someone please help to show, how to implement this code into JUnit test case.
This will be slightly long answer. For the customized output you have to add your RunListener
You can use following sample implementation for the same.
public class UnitTestRunner {
static JUnitCore junitCore;
static Class<?> testClasses;
public static void main(String[] args) {
System.out.println("Running Junit Test Suite.");
junitCore = new JUnitCore();
junitCore.addListener(new CustomExecutionListener());
Result result = junitCore.run(TestSuite.class);
for (Failure failure : result.getFailures()) {
System.out.println(failure.toString());
}
System.out.println("Successful: " + result.wasSuccessful() + " ran " + result.getRunCount() + " tests");
}
}
And implementation for the RunListener is as follows
import org.junit.runner.Description;
import org.junit.runner.Result;
import org.junit.runner.notification.Failure;
import org.junit.runner.notification.RunListener;
public class CustomExecutionListener extends RunListener {
public void testRunStarted(Description description) throws Exception {
System.out.println("Number of tests to execute: " + description.testCount());
}
public void testRunFinished(Result result) throws Exception {
System.out.println("Number of tests executed: " + result.getRunCount());
}
public void testStarted(Description description) throws Exception {
System.out.println("Starting: " + description.getMethodName());
}
public void testFinished(Description description) throws Exception {
System.out.println("Finished: " + description.getMethodName());
}
public void testFailure(Failure failure) throws Exception {
System.out.println("Failed: " + failure.getDescription().getMethodName());
}
public void testAssumptionFailure(Failure failure) {
System.out.println("Failed: " + failure.getDescription().getMethodName());
}
public void testIgnored(Description description) throws Exception {
System.out.println("Ignored: " + description.getMethodName());
}
}
And by overriding the methods in RunListener you can format you output.

Sync between error Listener and Test execution in WebDriver

I am trying to implement a javaScript error listener on the Selenium tests built in my Java project.
In order to detect console Java Script errors, I implemented a script in the JavaScript project which will push the console error messages at the bottom of the body, with a certain element containing a specific ID and the error message.
The error Listener I coded looks like:
public class ErrorListener implements Runnable{
WebDriver driver = null;
public ErrorListener (WebDriver driver)
{
this.driver = driver;
}
private void Listen ()
{
try
{
while(!driver.toString().contains("null")) //Chrome is alive
{
List<WebElement> list = driver.findElements(By.xpath("//div[#id='jsError']"));
if(list.size() != 0)
{
WebElement Error = list.get(0);
String ErrorMSG = Error.getText();
if(ErrorMSG != null)
{
Reporter.log("Found a javascript error with code: "+ErrorMSG);
Assert.assertTrue(false); // force the test failure
}
}
}
}catch(Exception ex)
{
ex.printStackTrace();
}
}
#Override
public void run()
{
Listen();
}
}
Which I am calling in my test method such as:
public class TC_NewAccount
{
public WebDriver driver;
public Thread listener;
#BeforeMethod
public void beforeTest()
{
Reporter.log("The test has just begun.");
driver = NewChrome.Generate(true);
ErrorListener errorlog = new ErrorListener(driver);
listener = new Thread(errorlog);
listener.start();
}
#AfterMethod
public void afterClass()
{
Reporter.log("Test has now finished.");
driver.close();
}
#DataProvider
public static Object[][] credentials()
{
return new Object[][] { { "id", "password" }};
}
#Test(dataProvider = "credentials")
public void Execute(String username, String password) throws Exception
{
... whatever the test does
}
}
The problem is, that since I am using the same instance of Chrome to constantly listen to a specific WebElement, I am throwing requests in parallel from both methods (the test and the listener), and the process ends up crashing because of them being at the same time and not being synced (one after another).
I realised that one option could be to check for errors after I do certain action every time, but this would greatly increment my lines of code, and it is only a partial solution because some errors may occur just in terms of milliseconds...
Is there a smooth solution for this problem?
Thanks in advance!
first of all you have to create you TestListener.java file
import org.testng.ITestContext;
import org.testng.ITestListener;
import org.testng.ITestResult;
public class TestListener implements ITestListener {
#Override
public void onTestStart(ITestResult result) {
System.out.println("Started Test: " + result.getName());
}
#Override
public void onTestSuccess(ITestResult result) {
System.out.println("Finished Test: " + result.getName() + " :PASSED");
}
#Override
public void onTestFailure(ITestResult result) {
System.out.println("Finished Test: " + result.getName() + " :FAILED");
}
#Override
public void onTestSkipped(ITestResult result) {
System.out.println("Finished Test: " + result.getName() + " :SKIPPED");
}
#Override
public void onTestFailedButWithinSuccessPercentage(ITestResult result) {
System.out.println("Finished Test: " + result.getName()
+ " :FAILED BUT WITHIN SUCCESS PERCENTAGE");
}
#Override
public void onStart(ITestContext context) {
// TODO Auto-generated method stub
}
#Override
public void onFinish(ITestContext context) {
// TODO Auto-generated method stub
}
}
you can customize this file according to you . Next what you have to do is you need to mention this listener in your Test class
#Listeners(TestListener.class)
public class TestClass{
#Test(dataProvider = "TestData" , dataProviderClass = DataProviderUtil.class)
public void test(List data) throws Exception {
try{
// your code here
}
catch(Exception e){
Log.exception(e);
}finally {
Log.endTestCase();
}
}
}

Categories