如何使用 Selenium 和 Java 在 webtable 单元格中发送文本

How to send text within a webtable cell using Selenium and Java

我正在尝试将值“100”发送到 Table 的位置 (row: 2, column 3),此处:

https://keisan.casio.com/exec/system/13800848854767

下面这段代码,你能告诉我,哪里出了问题吗?

代码:

driver.get("https://keisan.casio.com/exec/system/13800848854767");
List<WebElement> inputTable = driver.findElements(By.xpath("//*[@id='var_a_EXL']//tbody//tr"));
System.out.println(inputTable.size());
List<WebElement> columns;
for (int rows = 0; rows < inputTable.size(); rows++) {
    if (rows == 2) {
        columns = inputTable.get(rows).findElements(By.tagName("td"));
        for (int i = 0; i < columns.size(); i++) {
            if (i == 3) {
                columns.get(i).clear();
                columns.get(i).sendKeys("100");
            }
        }
    }
} 

你的循环逻辑是正确的,但是你的代码产生了这个错误:

org.openqa.selenium.InvalidElementStateException: invalid element state

您需要先 click 才能对该元素执行下一步操作才能成为可编辑元素,并且您必须使用 Actions class 与其交互:

driver.get("https://keisan.casio.com/exec/system/13800848854767");
List<WebElement> inputTable = new WebDriverWait(driver, 20).until(ExpectedConditions.visibilityOfAllElementsLocatedBy(By.xpath("//*[@id='var_a_EXL']//tbody//tr")));
System.out.println(inputTable.size());
List<WebElement> columns;
for (int rows = 0; rows < inputTable.size(); rows++) {
    if (rows == 2) {
        columns = inputTable.get(rows).findElements(By.tagName("td"));
        for (int i = 0; i < columns.size(); i++) {
            if (i == 3) {
                WebElement target = columns.get(i);
                Actions actions = new Actions(driver);
                actions.moveToElement(target)
                    .click(target)
                    .sendKeys("100")
                    .build()
                    .perform();
            }
        }
    }
}

而且我还在上面的代码中添加了WebDriverWait

以下导入:

import org.openqa.selenium.interactions.Actions;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.openqa.selenium.support.ui.WebDriverWait;

顺便说一句,这个 xpath //*[@id='var_a_EXL']//tbody//tr[3]//td[4] 有一个更简单的方法,而不是使用上面的循环:

driver.get("https://keisan.casio.com/exec/system/13800848854767");
WebElement target = new WebDriverWait(driver, 20).until(ExpectedConditions.visibilityOfElementLocated(By.xpath("//*[@id='var_a_EXL']//tbody//tr[3]//td[4]")));
Actions actions = new Actions(driver);
actions.moveToElement(target)
    .click(target)
    .sendKeys("100")
    .build()
    .perform();

或使用以下 css 选择器更好地定位元素:

By.cssSelector("#var_a_EXL tr:nth-child(3) td:nth-child(4)")

+1 @frianH 的回答,您的代码不起作用的原因是因为 .clear() 仅当元素是文本输入元素时才起作用。文本输入元素是 INPUT 和 TEXTAREA,这不是您的情况

这是使用 JSExecutor 的更简单方法

    List<WebElement> inputTable = driver.findElements(By.xpath("//*[@id='var_a_EXL']//tbody//tr"));
    System.out.println(inputTable.size());
    List<WebElement> columns;
    int rowss = 3;
    int columnss = 3;

    for (int rows = 0; rows < inputTable.size(); rows++) {
        if (rows == rowss) {
            columns = inputTable.get(rows).findElements(By.tagName("td"));
            System.out.println(columns.size());
            for (int i = 0; i < columns.size(); i++) {
                if (i == columnss) {
                    JavascriptExecutor js = (JavascriptExecutor) driver;
                    js.executeScript("arguments[0].innerText = '300'", columns.get(i));
                }

            }
        }

    }

您没有提到您面临的错误。提及错误会帮助我们构建一个更规范的答案。当您尝试在 <td> 元素上调用 clear() 时,您可能正面临 InvalidElementStateException

但是,要将字符串 100 发送到 table 的位置(行:2,列 z),您需要归纳 for the elementToBeClickable() and you can use the following

  • 使用 xpath:

    driver.get("https://keisan.casio.com/exec/system/13800848854767");
    new WebDriverWait(driver, 5).until(ExpectedConditions.elementToBeClickable(By.xpath("//td/span[@id='var_a_EXL_2_3C']"))).click();
    new WebDriverWait(driver, 5).until(ExpectedConditions.elementToBeClickable(By.xpath("//td/input[@id='var_a_EXL_2_3_input']"))).sendKeys("100");
    
  • 浏览器快照:


行号和列号作为变量

考虑 rowcolumn 数字作为变量:

  • 代码块:

    driver.get("https://keisan.casio.com/exec/system/13800848854767");
    int row = 2;
    int column = 3;
    new WebDriverWait(driver, 5).until(ExpectedConditions.elementToBeClickable(By.xpath("//td/span[contains(@id, '"+String.valueOf(row)+"') and contains(@id, '"+String.valueOf(column)+"')]"))).click();
    new WebDriverWait(driver, 5).until(ExpectedConditions.elementToBeClickable(By.xpath("//td/input[contains(@id, '"+String.valueOf(row)+"') and contains(@id, '"+String.valueOf(column)+"')]"))).sendKeys("100");