Ashwiinn Karaangutkar
Ashwiinn Karaangutkar

Reputation: 171

Null Pointer Exception while running code using TestNG

I am trying to automate a Login and Logout Scenario in TestNG and passing the browser as parameter from XML on the basis of which chromedriver() instance will be created and the code will run.I have two classes TestRunner and Login where login method gets data (username and password) TestRunner and data is fetched from excel.Exception e is getting null value as I found out while debugging. Any way to fix it?

FAILED: Registration_data("[email protected]", "ashwin123")
java.lang.NullPointerException
at com.DataDriven.Login.login(Login.java:68)
at com.DataDriven.TestRunner.Registration_data(TestRunner.java:28)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at   sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at   sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:483)
at   org.testng.internal.MethodInvocationHelper.invokeMethod(MethodInvocationHelper.java:84)
at org.testng.internal.Invoker.invokeMethod(Invoker.java:714)
at org.testng.internal.Invoker.invokeTestMethod(Invoker.java:901)
at org.testng.internal.Invoker.invokeTestMethods(Invoker.java:1231)
at     org.testng.internal.TestMethodWorker.invokeTestMethods(TestMethodWorker.java:12)
at org.testng.internal.TestMethodWorker.run(TestMethodWorker.java:111)
at org.testng.TestRunner.privateRun(TestRunner.java:767)
at org.testng.TestRunner.run(TestRunner.java:617)
at org.testng.SuiteRunner.runTest(SuiteRunner.java:334)
at org.testng.SuiteRunner.runSequentially(SuiteRunner.java:329)
at org.testng.SuiteRunner.privateRun(SuiteRunner.java:291)
at org.testng.SuiteRunner.run(SuiteRunner.java:240)
at org.testng.SuiteRunnerWorker.runSuite(SuiteRunnerWorker.java:52)
at org.testng.SuiteRunnerWorker.run(SuiteRunnerWorker.java:86)
at org.testng.TestNG.runSuitesSequentially(TestNG.java:1224)
at org.testng.TestNG.runSuitesLocally(TestNG.java:1149)
at org.testng.TestNG.run(TestNG.java:1057)
at org.testng.remote.RemoteTestNG.run(RemoteTestNG.java:111)
at org.testng.remote.RemoteTestNG.initAndRun(RemoteTestNG.java:204)

    package com.DataDriven;
    import java.util.concurrent.TimeUnit;
    import org.openqa.selenium.By;
    import org.openqa.selenium.WebDriver;
    import org.openqa.selenium.firefox.FirefoxDriver;
    public class TestRunner {

    @Test(dataProvider = "Authentication")
    public static void Registration_data(String sUserName, String sPassword)
        throws Exception {

    Login lp = new Login();
    lp.login(sUserName, sPassword);
    }

    @DataProvider
    public Object[][] Authentication() throws Exception {

    Object[][] testObjArray = ReadData.getTableArray(
            "F:\\Automation\\DataDrivenPractice\\DataFiles\\DataFile.xlsx",
            "Sheet1");

    return (testObjArray);  }  }

    package com.DataDriven;

    import java.io.File;

    import org.apache.commons.io.FileUtils;
    import org.openqa.selenium.By;
    import org.openqa.selenium.OutputType;
    import org.openqa.selenium.TakesScreenshot;
    import org.openqa.selenium.WebDriver;
    import org.openqa.selenium.chrome.ChromeDriver;

    public class Login {
     WebDriver driver = null;

     @Parameters("browser")
     @BeforeClass
    // Passing Browser parameter from TestNG xml
    public void beforeTest(String browser) {

    // If the browser is Firefox, then do this

    if (browser.equalsIgnoreCase("firefox")) {

        driver = new FirefoxDriver();

        // If browser is IE, then do this

      } else if (browser.equalsIgnoreCase("chrome")) {

        // Here I am setting up the path for my IEDriver

        driver = new ChromeDriver(); } }

     public void login(String username, String password) {
        try {
        driver.get("https://www.facebook.com/");

        driver.findElement(By.id("email")).sendKeys(username);
        driver.findElement(By.id("pass")).sendKeys(password);
        driver.findElement(By.id("loginbutton")).click();
        driver.findElement(By.linkText("Log Out")).click();
         }

       catch (Exception e) {
        File srcfile = ((TakesScreenshot) driver)
                .getScreenshotAs(OutputType.FILE);

        try {
            FileUtils.copyFile(srcfile, new File(
                    "F:\\Automation\\Screenshots\\Login.jpg"));
        } catch (Exception e1) {
            e1.printStackTrace();
        }   }  }}

        <?xml version="1.0" encoding="UTF-8"?>
        <!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
        <suite name="Suite" parallel="none">
        <test name="FirefoxTest">
         <parameter name="browser" value="chrome" />
         <classes>
         <class name="com.DataDriven.TestRunner" />
         <class name="com.DataDriven.Login" /> 
         </classes>
         </test>
         </suite>

Upvotes: 2

Views: 23204

Answers (2)

Nguyen Vu Hoang
Nguyen Vu Hoang

Reputation: 1570

There are many issues in your scripts

1 - Your classes init separately. The driver from @BeforeClass doesnot inherite into your @Test

2 - When you do

Login lp = new Login();

you have

WebDriver driver = null;
@BeforeClass is not invoked, no driver init, your driver is still null

Then

lp.login(sUserName, sPassword);

NullPointException throws because driver in following line of code is null

driver.get("https://www.facebook.com/");

Suggest action

  • You need to get driver goes through all your classes

TestBase.class

Put your @BeforeClass here

LoginPage.class, be sure you allow to cast driver into it

public LoginPage(WebDriver driver) {
    // your code here
}    

// Put login(sUserName, sPassword) method here

TestRunner.class

inherite/extends from TestBase.class
LoginPage lp = new LoginPage(driver);
lp.login(sUserName, sPassword);

Upvotes: 1

Fenio
Fenio

Reputation: 3635

Your problem is - your method beforeTest doesn't invoke. Your driver doesn't point to any type of object.

TestNG search through all your classes only for @Test annotation. How it's supposed to know that @BeforeClass annotation lies in specific class you've created?

To run @BeforeClass annotation, you either have to set extends for Login class (it won't be effective for multiple scripts) or run beforeTest method manually. Or set it to running class containing @Test annotation.

Correct me if i'm wrong. Hope it helps!

EDIT:

Move your method and WebDriver variable to Test Runner Class

 WebDriver driver = null;

 @Parameters("browser")
 @BeforeClass
// Passing Browser parameter from TestNG xml
public void beforeTest(String browser) {

// If the browser is Firefox, then do this

if (browser.equalsIgnoreCase("firefox")) {

    driver = new FirefoxDriver();

    // If browser is IE, then do this

  } else if (browser.equalsIgnoreCase("chrome")) {

    // Here I am setting up the path for my IEDriver

    driver = new ChromeDriver(); } }

TestRunner class should contain both, @Test and @BeforeClass. As TestNG reads Annotations from classes containing @Test annotation.

Upvotes: 0

Related Questions