TestNG

Java - Testing
Videos
Articles
Why
Using TestNG with Maven

@Test(expectedExceptions = { OrderUpdateException.class, OrderNotFoundException.class })

<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd" >
<suite name="Suite1" verbose="1" >
  <test name="Nopackage" >
    <classes>
       <class name="NoPackageTest" />
    </classes>
  </test>

  <test name="Regression1">
    <classes>
      <class name="test.sample.ParameterSample"/>
      <class name="test.sample.ParameterTest"/>
    </classes>
  </test>
</suite>

// A suite contains multiple test cases

// You can specify package names instead of class names: 
<suite name="Suite1" verbose="1" >
  <test name="Regression1"   >
    <packages>
      <package name="test.sample" />
   </packages>
 </test>
</suite>

// You can also specify groups and methods to be included and excluded: 

<test name="Regression1">
  <groups>
    <run>
      <exclude name="brokenTests"  />
      <include name="checkinTests"  />
    </run>
  </groups>

  <classes>
    <class name="test.IndividualMethodsTest">
      <methods>
        <include name="testMethod" />
      </methods>
    </class>
  </classes>
</test>

// You can also define new groups inside testng.xml and specify additional details in
// attributes, such as whether to run the tests in parallel, how many threads to use, 
// whether you are running JUnit tests, etc...  
// By default, TestNG will run your tests in the order they are found in the XML file. 
// If you want the classes and methods listed in this file to be run in an unpredictible 
// order, set the preserve-order attribute to false.

<test name="Regression1" preserve-order="false">
  <classes>
    <class name="test.Test1">
      <methods>
        <include name="m1" />
        <include name="m2" />
      </methods>
    </class>
    <class name="test.Test2" />
  </classes>
</test>

// We can have multiple xml files
java org.testng.TestNG testng1.xml [testng2.xml testng3.xml ...]

java org.testng.TestNG testng.xml

// We can put the switches into a file and tell TestNG to use that file
java org.testng.TestNG @c:\command.txt

// Passing properties on the command line of the Java Virtual Machine
java -Dtestng.test.classpath="c:/build;c:/java/classes;" org.testng.TestNG testng.xml

// Running tests that belong to groups
java org.testng.TestNG -groups windows,linux -testclass org.test.MyTest

// Not only can you declare that methods belong to groups, but you can also specify groups 
// that contain other groups. Then TestNG can be invoked and asked to include a certain 
// set of groups (or regular expressions) while excluding another set.  This gives you maximum
//  flexibility in how you partition your tests and doesn't require you to recompile anything if 
// you want to run two different sets of tests back to back.

// Groups are specified in your testng.xml file and can be found either under the <test> or 
// <suite> tag. Groups specified in the <suite> tag apply to all the <test> tags underneath. 
// Note that groups are accumulative in these tags: if you specify group "a" in <suite> and "b" 
// in <test>, then both "a" and "b" will be included. 

<include name="windows.*"/>
<exclude name="windows.*"/>

// We can include or exclude groups
<test name="Test1">
  <groups>
    <run>
      <include name="windows.*"/>
    </run>
  </groups>

  <classes>
    <class name="example1.Test1"/>
  </classes>
</test>

// We can also exclude or include individual methods: 
<test name="Test1">
  <classes>
    <class name="example1.Test1">
      <methods>
        <include name=".*enabledTestMethod.*"/>
        <exclude name=".*brokenTestMethod.*"/>
      </methods>
     </class>
  </classes>
</test>

// This can come in handy to deactivate a single method without having to recompile anything, 
// but I don't recommend using this technique too much since it makes your testing framework 
// likely to break if you start refactoring your Java code (the regular expressions used in the 
// tags might not match your methods any more). 

// Groups can also include other groups. These groups are called "MetaGroups".  For example, 
// you might want to define a group "all" that includes "checkintest" and "functest".  "functest" 
// itself will contain the groups "windows" and "linux" while "checkintest will only contain 
// "windows".  Here is how you would define this in your property file: 
<test name="Regression1">
  <groups>
    <define name="functest">
      <include name="windows"/>
      <include name="linux"/>
    </define>

    <define name="all">
      <include name="functest"/>
      <include name="checkintest"/>
    </define>

    <run>
      <include name="all"/>
    </run>
  </groups>

  <classes>
    <class name="test.sample.Test1"/>
  </classes>
</test>

// We can define groups at the class level and then add groups at the method level: 
@Test(groups = { "checkin-test" })
public class All {

  @Test(groups = { "func-test" )
  public void method1() { ... }

  public void method2() { ... }
}
// In this class, method2() is part of the group "checkin-test", which is defined at the class 
// level, while method1() belongs to both "checkin-test" and "func-test". 

// Parameters are scoped. In testng.xml, you can declare them either under a <suite> tag 
// or under <test>. If two parameters have the same name, it's the one defined in <test> 
// that has precedence. This is convenient if you need to specify a parameter applicable to 
// all your tests and override its value only for certain tests. 

// DataProvider
// 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);
} 

// By default, the data provider will be looked for in the current test class or one of its 
// base classes. If you want to put your data provider in a different class, it needs to be 
// a static method or a class with a non-arg constructor, and you specify the class where 
// it can be found in the dataProviderClass attribute: 
public class StaticProvider {
  @DataProvider(name = "create")
  public static Object[][] createData() {
    return new Object[][] {
      new Object[] { new Integer(42) }
    };
  }
}

public class MyTest {
  @Test(dataProvider = "create", dataProviderClass = StaticProvider.class)
  public void test(Integer n) {
    // ...
  }
}

<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">

// parallel="methods": TestNG will run all your test methods in separate threads. 
// Dependent methods will also run in separate threads but they will respect the order
// that you specified. 

// parallel="tests": TestNG will run all the methods in the same <test> tag in the same 
// thread, but each <test> tag will be in a separate thread. This allows you to group all 
// your classes that are not thread safe in the same <test> and guarantee they will all 
// run in the same thread while taking advantage of TestNG using as many threads as 
// possible to run your tests. 

// parallel="classes": TestNG will run all the methods in the same class in the same 
// thread, but each class will be run in a separate thread. 

// parallel="instances": TestNG will run all the methods in the same instance in the same 
// thread, but two methods on two different instances will be running in different threads. 

@Test(threadPoolSize = 3, invocationCount = 10,  timeOut = 10000)
public void testServer() {

// In this example, the function testServer will be invoked ten times from three different 
// threads. Additionally, a time-out of ten seconds guarantees that none of the threads will 
// block on this thread forever. 

// Rerunning failed tests:
java -classpath testng.jar;%CLASSPATH% org.testng.TestNG -d test-outputs testng.xml
java -classpath testng.jar;%CLASSPATH% org.testng.TestNG -d test-outputs test-outputs\testng-failed.xml

// TestNG can run JUnit 3 and JUnit 4 tests.  All you need to do is put the JUnit jar file on 
// the classpath, specify your JUnit test classes in the testng.classNames property and set 
// the testng.junit property to true: 
<test name="Test1" junit="true">
  <classes>
    <!-- ... -->

// You can invoke TestNG from your own programs very easily: 
TestListenerAdapter tla = new TestListenerAdapter();
TestNG testng = new TestNG();
testng.setTestClasses(new Class[] { Run2.class });
testng.addListener(tla);
testng.run(); 

// This example creates a TestNG object and runs the test class Run2. It also adds a TestListener. 
// You can either use the adapter class org.testng.TestListenerAdapter or implement 
// org.testng.ITestListener yourself. This interface contains various callback methods that let you
// keep track of when a test starts, succeeds, fails, etc... 

// Similary, you can invoke TestNG on a testng.xml file or you can create a virtual testng.xml file
// yourself. In order to do this, you can use the classes found the package org.testng.xml: 
// XmlClass, XmlTest, etc... Each of these classes correspond to their XML tag counterpart. 

// For example, suppose you want to create the following virtual file: 

<suite name="TmpSuite" >
  <test name="TmpTest" >
    <classes>
      <class name="test.failures.Child"  />
    <classes>
    </test>
</suite>

// You would use the following code: 
XmlSuite suite = new XmlSuite();
suite.setName("TmpSuite");
 XmlTest test = new XmlTest(suite);
test.setName("TmpTest");
List<XmlClass> classes = new ArrayList<XmlClass>();
classes.add(new XmlClass("test.failures.Child"));
test.setXmlClasses(classes) ;

> And then you can pass this XmlSuite to TestNG:
List<XmlSuite> suites = new ArrayList<XmlSuite>();
suites.add(suite);
TestNG tng = new TestNG();
tng.setXmlSuites(suites);
tng.run(); 
// See http://testng.org/javadocs/org/testng/package-summary.html

// If the <include> and <exclude> tags in testng.xml are not enough 
// for your needs, you can use a BeanShell expression to decide whether 
// a certain test method should be included in a test run or not. You specify
// this expression just under the <test> tag:
<test name="BeanShell test">
   <method-selectors>
     <method-selector>
       <script language="beanshell"><![CDATA[
         groups.containsKey("test1")
       ]]></script>
     </method-selector>
   </method-selectors>
  <!-- ... -->

// When a <script> tag is found in testng.xml, TestNG will ignore subsequent 
// <include> and <exclude> of groups and methods in the current <test> tag:  
// your BeanShell expression will be the only way to decide whether a test method
// is included or not.

// Go to http://testng.org/doc/documentation-main.html and search for Bean Shell
// for more information.
Unless otherwise stated, the content of this page is licensed under Creative Commons Attribution-ShareAlike 3.0 License