Учитывая, что у меня есть иерархия классов. Родительский класс, как показано ниже:

public class Utils {

    protected Driver driver;

    public Utils() {
        this.driver = new Driver();
    }

    public Utils(Driver driver,String xPath) {
        this.driver = driver;
        this.driver.waitForElement(xPath, 2);
    }

И ребенок это:

public class SelectRegisteredOwner extends Utils {


    final String newOrUsed = "//*[@id=\"root\"]/div/div[3]/div/div[2]/div/div/form/div[3]/div[2]/button[2]";


    public SelectRegisteredOwner( Driver driver) {
        super(driver,newOrUsed);
    }}

Проблема в том, что в дочернем классе в строке super(driver,newOrUsed); он жалуется:

Cannot refer to an instance field newOrUsed while explicitly invoking a constructor

и в качестве быстрого исправления предлагается рассмотреть newOrUsed как атрибут static

Есть ли в любом случае исправить эту проблему, не делая атрибут статичным?

0
Jeff 20 Дек 2019 в 18:46

3 ответа

Вы не можете использовать последнее поле newOrUsed до инициализации класса. Сделайте это статичным или переместите его в конструктор.

0
SteffenJacobs 20 Дек 2019 в 15:49

Так как поле имеет постоянное значение, вы можете сделать его static, как вы упомянули. Но так как вы не должны использовать static, я рекомендую этот подход

class Utils {

    protected Driver driver;

    public Utils() {
        this(new Driver());
    }

    public Utils(Driver driver) {
        this.driver = driver;
    }

    public void addXPath(String xPath) {
        this.driver.waitForElement(xPath, 2);
    }
}

class SelectRegisteredOwner extends Utils {

    final String newOrUsed = "//*[@id=\"root\"]/div/div[3]/div/div[2]/div/div/form/div[3]/div[2]/button[2]";

    public SelectRegisteredOwner(Driver driver) {
        super(driver);
        addXPath(newOrUsed);
    }
}

Теперь, поскольку у вас есть default и overloaded конструктор в Utils, это ясно указывает на то, что xPath не является обязательным.

Таким образом, вы можете использовать обычный метод, чтобы добавить его к своему driver после того, как он создан, поскольку добавление xPath полностью находится под контролем SelectRegisteredOwner.

0
Sunil Dabburi 20 Дек 2019 в 17:28

Это поле выглядит как константа, позволяющая идентифицировать элемент в пользовательском интерфейсе. Я бы сделал это константой и отделил бы ее от вашего подкласса:

public class Utils {

    private Driver driver;  //make them private and expose getters
    private String xPath;

    public Utils() {
        this.driver = new Driver();
    }

    public Utils(Driver driver,String xPath) {
        this.driver = driver;
        this.xPath = xPath;
        this.driver.waitForElement(xPath, 2);
    }
   protected Driver getDriver(){...}
   protected Driver getXPath(){...}
}

public class SelectRegisteredOwner extends Utils {
    public SelectRegisteredOwner( Driver driver) {
        super(driver,XPathSelector.NEW_OR_USED);
    }
}

public interface XPathSelector{
    String NEW_OR_USED = "//*[@id=\"root\"]/div/div[3]/div/div[2]/div/div/form/div[3]/div[2]/button[2]";
}
0
GabiM 20 Дек 2019 в 16:02