kgress / scaffold

A Java based Selenium WebDriver abstraction
MIT License
4 stars 7 forks source link

Update BaseWebElement's findElement and findElements with a complete By conversion to cssSelector #108

Open kgress opened 3 years ago

kgress commented 3 years ago

Summary

Currently, BaseWebElement#findElement(...) and BaseWebElement#findElement(...) will check to see if the parent and child By locators are css selectors and, if they are, combine them. We should update the logic to convert anything (except xpath) into css selectors for us. That way we can preserve the true full path. This is important for the findElements(...) method because it should perform a lookup using both the parent and the child.

Some initial brainstorm code:

private By convertToCssSelector(By by) {
        By convertedBy;

        if (by instanceof By.ById) {
            convertedBy = // convert to css
        }

        return convertedBy;
    }

    /**
     * An id is the id attribute of an element
     *
     * @param id    the id we're converting
     * @return      as {@link By#cssSelector(String)}
     */
    private By convertIdToCss(String id) {
        return By.cssSelector(String.format("#%s", id));
    }

    /**
     * The link text is the href of an element
     *
     * @param linkText  the link text we're converting
     * @return          as {@link By#cssSelector(String)}
     */
    private By convertLinkTextToCss(String linkText) {
        return By.cssSelector(String.format("[href=%s]", linkText));
    }

    /**
     * The link text is the href of an element. For partial link text, we check for contains with ^
     *
     * @param partialLinkText   the partial link text we're converting
     * @return                  as {@link By#cssSelector(String)}
     */
    private By convertPartialLinkTextToCss(String partialLinkText) {
        return By.cssSelector(String.format("[href^=%s]", partialLinkText));
    }

    /**
     * Names are the name attribute of an element
     *
     * @param name  the name we're converting
     * @return      as {@link By#cssSelector(String)}
     */
    private By convertNameToCss(String name) {
        return By.cssSelector(String.format("[name=%s]", name));
    }

    /**
     * Tag names are button, input, etc.
     *
     * @param tagName   the tagName we're converting
     * @return          as {@link By#cssSelector(String)}
     */
    private By convertTagNameToCss(String tagName) {
        return By.cssSelector(tagName);
    }

    /**
     * Class names are the class attribute of an element
     *
     * @param className     the class name we're converting
     * @return              as {@link By#cssSelector(String)}
     */
    private By convertClassNameToCss(String className) {
        return By.cssSelector(String.format(".%s", className));
    }

A/C

kgress commented 2 years ago

I think this is still a great idea. We've already worked a bit towards using exclusively By locators instead of using the WebElement constructors for elements.

In addition, we've deprecated findElement() from BaseWebElement with the intent to set its access to private and act as a helper method. Any new elements should be created and found using a constructor from a scaffold element.

We've also had a little bit of xpath update love, so we should also consider updating the xpath portion.