簡體   English   中英

Selenium Find By Xpath返回錯誤的元素

[英]Selenium Find By Xpath returning the wrong element

我正在嘗試從HTML表格中顯示的一系列通道中選擇一個通道。 我正在使用以下硒方法選擇鏈接

WebElement channel = driver.findElement(By.xpath("//span[contains(text(),Sales)]")); channel.click();

但是,它選擇的是列表中的第一個渠道(“帳戶管理”)。 我希望它會選擇正確的通道或引發錯誤,而不是選擇錯誤的通道。 以下是我想要的通道的完整xpath:

/html/body/div[2]/div[2]/form/div/table/tbody[2]/tr/td/ul/li[2]/a/span

通道列表在HTML代碼中的定義如下:

<form action="nextpage.do" method="post" name="selectChannelForm">
<div class="de">
    <h2>Select channel</h2>
    <table id="selectChannelForm">
        <tbody id=""></tbody>
        <tbody id="">
            <tr rowtype="container">
            <td class="desecond" colspan="3">
                <ul>    
                <li>
                    <a id="selected_a" href="nextpage.do?selectedChannel=123">
                    <span>Account Management</span></a>
                </li>   
                <li>
                    <a id="selected_a" href="nextpage.do?selectedChannel=456">
                    <span>Sales</span></a>
                </li>
                <li>
                    <a id="selected_a" href="nextpage.do?selectedChannel=789">
                    <span>Complaints</span></a>
                </li>
                </ul>
            </td>
            </tr>
        </tbody>
    </table>
    <input type="hidden" value="selectChannelForm" name="formid">
</div>

首先-您的錯誤!

您忘記了“銷售”兩邊的引號,只需稍微更改一下代碼即可使用:

WebElement channel = driver.findElement(By.xpath("//span[contains(text(),'Sales')]"));
channel.click();

第二-xpath錯誤?

您是對的,這很奇怪,您沒有收到錯誤消息,而是第一個元素是span。 這可能實際上是xpath中的錯誤。 contains函數實現了您的第二個參數不是字符串,而是返回true而不是返回false

它實際上擊中了所有三個跨度項。 結果只有第一個,因為您使用了findElement函數。

試試這個,你會看到這個怪癖:

System.out.println(driver.findElements(By.xpath("//span[contains(text(),Sales)]")).size());

結果將是:

3

第三-可能是“按設計”

看一下w3c定義,您會發現以下行:

如果$ arg2的值是零長度的字符串,則該函數返回true。

然后,在Microsoftxpath站點上,您將找到另一個有趣的提示:

如果參數不是字符串類型,則首先將其轉換為字符串,然后求值。

我猜想,將所有這些信息放在一起,xpath會將您的非字符串/不變的第二個參數解釋為空字符串,因此自從您搜索//span以來,所有span元素都返回true。

UPDATE

從@MichaelKay在我們學到的評論中,我的“猜測”非常接近:

在XPath和XQuery中,像“ hello”這樣的裸名意味着child :: hello,如果您不使用模式識別,那么系統將只查找稱為hello的子級,如果沒有,則它將返回一個空的節點集。

結論:OP所看到的行為是設計好的,即使它看起來很不直觀。

您使用的xpath在Sales文本周圍缺少引號"" text()函數采用的參數是字符串,可以使用引號將字符串形成。 通過以下方式更新xpath-

driver.findElement(By.xpath("//span[contains(text(),'Sales')]")).click();

或者,如果您要將其分配給WebElement,則請在引號中輸入-

WebElement channel = driver.findElement(By.xpath("//span[contains(text(),'Sales')]"));
channel.click();

如果您要編寫嵌套的雙引號或嵌套的單引號,請使用轉義符\\編寫。 這是如何做 -

WebElement channel = driver.findElement(By.xpath("//span[contains(text(),\"Sales\")]"));
channel.click();

希望這可以幫助。

xpath需要修改為“ // span [contains(text(),'Sales')]”“。

正如我們在下面的方法定義中看到的那樣,contains方法僅在第二個參數也是文本時才返回true。

資料來源: https : //en.wikipedia.org/wiki/XPath

如果s1包含s2,則contains(s1,s2)返回true。 text()查找text類型的節點

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM