yandex-qatools / htmlelements

Html Elements is a Java framework providing easy-to-use way of interaction with web-page elements in web-page tests.
Other
272 stars 116 forks source link

When we use inner classes we get "java.lang.InstantiationException" error during element initialization #80

Open emaks opened 9 years ago

emaks commented 9 years ago

When we use inner classes we get the error during element initialization. please, look through unit test for this situation

public class NestedClassTest {
    public WebDriver driver = mock(WebDriver.class);
    WebElement arrow = mock(WebElement.class);
    WebElement link = mock(WebElement.class);

    @Before
    public void before() {
        when(driver.findElement(By.className("arrow"))).thenReturn(arrow);
        when(arrow.findElement(By.className("link"))).thenReturn(link);
    }

    @Test
    public void test() {
        NestedPageObject pageObject = new NestedPageObject();
        HtmlElementLoader.populate(pageObject, driver);

        assertThat(pageObject, notNullValue());
        assertThat(pageObject.arrow.getName(), notNullValue());
        assertThat(pageObject.arrow.link.getWrappedElement(), notNullValue());
    }

    public class NestedPageObject {
        @FindBy(className = "arrow")
        public NestedHtmlElement arrow;
    }

    public class NestedHtmlElement extends HtmlElement {
        @FindBy(className = "link")
        public NestedTypifiedElement link;

        public class NestedTypifiedElement extends TypifiedElement {
            public NestedTypifiedElement(WebElement wrappedElement) {
                super(wrappedElement);
            }
        }
    }
}

Trace

ru.yandex.qatools.htmlelements.exceptions.HtmlElementsException: java.lang.InstantiationException: ru.yandex.qatools.htmlelements.NestedClassTest$NestedHtmlElement
    at ru.yandex.qatools.htmlelements.loader.decorator.HtmlElementFactory.createTypifiedElementInstance(HtmlElementFactory.java:53)
    at ru.yandex.qatools.htmlelements.loader.decorator.HtmlElementDecorator.decorateTypifiedElement(HtmlElementDecorator.java:102)
    at ru.yandex.qatools.htmlelements.loader.decorator.HtmlElementDecorator.decorate(HtmlElementDecorator.java:66)
    at org.openqa.selenium.support.PageFactory.proxyFields(PageFactory.java:115)
    at org.openqa.selenium.support.PageFactory.initElements(PageFactory.java:107)
    at ru.yandex.qatools.htmlelements.loader.decorator.HtmlElementDecorator.decorateHtmlElement(HtmlElementDecorator.java:115)
    at ru.yandex.qatools.htmlelements.loader.decorator.HtmlElementDecorator.decorate(HtmlElementDecorator.java:70)
    at org.openqa.selenium.support.PageFactory.proxyFields(PageFactory.java:115)
    at org.openqa.selenium.support.PageFactory.initElements(PageFactory.java:107)
    at ru.yandex.qatools.htmlelements.loader.HtmlElementLoader.populatePageObject(HtmlElementLoader.java:200)
    at ru.yandex.qatools.htmlelements.loader.HtmlElementLoader.populatePageObject(HtmlElementLoader.java:190)
    at ru.yandex.qatools.htmlelements.loader.HtmlElementLoader.populate(HtmlElementLoader.java:58)
    at ru.yandex.qatools.htmlelements.NestedClassTest.test(NestedClassTest.java:36)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:47)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:44)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:271)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:70)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:238)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:63)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:53)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:229)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
    at org.junit.runner.JUnitCore.run(JUnitCore.java:160)
    at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:78)
    at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:212)
    at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:68)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:140)
Caused by: java.lang.InstantiationException: ru.yandex.qatools.htmlelements.NestedClassTest$NestedHtmlElement
    at java.lang.Class.newInstance(Class.java:427)
    at ru.yandex.qatools.htmlelements.utils.HtmlElementUtils.newInstance(HtmlElementUtils.java:35)
    at ru.yandex.qatools.htmlelements.loader.decorator.HtmlElementFactory.createTypifiedElementInstance(HtmlElementFactory.java:49)
    ... 39 more
Caused by: java.lang.NoSuchMethodException: ru.yandex.qatools.htmlelements.NestedClassTest$NestedHtmlElement.<init>()
    at java.lang.Class.getConstructor0(Class.java:3082)
    at java.lang.Class.newInstance(Class.java:412)
    ... 41 more
emaks commented 9 years ago

I guess problem in this

artkoshelev commented 9 years ago

Hi, thank you for bug report and investigation, but it looks like you create problems for yourself =). Using nested Page Object in tests is a bad practice since you don't have a single point to view/fix your application presentation part. Using nested classes limits code reuse as well. So, what's the point in using nested Page Objects and nested elements declaration?

ayan13579 commented 1 year ago

update this version ru.yandex.qatools.htmlelements to 1.20.0, in earlier version it was using newInstance() method which is deprecated now. I hope this will solve the issue.