【问题标题】:Selenium: Not able to print all the values from a list stored of IMDB Top Movies and RatingsSelenium:无法打印存储的 IMDB 热门电影和评分列表中的所有值
【发布时间】:2017-07-21 15:45:46
【问题描述】:

我无法打印列表中的所有值。

下面是完整的代码:

public class TestCase1{

private static XSSFWorkbook wb;
private static XSSFSheet sh;
private static File file;
static int i=0;

public static void main(String args[]) throws Exception
{
    file = new File("D:\\Eclipse and workspace\\workspace\\SeleniumPractice\\IMDBTestCase1.xlsx");
    FileInputStream fIs = new FileInputStream(file);
    wb = new XSSFWorkbook(fIs);
    sh = wb.getSheet("Sheet1");
    sh.createRow(i);

    System.setProperty("webdriver.gecko.driver", "D:\\Eclipse and workspace\\eclipse\\geckodriver.exe");
    WebDriver driver = new FirefoxDriver();

    driver.get("http://www.imdb.com");

    driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
    Actions action = new Actions(driver);
    action.moveToElement(driver.findElement(By.id("navTitleMenu"))).build().perform();

    Thread.sleep(5000);

    driver.findElement(By.xpath("//div[@id='navMenu1']/div[2]/ul[1]/li[6]/a")).click();

    WebDriverWait wait = new WebDriverWait(driver, 10);
    wait.until(ExpectedConditions.visibilityOfElementLocated(By.xpath("//table[@class='chart full-width']/thead/tr/th[2]")));

    WebElement elem1 = driver.findElement(By.xpath("//table[@class='chart full-width']/thead/tr/th[2]"));
    String title = elem1.getText();
    write(0,0,title);

    WebElement elem2 = driver.findElement(By.xpath("//table[@class='chart full-width']/thead/tr/th[3]"));
    String rating = elem2.getText();
    write(0,1,rating);
    i++;

    List <WebElement> elements = driver.findElements(By.className("lister-list"));
    for(WebElement element : elements)
    {   
        String str1 = element.findElement(By.xpath("//tbody[@class='lister-list']/tr["+i+"]/td[2]")).getText();
        System.out.println(str1);
        //write(i,0,elem3.getText());

        String str2 = element.findElement(By.xpath("//tbody[@class='lister-list']/tr["+i+"]/td[3]")).getText();
        System.out.println(str2);
        //write(i,1,elem4.getText());

        i++;
    }
    System.out.println("Success");

    wb.close(); 
}

public static void write(int row, int col, String val) throws Exception
{
    FileOutputStream fos = new FileOutputStream(file);
    sh.createRow(row+1);
    sh.getRow(row).createCell(col).setCellValue(val);
    wb.write(fos);
}

}

现在在下面的部分,

List <WebElement> elements = driver.findElements(By.className("lister-list"));
    for(WebElement element : elements)
    {   
        String str1 = element.findElement(By.xpath("//tbody[@class='lister-list']/tr["+i+"]/td[2]")).getText();
        System.out.println(str1);
        //write(i,0,elem3.getText());

        String str2 = element.findElement(By.xpath("//tbody[@class='lister-list']/tr["+i+"]/td[3]")).getText();
        System.out.println(str2);
        //write(i,1,elem4.getText());

        i++;
    }

这里的输出只打印这个:

1. The Shawshank Redemption (1994)
9.2
Success

我想打印所有电影名称及其评分,但我不确定为什么只打印第一个。 此外,如果我使用下面的 for 循环,它将打印所有名称和评级,但我希望将它们分开,因为我想将它们存储在 excel 文件中。

for(WebElement element : elements)
    {   
        System.out.println(element.getText());
    }

PS:我真正要做的是将电影名称和它们的评分存储在一个 excel 文件中。

【问题讨论】:

    标签: java selenium xpath


    【解决方案1】:

    如果你调试你的元素列表,你会发现它只有 1 个元素。需要在 tbody 中指定 tr 元素才能返回多个元素。

    我更喜欢通过 CSS 选择器获取元素,因为我发现它更容易编写。 这将得到你想要的......

    List <WebElement> elements = driver.findElements(By.cssSelector(".lister-list > tr"));
    
    for(WebElement element : elements)
    {   
        String title = element.findElement(By.cssSelector(".titleColumn")).getText();
        System.out.println(title);
    
        String rating = element.findElement(By.cssSelector(".ratingColumn.imdbRating")).getText();
        System.out.println(rating);
    
    }
    

    更新:这是使用 XPATH 的实现。

    List <WebElement> elements = driver.findElements(By.xpath("//tbody[@class='lister-list']//tr"));
    
    for(WebElement element : elements)
    {   
        String title = element.findElement(By.xpath("td[@class='titleColumn']")).getText();
        System.out.println(title);
    
        String rating = element.findElement(By.xpath("td[contains(@class, 'ratingColumn') and contains(@class, 'imdbRating')]")).getText();
        System.out.println(rating);
    
    }
    

    【讨论】:

    • 实际上我的元素列表包含所有“元素”。我在问题中提到,如果我写如下内容,那么它将打印所有电影的名称及其收视率。 for(WebElement 元素:元素) { System.out.println(element.getText()); }
    • 如果您可以使用 xpath 编写代码,那么请这样做,因为这样我就能够理解问题的真正所在。已经谢谢你了。
    • 是的,您的列表包含 1 个元素。在该 1 元素上执行 getText() 时,它将返回所有子元素的文本。通过指定 tr 子元素,您将获得约 250 个元素的列表。我会用 xpath 更新
    • 现在我明白了。非常感谢。
    猜你喜欢
    • 2022-08-14
    • 2020-04-22
    • 1970-01-01
    • 2021-09-15
    • 1970-01-01
    • 2011-04-12
    • 1970-01-01
    • 1970-01-01
    • 2020-11-07
    相关资源
    最近更新 更多