TestNG, 0 or multiples parameters from a xml file - java

i'm using the testNG framework. I have tests that can have parameter or not.
By exemple i could have the following xml :
<?xml version="1.0" encoding="UTF-8"?>
<suite name="Suite" parallel="tests">
<test name="FlowTest0">
<parameter name="node" value="http://192.168.117.135:5555/wd/hub"/>
<parameter name="name" value="nameTest0"/>
<parameter name="direction" value="IN"/>
<classes>
<class name="selenium.test.flow.FlowSaveTest"/>
</classes>
</test>
</suite>
Or i could have this one :
<?xml version="1.0" encoding="UTF-8"?>
<suite name="Suite" parallel="tests">
<test name="FlowTest0">
<parameter name="node" value="http://192.168.117.135:5555/wd/hub"/>
<classes>
<class name="selenium.test.flow.FlowSaveTest"/>
</classes>
</test>
</suite>
Or no parameters at all or a lot more.
Then in my test case i get the parameters this way :
#Parameters({"name", "direction"})
public void initTest(String name, String direction) {
//code of the method
}
What i want is to be able to pass a variable number of value depending what i have in the xml. Can i do this with the testNG parameters annotation ?
EDIT 1 :
I would expect something like the declaration of the printf declaration in C, something like :
#Parameters("node", Something that will get all the paramaters)
#BeforeTest
public void initTest(Object ...) {
}

You can inject the ITestContext and get all attributes from there:
#Test
public void initTest(ITestContext context) {
Map<String, String> params = context.getCurrentXmlTest().getAllParameters();
// ...
}

Related

TestNG get the value of "test" level parameter from "ISuiteListener" class's "onStart" method

In my TestNG.xml file , I have two different values for Test level parameter, "TestRailRunId".
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "https://testng.org/testng-1.0.dtd">
<suite thread-count="4" name="Change_Management_Regression_Suite" parallel="tests">
<listeners>
<listener class-name="com.sam.reporting.SuiteListener" />
<listener class-name="com.sam.reporting.Listeners" />
</listeners>
<parameter name="browser" value="Chrome" />
<parameter name="browserVersion" value="104" />
<test name="CM-04">
<parameter name="TestRailRunId" value="200" />
<classes>
<class name="com.sam.testdata.TC01"/>
</classes>
</test> <!-- Test -->
<test name="CM-04">
<parameter name="TestRailRunId" value="201" />
<classes>
<class name="com.sam.testdata.TC02"/>
</classes>
</test> <!-- Test -->
</suite>
So in my "SuiteListener" class I implements ISuiteListener class. So in it's onStart method,
I want to get the TestRailRunId value from current test.
IS this possible? If so please help.
Currently what I did was defining it in Suite level and using below code snippet ,get the value.
String TestRailRunId = suite.getXmlSuite().getParameter("TestRailRunId");
Here is the current full code.
#Override
public void onStart(ISuite suite) {
String TestRailRunId = suite.getXmlSuite().getParameter("TestRailRunId");
}

Appium / selenium: testNG parallel execution not working

i am using appium and selenium.
i am trying to rum it parallel (one case after another case)
my first case (forgot password is running properly ) and after that execution is just stop.
can anyone help me with this?
i have attached testng.xml , and testbase file. also login and forgot password scripts.
i guess there is some issues with annotations.
i have tried few but now working.
can anyone help me with this?
Thanks!!!
Here my code looks like:
1.testng.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite">
<test thread-count="5" name="Test" parallel="classes">
<classes>
<class name="com.live.testcase.TC0001ForgotPassword" />
<class name="com.live.testcase.TC0002Login" />
<class name="com.live.testcase.TC0003Dashboard" />
<class name="com.live.testcase.TC0004Activity" />
<class name="com.live.testcase.TC0005MoveMoney" />
<class name="com.live.testcase.TC0006InternationalTransfer" />
<class name="com.live.testcase.TC0007Integration" />
<class name="com.live.testcase.TC0008Account" />
</classes>
</test> <!-- Test -->
</suite> <!-- Suite -->
2. testbase.java
public class testBase {
private String reportDirectory = "reports";
private String reportFormat = "xml";
private String testName = "Untitled";
protected IOSDriver<IOSElement> driver = null;
#BeforeSuite
public void setup() throws MalformedURLException {
DesiredCapabilities dc = new DesiredCapabilities();
dc.setCapability("reportDirectory", reportDirectory);
dc.setCapability("reportFormat", reportFormat);
dc.setCapability("testName", testName);
dc.setCapability(MobileCapabilityType.UDID, "afb65172e9b47b01482d912dede58515819748a3");
dc.setCapability(IOSMobileCapabilityType.BUNDLE_ID, "com.novo.ios.dev");
driver = new IOSDriver<IOSElement>(new URL("http://localhost:4723/wd/hub"), dc);
driver.setLogLevel(Level.INFO);
}
#AfterSuite
public void teardown() {
}
}
3.Forgot password
public class TC0001ForgotPassword extends testBase {
#Test
public void ForgotPassword() throws InterruptedException {
// Test case for blank email address.
driver.findElement(By.xpath("//*[#text='Forgot Password?']")).click();
driver.findElement(By.xpath("//*[#placeholder='Email']")).sendKeys("Automationtesting#banknovo.com");
driver.findElement(By.xpath("//*[#text='Done']")).click();
Thread.sleep(1000);
driver.findElement(By.xpath("//*[#text='CONFIRM']")).click();
Thread.sleep(5000);
driver.findElement(By.xpath("//*[#text='(MM/DD/YYYY)']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='Done']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='CONFIRM']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='1']")).click();
driver.findElement(By.xpath("//*[#text='2']")).click();
driver.findElement(By.xpath("//*[#text='3']")).click();
driver.findElement(By.xpath("//*[#text='4']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='CONFIRM']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='CONFIRM']")).sendKeys("111111");
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='CONFIRM']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#placeholder='Password']")).sendKeys("Novo#2019");
driver.findElement(By.xpath("//*[#placeholder='Confirm Password']")).sendKeys("Novo#2019");
Thread.sleep(2000);
driver.findElement(
By.xpath("(//*[#class='UIAView' and ./parent::*[#class='UIAScrollView']]/*[#text='icEyeOpen'])[1]"))
.click();
driver.findElement(By.xpath("//*[#text='icEyeOpen']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='RESET PASSWORD']")).click();
Thread.sleep(2000);
driver.findElement(By.xpath("//*[#text='DONE']")).click();
}
4. Login
package com.live.testcase;
import org.testng.annotations.Test;
import org.openqa.selenium.By;
import com.live.common.testBase;
public class TC0002Login extends testBase {
#Test
public void TC000001_Blank_Email_Password() {
// Test case for blank email address.
driver.findElement(By.xpath("//*[#text='LOG IN']")).click();
driver.findElement(By.xpath("//*[#text='OK']")).click();
}
#Test
public void TC000002_Invailid_Email() throws Exception {
// Test case for invalid email addresses
driver.findElement(By.xpath("//*[#placeholder='Email']")).sendKeys("automationtesting");
driver.findElement(By.xpath("//*[#placeholder='Password']")).sendKeys("Novo");
driver.findElement(By.xpath("//*[#text='LOG IN']")).click();
driver.findElement(By.xpath("//*[#text='OK']")).click();
}
#Test
public void TC000003_Invailid_Password() throws Exception {
// Test case for invalid email addresses
driver.findElement(By.xpath("//*[#placeholder='Email']")).clear();
driver.findElement(By.xpath("//*[#placeholder='Password']")).clear();
driver.findElement(By.xpath("//*[#placeholder='Password']")).sendKeys("Novo#2019");
driver.findElement(By.xpath("//*[#text='LOG IN']")).click();
driver.findElement(By.xpath("//*[#text='OK']")).click();
}
#Test
public void TC000004_Valid_Email_Password() throws Exception {
// Test case for Valid email addresses & password
driver.findElement(By.xpath("//*[#placeholder='Email']")).sendKeys("automationtesting#banknovo.com");
driver.findElement(By.xpath("//*[#placeholder='Password']")).sendKeys("Novo#2019");
driver.findElement(By.xpath("//*[#text='LOG IN']")).click();
}
}
5. pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.novo.app</groupId>
<artifactId>com.novo.app</artifactId>
<version>0.0.1-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>io.appium</groupId>
<artifactId>java-client</artifactId>
<version>7.1.0</version>
</dependency>
<dependency>
<groupId>org.testng</groupId>
<artifactId>testng</artifactId>
<version>6.14.3</version>
</dependency>
</dependencies>
</project>
I assume this could be the issue:
You instruct testng to run parallel at suite tag not at test tag.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite" thread-count="5" parallel="classes">
<test name="Test">
<classes>
<class name="com.live.testcase.TC0001ForgotPassword" />
<class name="com.live.testcase.TC0002Login" />
<class name="com.live.testcase.TC0003Dashboard" />
<class name="com.live.testcase.TC0004Activity" />
<class name="com.live.testcase.TC0005MoveMoney" />
<class name="com.live.testcase.TC0006InternationalTransfer" />
<class name="com.live.testcase.TC0007Integration" />
<class name="com.live.testcase.TC0008Account" />
</classes>
</test> <!-- Test -->
As per Parallelism and time-outs chapter:
The parallel attribute on the <suite> tag can take one of following values:
<suite name="My suite" parallel="methods" thread-count="5">
<suite name="My suite" parallel="tests" thread-count="5">
<suite name="My suite" parallel="classes" thread-count="5">
<suite name="My suite" parallel="instances" thread-count="5">
So my expectation is that you need to amend your testng.xml to look like:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite" parallel="tests" configfailurepolicy="continue" verbose="2">
<test name="TC0001ForgotPassword">
<classes>
<class name="com.live.testcase.TC0001ForgotPassword"/>
</classes>
</test>
<test name="TC0002Login">
<classes>
<class name="com.live.testcase.TC0002Login"/>
</classes>
</test>
<test name="TC0003Dashboard">
<classes>
<class name="com.live.testcase.TC0003Dashboard"/>
</classes>
</test>
<test name="TC0004Activity">
<classes>
<class name="com.live.testcase.TC0004Activity"/>
</classes>
</test>
<test name="TC0005MoveMoney">
<classes>
<class name="com.live.testcase.TC0005MoveMoney"/>
</classes>
</test>
<test name="TC0006InternationalTransfer">
<classes>
<class name="com.live.testcase.TC0006InternationalTransfer"/>
</classes>
</test>
<test name="TC0007Integration">
<classes>
<class name="com.live.testcase.TC0007Integration"/>
</classes>
</test>
<test name="TC0008Account">
<classes>
<class name="com.live.testcase.TC0008Account"/>
</classes>
</test>
</suite>
More information including sample project: Parallel Tests Execution

TestNG Based Selenium Tests not running in Parallel

I am using the below TestNG Config to enable parallel execution of Selenium tests.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Test-Automation" parallel="methods" thread-count="2" verbose="1">
<test name="Suite Test">
<classes>
<class name="SampleTest">
<methods>
<include name="firstTest"/>
<include name="secondTest"/>
<include name="thirdTest"/>
</methods>
</class>
</classes>
</test>
</suite>
Java Code:
#Test(dataProvider = "TestData")
public void firstTest(String data){
//Code
}
#Test(dataProvider = "TestData")
public void secondTest(String data){
//Code
}
#Test(dataProvider = "TestData")
public void thirdTest(String data){
//Code
}
The Selenium tests are expected to run in parallel. I expect 2 browsers to be open and run the test script.
But I see only 1 browser and all 3 tests run one after the other and not in parallel. I have tried using test, methods, class, instance options for "parallel" attribute.
Any help?
This is due to a bug in TestNG 6.13.1 [ See GITHUB-1636 for more details ]
I have fixed this in the latest SNAPSHOT of TestNG (6.14-SNAPSHOT) and this should be available for use in the released version of TestNG (6.14).
But until then, please alter your suite xml file to look like below :
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Test-Automation" parallel="methods" thread-count="2" verbose="1">
<test name="Suite Test" parallel="methods" thread-count="2" verbose="1">
<classes>
<class name="SampleTest">
<methods>
<include name="firstTest"/>
<include name="secondTest"/>
<include name="thirdTest"/>
</methods>
</class>
</classes>
</test>
</suite>
The work-around is basically to add the attributes parallel="methods" thread-count="2" at the <test> level also.
Seperate all the test and then try with parallel="test"
<test name="Suite Test1">
<classes>
<class name="//..//packg name..SampleTest">
</class>
</classes>
</test>
<test name="Suite Test2">
<classes>
<class name="//..//SampleTest">
</class>
</classes>
</test>
<test name="Suite Test3">
<classes>
<class name="//..//packg name..SampleTest">
</class>
</classes>
</test>
</suite>

TestNG inherit #Parameters from parent class

I'm trying to get to work a stub for concurrent cross browser test framework using TestNG. BUT seems I cannot get #Parameters from parent class and keep getting
Parameter 'browsername' is required by #Configuration on method setup but has not been marked #Optional or defined
at org.testng.internal.Parameters.createParameters(Parameters.java:155)
at org.testng.internal.Parameters.createParameters(Parameters.java:358)
at org.testng.internal.Parameters.createConfigurationParameters(Parameters.java:86)
at org.testng.internal.Invoker.invokeConfigurations(Invoker.java:199)
at org.testng.internal.Invoker.invokeConfigurations(Invoker.java:138)
at org.testng.internal.TestMethodWorker.invokeBeforeClassMethods(TestMethodWorker.java:175)
at org.testng.internal.TestMethodWorker.run(TestMethodWorker.java:107)
at org.testng.TestRunner.privateRun(TestRunner.java:767)
at org.testng.TestRunner.run(TestRunner.java:617)
at org.testng.SuiteRunner.runTest(SuiteRunner.java:348)
at org.testng.SuiteRunner.runSequentially(SuiteRunner.java:343)
at org.testng.SuiteRunner.privateRun(SuiteRunner.java:305)
at org.testng.SuiteRunner.run(SuiteRunner.java:254)
TestNG.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="1265_Suite" parallel="tests" verbose="2" thread-count="2" preserve-order="true">
<test name="92" parallel="false" preserve-order="true">
<classes>
<class name="com.javacodegeeks.testng.maven.BaseTest"/>
<class name="com.javacodegeeks.testng.maven.ChildTest"/>
<parameter name="browsername" value="chrome"/>
</classes>
</test>
<test name="93" parallel="false" preserve-order="true">
<classes>
<class name="com.javacodegeeks.testng.maven.BaseTest"/>
<class name="com.javacodegeeks.testng.maven.ChildTest"/>
<parameter name="browsername" value="firefox"/>
</classes>
</test>
</suite>
BaseTest
public class BaseTest extends Assert {
protected String browser;
#BeforeClass
#Parameters({"browsername"})
public void setup(String browsername) {
System.err.println("Browser name in #BeforeClass is " + browsername);
this.browser = browsername;
}
}
ChildTest
public class ChildTest extends BaseTest {
#Test
public void test() {
System.out.println(browser);
}
}
I didn't find enough information on how to get this to work so if you have any ideas I would like to hear them.
Already checked but not enough info:
TestNG Annotations in a Superclass
Try again with <parameter> nodes on the <test> nodes (and BaseTest should be useless):
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="1265_Suite" parallel="tests" verbose="2" thread-count="2" preserve-order="true">
<test name="92" parallel="false" preserve-order="true">
<parameter name="browsername" value="chrome"/>
<classes>
<!--class name="com.javacodegeeks.testng.maven.BaseTest"/-->
<class name="com.javacodegeeks.testng.maven.ChildTest"/>
</classes>
</test>
<test name="93" parallel="false" preserve-order="true">
<parameter name="browsername" value="firefox"/>
<classes>
<!--class name="com.javacodegeeks.testng.maven.BaseTest"/-->
<class name="com.javacodegeeks.testng.maven.ChildTest"/>
</classes>
</test>
</suite>

How to use testNG #Parameters in #BeforeSuite to read resource file

I am using testNG with Selenium webdriver2.0.
In my testNG.xml I have
<suite data-provider-thread-count="2" name="selenium FrontEnd Test" parallel="false" skipfailedinvocationCounts="false" thread-count="2">
<parameter name="config_file" value="src/test/resources/config.properties/"/>
<test annotations="JDK" junit="false" name="CarInsurance Sanity Test" skipfailedinvocationCounts="false" verbose="2">
<parameter name="config-file" value="src/test/resources/config.properties/"/>
<groups>
<run>
<include name="abstract"/>
<include name="Sanity"/>
</run>
</groups>
<classes>
</classes>
</test>
</suite>
In java file
#BeforeSuite(groups = { "abstract" } )
#Parameters(value = { "config-file" })
public void initFramework(String configfile) throws Exception
{
Reporter.log("Invoked init Method \n",true);
Properties p = new Properties();
FileInputStream conf = new FileInputStream(configfile);
p.load(conf);
siteurl = p.getProperty("BASEURL");
browser = p.getProperty("BROWSER");
browserloc = p.getProperty("BROWSERLOC");
}
Getting error as
AILED CONFIGURATION: #BeforeSuite initFramework
org.testng.TestNGException:
Parameter 'config-file' is required by #Configuration on method initFramework
but has not been marked #Optional or defined in
How to use #Parameters for resource file?
Looks like your config-file parameter is not defined at the <suite> level. There are several ways to solve this:
1. Make sure the <parameter> element is defined within <suite> tag but outside of any <test>:
<suite name="Suite1" >
<parameter name="config-file" value="src/test/resources/config.properties/" />
<test name="Test1" >
<!-- not here -->
</test>
</suite>
2. If you want to have the default value for the parameter in the Java code despite the fact it is specified in testng.xml or not, you can add #Optional annotation to the method parameter:
#BeforeSuite
#Parameters( {"config-file"} )
public void initFramework(#Optional("src/test/resources/config.properties/") String configfile) {
//method implementation here
}
EDIT (based on posted testng.xml):
Option 1:
<suite>
<parameter name="config-file" value="src/test/resources/config.properties/"/>
<test >
<groups>
<run>
<include name="abstract"/>
<include name="Sanity"/>
</run>
</groups>
<classes>
<!--put classes here -->
</classes>
</test>
</suite>
Option 2:
#BeforeTest
#Parameters( {"config-file"} )
public void initFramework(#Optional("src/test/resources/config.properties/") String configfile) {
//method implementation here
}
In any case, I would recommend not having two parameters with almost identical names, identical values, and different scope.
You want to use #Parameter in #BeforeSuite. Suite level parameters are parsed once the suite begins execution and I believe TestNG invokes #BeforeSuite even before the suite is processed:
Here is a workaround: add ITestContext in method parameters to inject
#BeforeSuite(groups = { "abstract" } )
#Parameters({ "configFile" })
public void initFramework(ITestContext context, String configFile) throws Exception {

Categories