There are few important points to keep in mind for Parameterization through @Parameter annotation in TestNG:
Consider the following example :
Program :
package Package1;
import org.testng.annotations.Optional;
import org.testng.annotations.Parameters;
import org.testng.annotations.Test;
public class Pack1class1 {
@Test
@Parameters({"Parameter1","Parameter2"})
public void P1c1M1(String Parameter1 ,String Parameter2) {
System.out.println("Package1_class1_Method1");
System.out.println(Parameter1);
System.out.println(Parameter2);
}
}
testng.xml :
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite">
<parameter name="Parameter1" value="TestParm1"></parameter>
<parameter name="Parameter2" value="TestParm2"></parameter>
<test thread-count="5" name="Test">
<classes>
<class name="Package1.Pack1class1"/>
</classes>
</test> <!-- Test -->
</suite> <!-- Suite -->
-> We can give only one parameter value for one type of parameter. If we want to have multiple values then we can use data-providers. In the above example we have defined 2 parameters Parameter1 and Parameter2 with single value. The purpose of these parameters are just to give the value from testng.xml.
-> If we try to give more values by giving comma then script will consider it as one single string:
<parameter name="Parameter1" value="TestParm1"></parameter>
<parameter name="Parameter2" value="TestParm2 , TestParam3"></parameter>
In this example we have tried to give two values in parameters , but TestNg will consider it as a single parameter and output will be
TestParm2 , TestParam3
There is no way to give 2 parameter values.
-> Now in another try if we give different values by creating new line in testng.xml fil as below :
<parameter name="Parameter1" value="TestParm1"></parameter>
<parameter name="Parameter2" value="TestParm1"></parameter>
<parameter name="Parameter2" value="TestParm3"></parameter>
Here we can see that we are trying to give 2 different values to Parameter2 but while execution only the last value will be considered and output will be
TestParm3
-> Through testng.xml file the parameters can only be given at Suite and test level.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite">
<parameter name="Parameter1" value="TestParm1"></parameter>
<parameter name="Parameter2" value="TestParm1"></parameter>
<test thread-count="5" name="Test">
<parameter name="Parameter3" value="TestParm1"></parameter>
<classes>
<class name="Package1.Pack1class1"/>
</classes>
</test> <!-- Test -->
</suite> <!-- Suite -->
->In case if the parameter name is same in suite level and test level then test level parameter will get preference over suite level. So, in that case, all the classes inside that test level will share the overridden parameter, and other classes which are outside the test level will share suite level parameter.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite">
<parameter name="Parameter1" value="TestParm1"></parameter>
<parameter name="Parameter2" value="TestParm1"></parameter>
<test thread-count="5" name="Test">
<parameter name="Parameter2" value="TestParm2"></parameter>
<classes>
<class name="Package1.Pack1class1"/>
</classes>
</test> <!-- Test -->
</suite> <!-- Suite -->
So here the TesgNG will pick the value of the Parameter2 from the Test level that is TestParm2. The value at suite level will be ignored. The output of the above program will be :
Package1_class1_Method1
TestParm1
TestParm2
-> If the parameter has no value in testng.xml then we can give @Optional annotation and define he default value.
(i) Program with @Optional value but we have Parameters present in Testng.xml
package Package1;
import org.testng.annotations.Optional;
import org.testng.annotations.Parameters;
import org.testng.annotations.Test;
public class Pack1class1 {
@Test
@Parameters({"Parameter1","Parameter2"})
public void P1c1M1(@Optional ("ABC") String Parameter1 ,@Optional("XYZ")String Parameter2) {
System.out.println("Package1_class1_Method1");
System.out.println(Parameter1);
System.out.println(Parameter2);
}
}
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite">
<parameter name="Parameter1" value="TestParm1"></parameter>
<parameter name="Parameter2" value="TestParm1"></parameter>
<test thread-count="5" name="Test">
<classes>
<class name="Package1.Pack1class1"/>
</classes>
</test> <!-- Test -->
</suite> <!-- Suite -->
Since we have valid values in testng.xml for the given parameters so output of above program will be :
Package1_class1_Method1
TestParm1
TestParm1
(ii) Program with @Optional value but we don't have Parameters present in Testng.xml
package Package1;
import org.testng.annotations.Optional;
import org.testng.annotations.Parameters;
import org.testng.annotations.Test;
public class Pack1class1 {
@Test
@Parameters({"Parameter1","Parameter2"})
public void P1c1M1(@Optional ("ABC") String Parameter1 ,@Optional("XYZ")String Parameter2) {
System.out.println("Package1_class1_Method1");
System.out.println(Parameter1);
System.out.println(Parameter2);
}
}
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite name="Suite">
<parameter name="Parameter1" value="TestParm1"></parameter>
<test thread-count="5" name="Test">
<classes>
<class name="Package1.Pack1class1"/>
</classes>
</test> <!-- Test -->
</suite> <!-- Suite -->
Here we can see that there is just one parameter in testng.xml but we are passing 2 parameters in our program. In this case the optional value will be called for second parameter, Output will be :
Package1_class1_Method1
TestParm1
XYZ
-> Now there can be a situation when the parameter type in xml is
string and in method we have given
int. It means there is type mismatch in the parameter type. In this case we get the following exception:
[Utils] [ERROR] [Error]
java.lang.NumberFormatException: For input string: "ABC"