Search code examples
seleniumtestngtestng-dataprovider

testng: how to design to run @test with multiple cases from dataprovider on different urls which are from another dataprovider?


Suppose I have a set of test cases, and I first open one url, and run the test:

@BeforeMethod
    @Parameters("browser")
    public void start(String browser) throws Exception {
    driver = new FirefoxDriver();
    driver.get(url);

}
@Test(dataProvider = "TestA", dataProviderClass = xxx.class)
public void TestA(String VariableA1, String VariableA2..){

}

@Test(dataProvider = "TestB", dataProviderClass = xxx.class)
public void TestB(String VariableB1, String VariableB2..){

}

@Test(dataProvider = "TestC", dataProviderClass = xxx.class)
public void TestC(String VariableC1, String VariableC2..){

}

And I want to run the same set of test cases on different url which also stored in one of the table from the dataprovider. How can I design to achieve this logic?:

  1. get a url urlX from the url table in the excel dataprovider.
  2. run test: TestA, TestB, TestC.
  3. then get url urlY from the url table in the excel dataprovider.
  4. run test: TestA, TestB, TestC...
  5. so on so forth..

How can I achieve that?

Thank you!


Solution

  • Take a look at TestNG factories. e.g.

    import org.testng.annotations.DataProvider;
    import org.testng.annotations.Factory;
    import org.testng.annotations.Test;
    
    import java.util.Arrays;
    import java.util.Iterator;
    
    public class DemoTest {
        private final String url;
    
        @Factory(dataProvider = "urls", dataProviderClass = xxx.class)
        public DemoTest(String url) {
            this.url = url;
        }
    
        @Test(dataProvider = "someData", dataProviderClass = DemoTest.xxx.class)
        public void something(int a, int b) {
            System.out.println(String.format("%s, %d, %d", url, a, b));
        }
    
        @Test(dataProvider = "someOtherData", dataProviderClass = DemoTest.xxx.class)
        public void somethingElse(int a, int b) {
            System.out.println(String.format("%s, %d, %d", url, a, b));
        }
    
        public static class xxx {
            @DataProvider
            public static Iterator<Object[]> urls() {
                String[] urls = {
                        "https://www.google.com/",
                        "https://inbox.google.com/",
                        "https://calendar.google.com/",
                        "https://drive.google.com/"
                };
                return Arrays.stream(urls)
                        .map(s -> new Object[]{s})
                        .iterator();
            }
    
            @DataProvider
            public static Object[][] someData() {
                return new Object[][]{
                        {1, 2},
                        {3, 4}
                };
            }
    
            @DataProvider
            public static Object[][] someOtherData() {
                return new Object[][]{
                        {4, 3},
                        {2, 1}
                };
            }
        }
    }
    

    Example output:

    https://calendar.google.com/, 1, 2
    https://calendar.google.com/, 3, 4
    https://inbox.google.com/, 1, 2
    https://inbox.google.com/, 3, 4
    https://drive.google.com/, 1, 2
    https://drive.google.com/, 3, 4
    https://www.google.com/, 1, 2
    https://www.google.com/, 3, 4
    https://calendar.google.com/, 4, 3
    https://calendar.google.com/, 2, 1
    https://inbox.google.com/, 4, 3
    https://inbox.google.com/, 2, 1
    https://drive.google.com/, 4, 3
    https://drive.google.com/, 2, 1
    https://www.google.com/, 4, 3
    https://www.google.com/, 2, 1