Data Providers for BeforeMethod capabilities - java

Is there a way to use Data Providers for BeforeMethod function?
I would like to run parallel tests for number of different devices, so I would like to use parameters to setup capabilities. But I want to have a different way than using testng.xml.

You can get the data passed to the test by the data provider in your BeforeMethod by having Object[] parameter.
#BeforeMethod
public void beforeMethod(Object[] data) {
//.......
}
Assume the following code:
#Test(dataProvider = "dataOne")
public void testMethodOne(String one, int two) {
}
#Test(dataProvider = "dataTwo")
public void testMethodTwo(int one) {
}
#DataProvider
public Object[][] dataOne() {
return new Object[][]{ {"a", 1} };
}
#DataProvider
public Object[][] dataTwo() {
return new Object[][]{ {1} };
}
In order to get the data passed by the data provider before it reaches the test methods, you define a before method as below. I have added Method m parameter as well. This would help to identify the running test case. Object[] data contains the data passed by the data provider. If you have added this argument, then testNG would automatically pass the data to the before method.
#BeforeMethod
public void beforeMethod(Method m, Object[] data) {
if(m.getName().equals("testMethodOne")) {
String x = (String) data[0];
int y = (int) data[1];
} else if(m.getName().equals("testMethodTwo")) {
int x = (int) data[0];
}
}

Related

Can we make sure #beforesuite gets called before dataprovider?

Can we follow the below method to initialise the test data? There are 2 points I want to implement.
Need to initialise/load the test data once from the file and use the same test data in all dataproviders.Thought to implement test data loader in #beforesuite class.
Need data from dataprovider and a parameter from testNG file at the same time in #test method.
#BeforeSuite
#Parameters(value = { "test_data_file" })
public static synchronized void init(String test_data_file) {
TestDataFactory.load(test_data_file);
}
#Test(dataProvider="dp_dummy",dataProviderClass = DP_1.class)
public void testDummyAPI(TestData test_data,ITestContext context){
String param = context.getCurrentXmlTest().getParameter("param");
}
#DataProvider(name = "dp_dummy")
public Object[][] getDataFromDataprovider(ITestContext context) {
List<TestData> test_data_collection = TestDataFactory.getTestData(targated_test_data);
Object[][] test_data_set = new Object[test_data_collection.size()][1];
for(TestData test_data : test_data_collection)
test_data_set[i++][0] = test_data;
return test_data_set;}
Assuming you are creating your test_data_set correctly you can achieve your second point like this
#Test(dataProvider="dp_dummy",dataProviderClass = DP_1.class)
public void testDummyAPI( String p, Object[][] ob){
System.out.println(p);
System.out.println(ob[0][0]);
}
#DataProvider(name = "dp_dummy")
public Object[][] getDataFromDataprovider(ITestContext context) {
List<TestData> test_data_collection = TestDataFactory.getTestData(targated_test_data);
Object[][] test_data_set = new Object[test_data_collection.size()][1];
for(TestData test_data : test_data_collection)
test_data_set[i++][0] = test_data;
String param = context.getCurrentXmlTest().getParameter("param");
return new Object[][] {
{ param, test_data_set}
};
}

Selenium java testNG: Is it possible to use dataprovider data partially in testng test method

I am new to Page-Object model automation using selenium and java. I am using the Page Object model and have each page as a single class and the actions in that page as methods.Using excel to keep read test data. I have a test for searching for client using various parameters like client number, policy number, surname, firstname, webrefernce, email eand many more...... Now I have to provide all parameters in method signature otherwise test is failing with dataprovider mismatch error. I have a GetData method which provide string array from excelsheet specified.
Is it possible to make parameters optional so that I can specify only the parameters required for that particular test in the test method's signature.? In actual test there are 15 parameters and additional combinations. (If this is not possible, I have to split the data in to 16 different tab and define data providers for each tests separately). Or any other way to achieve this? Thanks
Current code:
#DataProvider(name="ClientSearchData")
public String[][] getTestData() {
String[][] testRecords = getData("TestData_igo4.xlsx","ClientSearch");
return testRecords;
}
#BeforeTest
public void setUp() {
init();
}
#Test(dataProvider="ClientSearchData")
public void verifyClientSearchByClientNumber(String clientnumber, String policynumber, String surname, String webreference, String email) {
//code for search by clientnumber
}
#Test(dataProvider="ClientSearchData")
public void verifyClientSearchByPolicyNumber(String clientnumber, String policynumber, String surname, String webreference, String email) {
//Code for search by policynumber
}
I want something like the following to avoid unnecessary parameters for each tests..
#DataProvider(name="ClientSearchData")
public String[][] getTestData() {
String[][] testRecords = getData("TestData.xlsx","ClientSearch");
return testRecords;
}
#BeforeTest
public void setUp() {
init();
}
#Test(dataProvider="ClientSearchData")
public void verifyClientSearchByClientNumber(String clientnumber) {
//code for search by clientnumber
}
#Test(dataProvider="ClientSearchData")
public void verifyClientSearchByPolicyNumber(String policynumber) {
//Code for search by policynumber
}
I think what you are looking is Varargs.
You can simply do like below
#DataProvider(name = "testData")
public static Object[][] testDataProvider() {
return new Object[][] {new String[]{"a","b","c"}};
}
#Test(priority=3,dataProvider = "testData")
public void test1(String... str1) {
System.out.println("first string"+" "+str1[0]);
}
#Test(priority=4,dataProvider = "testData")
public void test2(String... str2) {
System.out.println("second string"+" " + str2[1]);
}
The above prints
first string a
second string b
In above code just adjust data provider according to your getTestData
Three dots ... is the key here
EDIT:
You can actually do it without Varargs. The below also prints same
#Test(priority=3,dataProvider = "testData")
public void test1(String str1[] ) {
System.out.println("first string"+" "+str1[0]);
}
#Test(priority=4,dataProvider = "testData")
public void test2(String str2[]) {
System.out.println("second string"+" " + str2[1]);
}
You can model your dataprovider based on the method calling it. What I would do is probably write logic based on method name. Pass the Method object to your dataprovider, based on the name of the method, create your Object[][].
say
public Object[][] dp(Method m) {
key = m.getName.replace("verifyClientSearchBy","");
//From excel data, just fetch key column's values or put
//logic here whatever is convenient
//Build your Object[][] with only one value

How to custom objects from TestNG Dataprovider

I have the below DataProvider in TestNG. It has List of custom Objects called
DataSheet[]. I need to pass it to Test method individually but it returns as array.
#DataProvider(name="accountsDetails")
public static Object[][] getData()
{
List<DataSheet> csvValues= CSVReaderUtils.getCSVValues(csvFilePath);
DataSheet[] array = csvValues.toArray(new DataSheet[csvValues.size()]);
return new Object[][]{{array}};
}
#Test(dataProvider="accountsDetails")
public void loginTest(DataSheet data)
{
}
I don't have to iterate in the Test method, It is possible to return ? How to return from data provider method.
Any help is much appreciated.
you can always do something like this:
#DataProvider(name="accountsDetails")
public static Object[][] getData()
{
List<DataSheet> csvValues= CSVReaderUtils.getCSVValues(csvFilePath);
DataSheet[] array = csvValues.toArray(new DataSheet[csvValues.size()]);
Object[][] obj=new Object[numberOfRows][numberOfColumns];
for(int i=0;i< array.length; i++) {
obj[i][0]=array[i];
}
return obj;
}
Please note this is not tested code. but you should get the basic idea.

How to the get test data (provided by dataprovider) in the method "onTestStart" of iTestListener

So the problem I am trying to solve is :
I have test class and a #test method runtest which receives data from a data provider. I want to perform some action based on the test data run test is going to receive from the data provider, before starting the runtest method.
For this I was looking at iTestListener, it has a method onTestStart but I am not able to figure out how to get the test data for that instance of run in the method.
Any other good approach is welcome.
Create a class extending TestListenerAdapter
public class TestListener extends TestListenerAdapter {
#Override
public void onTestStart(ITestResult tr) {
super.onTestStart(tr);
Object[] params = tr.getParameters();
String a = (String)params[0];
int b = (int)params[1];
//Add whatever you want to do before the test case starts
}
}
Add annotation to your test class
#Listeners(ResultReporter.class)
public class CoreSingleApplicant1TestCase {
#Test(dataprovider = "dataprovider",dataProviderClass = StaticProvider.class))
public void runtest(String a, int b){
}
}
Dataprovider class
public class StaticProvider {
#DataProvider(name = "create")
public static Object[][] createData() {
return new Object[][] {
new Object[] {
{"String", 1},
{"Integer",2} }
}
}
}

Can a JUnit testmethod have a argument?

import java.util.regex.Pattern;
public class TestUI {
private static Pattern p = Pattern.compile("^[A-Za-z0-9()+-]+$");
public static void main(String[] args) {
// Test case1
String[] str=test();
System.out.println(str[0]+str.length);
match("Alphanumeric(Text)");
}
private static String[] test() {
boolean res;
String[] array={"a","b","c","d","e"};
for(int i=0;i<array.length;i++){
System.out.println(match(array[i]));
res=match(array[i]);
if(res=true)
calltomethod(array);
}
return array;
}
private static boolean match(String s) {
return p.matcher(s).matches();
}
}
In the above code I need to pass the array as a argument to a JUnit method, the above code will be present in a JUnit class, can I have these kind of methods in a JUnit class and a test =method with argument?
You should take a look at parameterized unit tests (introduced in JUnit 4).
Daniel Mayer's blog has an example of this.
Another, more simple example is on mkyong's webpage
Yes you can with the Theories Runner in JUnit 4.4
#RunWith(Theories.class)
public class TheorieTest {
#DataPoints
public static String[] strings={"a","b","c","d","e"};
private static Pattern p = Pattern.compile("^[A-Za-z0-9()+-]+$");
#Theory
public void stringTest(String x) {
assertTrue("string " + x + " should match but does not", p.matcher(x).matches());
}
}
For more details:
Junit 4.4 Release Notes
Blog
yes, it can. recently i started zohhak project. it lets you write:
#TestWith({
"25 USD",
"38 GBP",
"null"
})
public void testMethod(Money money) {
...
}
You can't directly pass parameters to test methods with JUnit. TestNG allows it, though:
//This method will provide data to any test method that declares that its Data
// Provider is named "test1"
#DataProvider(name = "test1")
public Object[][] createData1() {
return new Object[][] {
{ "Cedric", new Integer(36) },
{ "Anne", new Integer(37)},
};
}
//This test method declares that its data should be supplied by the Data Provider
//named "test1"
#Test(dataProvider = "test1")
public void verifyData1(String n1, Integer n2) {
System.out.println(n1 + " " + n2);
}
will print:
Cedric 36
Anne 37

Categories

Resources