1

I have created two class files 'LoginPage.java' and 'orangeHRM.java'

Now as part of POM, I have initialized the 'LoginPage' object in 'OrangeHRM'

LoginPage LP = new LoginPage(driver);

I have declared constructor in LoginPage file

WebDriver driver;
    public LoginPage(WebDriver driver) 
    {
        this.driver=driver;
    }

Now in the LoginPage.Java file if I use driver as a statement it is throwing NullpointerException. see the below code:

WebElement username = **driver**.findElement(By.xpath("//input[@name='txtUsername' and @id='txtUsername']"));
    WebElement password = **driver**.findElement(By.xpath("//input[@name='txtPassword' and @id='txtPassword']"));   
    WebElement loginbtn = **driver**.findElement(By.xpath("//input[@type='submit' and @id='btnLogin']"));

    public void Login(String UName,String Pwd)
    {
        username.sendKeys(UName);
        password.sendKeys(Pwd);
        loginbtn.click();
    }

Where as if I use driver inside a method in LoginPage.java it is working fine.see the below code:

By username = By.xpath("//input[@name='txtUsername' and @id='txtUsername']");
    By password = By.xpath("//input[@name='txtPassword' and @id='txtPassword']");   
    By loginbtn = By.xpath("//input[@type='submit' and @id='btnLogin']");

    public void Login(String UName,String Pwd)
    {
        **driver**.findElement(username).sendKeys(UName);
        **driver**.findElement(password).sendKeys(Pwd);
        **driver**.findElement(loginbtn).click();
    }

Can someone please explain me the reason why I should not use WebElement declaration using driver in POM model.

LoginPage with WebElement decalarion:

package common;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.testng.Assert;

public class LoginPage
{

    WebDriver driver;
    public LoginPage(WebDriver driver) 
    {
        this.driver=driver;
    }


    WebElement username = driver.findElement(By.xpath("//input[@name='txtUsername' and @id='txtUsername']"));
    WebElement password = driver.findElement(By.xpath("//input[@name='txtPassword' and @id='txtPassword']"));   
    WebElement loginbtn = driver.findElement(By.xpath("//input[@type='submit' and @id='btnLogin']"));

    public void Login(String UName,String Pwd)
    {
        username.sendKeys(UName);
        password.sendKeys(Pwd);
        loginbtn.click();
    }


    public void VerifyTitle(String actualtitle, String expectedtitle)
      {
          Assert.assertEquals(actualtitle, expectedtitle);
      }

}

OrangeHRM File:

package frameWork;

import java.util.concurrent.TimeUnit;

import org.openqa.selenium.WebDriver;
import org.openqa.selenium.chrome.ChromeDriver;
import org.testng.annotations.Test;

import common.LoginPage;

public class OrangeHRM
{

    LoginPage LP;
    public static WebDriver driver;

    @Test
    public void Login()
    {
        System.setProperty("webdriver.chrome.driver", "D://Pavani//Automation Testing//Drivers//chromedriver.exe");
         driver = new ChromeDriver();
        driver.get("https://opensource-demo.orangehrmlive.com/");
        driver.manage().window().maximize();
         LP = new LoginPage(driver);
        driver.manage().timeouts().implicitlyWait(100, TimeUnit.SECONDS);
        LP.Login("Admin", "admin123");
        String actual = "OrangeHRM";
        String expected = driver.getTitle();
        LP.VerifyTitle(actual, expected);       
    }

}

2 Answers 2

2

To explain this:

Try the below code:

public class HelloWorld{

     public static void main(String []args){
        test t=new test(5);
        System.out.println(t.a);
        System.out.println(t.b);
        System.out.println(t.c);
        System.out.println(t.d);
     }

}


     class test{
         int a;
         int b;
         public test(int val){
             this.a=val;
         }

         int c=1+this.a;
         int d=1+a;
     }

Here you can see that whatever you pass, c and d always returns 1.

This is because the declared (without assigning any value) class variables will get initialized to its default value when we create an object. So a and b will have '0' as default value.

Also, whatever class variable declaration you will make will be executed before the actual constructor code. The compiler will move class declarations to the top of your actual constructor. This ensures that first all class variables are initialized before executing the actual constructor code.

Read below answer for explanation:

https://stackoverflow.com/questions/18830103/why-instance-variables-get-initialized-before-constructor-called

So, c=1+this.a and d=1+a;

will get executed before "this.a=val" as they are class variables

Now coming to your problem:

  1. you have declared webdriver in login page ( a class varaible )
  2. Now when you create the login page object, the driver will be initialized with the value "null" ( As you have not assigned any value during class declaration)
  3. Now you were expecting this.driver=driver to get executed before :

WebElement username = driver.findElement

But as in the above example, as webelement declaration is in class level, this will get executed well before the actual constructor code.

  1. so when you try to get driver.findelement , you are trying to get findelement from a null object. Hence you get null point exception

So the solution is to call the findelement inside the constructor

 WebDriver driver;
 WebElement username;
 WebElement password;


    public LoginPage(WebDriver driver) 
    {
    this.driver=driver;
    username = this.driver.findElement(By.xpath("//input[@name='txtUsername' and @id='txtUsername']"));
    password = this.driver.findElement(By.xpath("//input[@name='txtPassword' and @id='txtPassword']"));   
    }
0

Here you are creating the new instance for the driver variable and also another instance in OrangeHRM.

Two instance will be created as it is initialized in two classes

Use driver object of class OrangeCRM in "loginpage.java" through inheritance

Try with required imports

Your code will be like

OrangeHRM.java

package com.test;

import java.util.concurrent.TimeUnit;

import org.junit.Test;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.chrome.ChromeDriver;

public class orangeHRM {
    LoginPage LP;

    public static WebDriver driver;

    @Test
    public void Login()
    {
        System.setProperty("webdriver.chrome.driver", "your chromepath");
         driver = new ChromeDriver();
        driver.get("https://opensource-demo.orangehrmlive.com/");
        driver.manage().window().maximize();
         LP = new LoginPage();
        driver.manage().timeouts().implicitlyWait(100, TimeUnit.SECONDS);
        LP.Login("Admin", "admin123");
        String actual = "OrangeHRM";
        String expected = driver.getTitle();
        LP.VerifyTitle(actual, expected);       
    }

}

LoginPage.java

package com.test;

import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;

import junit.framework.Assert;


public class LoginPage extends orangeHRM {
     //WebDriver driver;
        //public LoginPage(WebDriver driver) 
        //{
           // this.driver=driver;
        //}


        WebElement username = driver.findElement(By.xpath("//input[@name='txtUsername' and @id='txtUsername']"));
        WebElement password = driver.findElement(By.xpath("//input[@name='txtPassword' and @id='txtPassword']"));   
        WebElement loginbtn = driver.findElement(By.xpath("//input[@type='submit' and @id='btnLogin']"));

        public void Login(String UName,String Pwd)
        {
            username.sendKeys(UName);
            password.sendKeys(Pwd);
            loginbtn.click();
        }


        public void VerifyTitle(String actualtitle, String expectedtitle)
          {
              Assert.assertEquals(actualtitle, expectedtitle);
          }

}

I suggest you to study the POM approach of selenium and Core java tutorials

Modified Code as shown below based on my approach

Baseclass.java This class acts as the parent to all other classes which contains basic setup needed for selenium test can be taken as configuration class

package com.orangecrm.baseclass;

import java.io.File;
import java.io.FileInputStream;
import java.util.Properties;
import java.util.concurrent.TimeUnit;

import org.openqa.selenium.WebDriver;
import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.support.ui.WebDriverWait;

public class TestBase {
    public Properties prop;
    public FileInputStream file;
    public static WebDriver driver;
    public static WebDriverWait wait;


    public TestBase() {
        try {
            prop = new Properties();
            file = new FileInputStream("Z:/OrangeCRM/assets/property/OrangeCRM.properties");
            prop.load(file);
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

    public void intialization() {
        if (prop.getProperty("browser").contentEquals("chrome")) {
            System.setProperty("webdriver.chrome.driver",new File("Z:/OrangeCRM/assets/driver/chromedriver.exe").getAbsolutePath());
            driver = new ChromeDriver();
        } else {
            System.out.println("No browser found");
        }

        try {
            driver.manage().timeouts().pageLoadTimeout(20, TimeUnit.SECONDS);
            driver.manage().timeouts().implicitlyWait(20, TimeUnit.SECONDS);
            driver.manage().window().maximize();
            driver.get(prop.getProperty("url"));

        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("Alert Site seems very slow!!!! Please increase the page load time out in util class");
            //driver.close();
            //System.exit(0);
        }
    }
}

LoginPage.java which acts as element class should be in separate package

package com.stack;

import org.openqa.selenium.By;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
import org.openqa.selenium.support.PageFactory;

import com.orangecrm.baseclass.TestBase;

public class LoginPage extends TestBase {
     //WebDriver driver;
    //public LoginPage(WebDriver driver) 
    //{
       // this.driver=driver;
    //}


    //WebElement username = driver.findElement(By.xpath("//input[@name='txtUsername' and @id='txtUsername']"));
    //WebElement password = driver.findElement(By.xpath("//input[@name='txtPassword' and @id='txtPassword']"));   
    //WebElement loginbtn = driver.findElement(By.xpath("//input[@type='submit' and @id='btnLogin']"));

    /* Using pagefactory element*/
    @FindBy(xpath="//input[@name='txtUsername' and @id='txtUsername']")
    WebElement username;

    @FindBy(xpath="//input[@name='txtPassword' and @id='txtPassword']")
    WebElement password;

    @FindBy(xpath="//input[@type='submit' and @id='btnLogin']")
    WebElement loginbtn;

    public LoginPage(){
        PageFactory.initElements(driver, this);
    }

    public void Login(String UName,String Pwd)
    {
        username.sendKeys(UName);
        password.sendKeys(Pwd);
        loginbtn.click();
    }

    //No test cases in element class
   /* public void VerifyTitle(String actualtitle, String expectedtitle)
      {
          Assert.assertEquals(actualtitle, expectedtitle);
      }*/

}

TestOrangeHRM.java class acts as the test case where we can write our test suites using Junit or Testng but now i used Junit

package test.cloudblm.com;

import static org.junit.Assert.*;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import com.orangecrm.baseclass.TestBase;
import com.stack.LoginPage;

public class TestOrangeHRM extends TestBase {

    public TestOrangeHRM(){
        super();
    }

    @Before
    public void BrowserSetup() {
        intialization();
    }

    @Test
    public void GetTitle() {
        LoginPage loginpage=new LoginPage();
        loginpage.Login("Admin", "admin123");
        System.out.println(driver.getTitle());
        assertEquals(driver.getTitle(),"OrangeHRM");
    }

    @After
    public void TearDown() {
        driver.close();
    }


}

OrangeCRM.properties Atlast my property file will be like below

url=https://opensource-demo.orangehrmlive.com/
browser=chrome
7
  • I have not declared driver as a static variable. I have declared it as WebDriver driver; I have tried it using static but still found exception. Feb 17, 2020 at 7:02
  • Please copy paste the code where your driver is initialized i have no proper reputation to post comment orelse i would have given the comment this is not a valid answer still don't down vote this Feb 17, 2020 at 7:13
  • @ Mohamed Sulaimaan Sheriff I have added code of both LoginPage and OrangeHRM above. I have passed the driver which is intialized as driver=new ChromeDriver(); while creation of LoginPage object (LP=new LoginPage(driver)) in 'OrangeHRM' Feb 17, 2020 at 7:24
  • Please review the updated answer Feb 17, 2020 at 8:10
  • @MohamedSulaimaanSheriff In your approach how will you handle multiple test suite file?
    – PDHide
    Feb 17, 2020 at 17:23

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.