7
votes

WebDriver: Get XPath's XPath?

est-il possible de renvoyer XPath's XPath?


0 commentaires

8 Réponses :


9
votes

Pas directement à partir de webDriver, mais vous pouvez le simuler si vous avez vraiment besoin de:

public String getElementXPath(WebDriver driver, WebElement element) {
    return (String)((JavascriptExecutor)driver).executeScript("gPt=function(c){if(c.id!==''){return'id(\"'+c.id+'\")'}if(c===document.body){return c.tagName}var a=0;var e=c.parentNode.childNodes;for(var b=0;b<e.length;b++){var d=e[b];if(d===c){return gPt(c.parentNode)+'/'+c.tagName+'['+(a+1)+']'}if(d.nodeType===1&&d.tagName===c.tagName){a++}}};return gPt(arguments[0]).toLowerCase();", element);
}


1 commentaires

C'est génial :) fonctionne parfait avec Chrome 62. Merci dflems :)



1
votes
public String getElementXPath(WebDriver driver, WebElement element) {

    String javaScript = "function getElementXPath(elt){" +
                            "var path = \"\";" +
                            "for (; elt && elt.nodeType == 1; elt = elt.parentNode){" +
                                "idx = getElementIdx(elt);" +
                                "xname = elt.tagName;" +
                                "if (idx > 1){" +
                                    "xname += \"[\" + idx + \"]\";" +
                                "}" +
                                "path = \"/\" + xname + path;" +
                            "}" + 
                            "return path;" +
                        "}" +
                        "function getElementIdx(elt){" +
                            "var count = 1;" +
                            "for (var sib = elt.previousSibling; sib ; sib = sib.previousSibling){" +
                                "if(sib.nodeType == 1 && sib.tagName == elt.tagName){" +
                                    "count++;" +
                                "}" +
                            "}" +
                            "return count;" + 
                        "}" +
                        "return getElementXPath(arguments[0]).toLowerCase();";      

    return (String)((JavascriptExecutor)driver).executeScript(javaScript, element);     

}

1 commentaires

La signature de méthode ci-dessus ne correspondait pas à la zone grisée, alors assurez-vous de faire attention à cela ...



4
votes

Les deux des réponses ci-dessus souffrent du même problème. En renvoyant le XPath complété avec la fonction .tolowercase () code> appelé, tout XPath contenant un ID avec une lettre majuscule ne fonctionnera pas.

Exemple: // div [@ Id = "AppareilBlock-1111"] code> ne fonctionnera pas sur la balise

P >

Vous pouvez toutefois simplement supprimer le .tolowercase () code> appeler le retour, mais vous allez vous retrouver avec XPath's ressemblant à ceci: // div [@ Id = "AppareilBlock- 1111 "] / div [2] / Sélectionnez [1] / OPTION [5] CODE> P>

Pour résoudre ce problème, utilisez la fonction ci-dessous. P>

public String GetElementXPath(WebElement element, WebDriver driver)
{
    return (String) ((JavascriptExecutor) driver).executeScript(
    "getXPath=function(node)" +
    "{" +
        "if (node.id !== '')" +
        "{" +
            "return '//' + node.tagName.toLowerCase() + '[@id=\"' + node.id + '\"]'" +
        "}" +

        "if (node === document.body)" +
        "{" +
            "return node.tagName.toLowerCase()" +
        "}" +

        "var nodeCount = 0;" +
        "var childNodes = node.parentNode.childNodes;" +

        "for (var i=0; i<childNodes.length; i++)" +
        "{" +
            "var currentNode = childNodes[i];" +

            "if (currentNode === node)" +
            "{" +
                "return getXPath(node.parentNode) + 
                    '/' + node.tagName.toLowerCase() + 
                    '[' + (nodeCount+1) + ']'" +
            "}" +

            "if (currentNode.nodeType === 1 && " +
                "currentNode.tagName.toLowerCase() === node.tagName.toLowerCase())" +
            "{" +
                "nodeCount++" +
            "}" +
        "}" +
    "};" +

    "return getXPath(arguments[0]);", element);
}


0 commentaires

0
votes

Il existe un moyen d'obtenir les éléments XPath sans utiliser JavaScript.

  1. Définissez le point de départ de l'extérieur XPATH, par exemple étiquette de corps.
  2. Vérifiez toutes les étiquettes intérieures possibles avec sélénium pour NosuchelementException .
  3. Vérifiez gettext pour les listes de XPATHS générées.
  4. gagnez

0 commentaires

5
votes

Si la diffusion a été trouvée par by.xpath: Sur java: xxx


0 commentaires

0
votes
public static String getXPathFromElement(WebElement element) {
        String elementDescription = element.toString();
        return elementDescription.substring(elementDescription.lastIndexOf("-> ") + 3, elementDescription.lastIndexOf("]"));
}
Web element toString() looks like this:'[[FirefoxDriver: firefox on WINDOWS (ceb69f9f-bef4-455d-b626-ab439f195be6)] -> id: pageBeanfundDescription]'I just extract the id/xpath.

0 commentaires

0
votes
/**
 * This method return By reference for the WebElement passed to it as a parameter.
 * @param element
 * @return
 */
public static By convertWebElementToByReference(WebElement element) 
{
    By byLocator = null;
    String elementDescription = element.toString();
    String elementTypeAndValue[] = (elementDescription.substring(elementDescription.lastIndexOf("-> ") + 3, elementDescription.lastIndexOf("]"))).split(":");        

    switch (elementTypeAndValue[0].trim()) 
    {
        case "id": byLocator = By.id(elementTypeAndValue[1].trim());
           break;

        case "xpath": byLocator = By.xpath(elementTypeAndValue[1].trim());
           break;

        case "link text": byLocator = By.linkText(elementTypeAndValue[1].trim());
           break;

        case "tag name": byLocator = By.tagName(elementTypeAndValue[1].trim());
           break;

        case "class name": byLocator = By.className(elementTypeAndValue[1].trim());
           break;

        case "partial link text": byLocator = By.partialLinkText(elementTypeAndValue[1].trim());
           break;

        case "name": byLocator = By.name(elementTypeAndValue[1].trim());
           break;

        case "css selector": byLocator = By.cssSelector(elementTypeAndValue[1].trim());
           break;

        default:
            throw new RuntimeException("Invalid locator type: " + elementTypeAndValue[0].trim());
    }

    return byLocator;
}

1 commentaires

Veuillez inclure une description avec le code exemple.



1
votes

Je commenterais directement sur dflems ' réponse , mais je n'ai pas la réputation de le faire.

Conversion de l'ensemble de xPath en minuscule est fine sauf si le XPath contient une valeur d'identification qui n'est pas tout minuscule. Vous trouverez ci-dessous une version modifiée de JavaScript DFLEMS ', mais à Python au lieu de Java: xxx


1 commentaires

Fonctionne parfaitement également sur le navigateur Tbselenium et Tor (Firefox Quantum 8.0.2 (basé sur Mozilla Firefox 60.2.2.2.2.2.2.2.2.2.2.2..2.1ESR) (64 bits)))