Selenium HTMLUnitDriver 无法登录
Selenium HTMLUnitDriver Cannot Sign in
更新
我正在尝试登录此网站:
很遗憾,我没有成功。这是我的代码:
WebDriver driver = new HtmlUnitDriver();
driver.get("https://trailhead.salesforce.com/en/home");
System.out.println(driver.getTitle());
WebElement btnLogin = driver.findElement(By.xpath("//*[@id=\"main-wrapper\"]/header/div[1]/div[2]/span[2]/div/span/button"));
System.out.println(btnLogin);
driver.quit();
我正在尝试从 header 获取登录按钮,但是我找不到元素,这是我收到的异常消息:
Exception in thread "main" org.openqa.selenium.NoSuchElementException:
Unable to locate a node using
//*[@id="main-wrapper"]/header/div1/div[2]/span[2]/div/span/button
我正在尝试从下方测试答案,但没有成功。我想更好地了解 WebDriverWait 的工作原理和 until() 方法。
谢谢。
问题是有多个登录按钮。您的代码等待 第一个按钮 可见。不幸的是,它不会。所以 Selenium 一直等到超时。
我建议创建一种方法,通过遍历所有 saleforce 登录按钮并检查 属性 isDisplayed()
来找到正确的按钮。如果是,请使用按钮。请参阅下面的示例。
private WebElement findLoginButton(WebDriver d, By by) {
List<WebElement> elements = d.findElements(by);
for (Iterator<WebElement> e = elements.iterator(); e.hasNext();) {
WebElement item = e.next();
if(item.isDisplayed())
return item;
}
return null;
}
@Test
public void testSaleforce() {
WebDriver driver = new HtmlUnitDriver();
driver.get("https://trailhead.salesforce.com/en/home");
System.out.println(driver.getTitle());
WebElement btnLogin = driver.findElement(By.xpath("//*[@data-react-class='auth/LoginModalBtn']"));
System.out.println(btnLogin);
btnLogin.click();
WebDriverWait wait = new WebDriverWait(driver,10);
WebElement btnLoginSalesforce = wait.until((WebDriver d) -> findLoginButton(d,By.cssSelector(".th-modal-btn__salesforce")));
btnLoginSalesforce.click();
...
}
在此网页中,开发人员非常友好地向 HTML 添加特殊 (HTML5) 属性以进行测试,称为 'data-test'。借助此属性,您可以使用 CSS 选择器在您的 Selenium 代码中定位 Webelements。因此不需要复杂的 Xpath 选择器,也不需要像@Buaban 建议的那样遍历按钮。
我测试了以下 C# 代码并成功点击了登录按钮。
IWebElement btnLogin = Driver.FindElement(By.CssSelector("button[data-test=header-login]"));
btnLogin.Click();
我想你用的是Java,那么它将是:
WebElement btnLogin = driver.findElement(By.cssSelector("button[data-test=header-login]"));
btnLogin.click();
要获得更稳定的解决方案,您必须使用显式等待:
WebDriverWait wait = new WebDriverWait(driver, 20);
WebElement element = wait.until(ExpectedConditions.elementToBeClickable(By.css(""button[data-test=header-login]"")));
Selenium 将尝试每 500 毫秒查找一次按钮,最长 20 秒。 NoSuchElementExceptions 将被忽略,直到找到按钮或经过 20 秒。如果 20 秒后仍未找到按钮,将抛出超时异常。
更新
我正在尝试登录此网站:
很遗憾,我没有成功。这是我的代码:
WebDriver driver = new HtmlUnitDriver();
driver.get("https://trailhead.salesforce.com/en/home");
System.out.println(driver.getTitle());
WebElement btnLogin = driver.findElement(By.xpath("//*[@id=\"main-wrapper\"]/header/div[1]/div[2]/span[2]/div/span/button"));
System.out.println(btnLogin);
driver.quit();
我正在尝试从 header 获取登录按钮,但是我找不到元素,这是我收到的异常消息:
Exception in thread "main" org.openqa.selenium.NoSuchElementException: Unable to locate a node using //*[@id="main-wrapper"]/header/div1/div[2]/span[2]/div/span/button
我正在尝试从下方测试答案,但没有成功。我想更好地了解 WebDriverWait 的工作原理和 until() 方法。
谢谢。
问题是有多个登录按钮。您的代码等待 第一个按钮 可见。不幸的是,它不会。所以 Selenium 一直等到超时。
我建议创建一种方法,通过遍历所有 saleforce 登录按钮并检查 属性 isDisplayed()
来找到正确的按钮。如果是,请使用按钮。请参阅下面的示例。
private WebElement findLoginButton(WebDriver d, By by) {
List<WebElement> elements = d.findElements(by);
for (Iterator<WebElement> e = elements.iterator(); e.hasNext();) {
WebElement item = e.next();
if(item.isDisplayed())
return item;
}
return null;
}
@Test
public void testSaleforce() {
WebDriver driver = new HtmlUnitDriver();
driver.get("https://trailhead.salesforce.com/en/home");
System.out.println(driver.getTitle());
WebElement btnLogin = driver.findElement(By.xpath("//*[@data-react-class='auth/LoginModalBtn']"));
System.out.println(btnLogin);
btnLogin.click();
WebDriverWait wait = new WebDriverWait(driver,10);
WebElement btnLoginSalesforce = wait.until((WebDriver d) -> findLoginButton(d,By.cssSelector(".th-modal-btn__salesforce")));
btnLoginSalesforce.click();
...
}
在此网页中,开发人员非常友好地向 HTML 添加特殊 (HTML5) 属性以进行测试,称为 'data-test'。借助此属性,您可以使用 CSS 选择器在您的 Selenium 代码中定位 Webelements。因此不需要复杂的 Xpath 选择器,也不需要像@Buaban 建议的那样遍历按钮。
我测试了以下 C# 代码并成功点击了登录按钮。
IWebElement btnLogin = Driver.FindElement(By.CssSelector("button[data-test=header-login]"));
btnLogin.Click();
我想你用的是Java,那么它将是:
WebElement btnLogin = driver.findElement(By.cssSelector("button[data-test=header-login]"));
btnLogin.click();
要获得更稳定的解决方案,您必须使用显式等待:
WebDriverWait wait = new WebDriverWait(driver, 20);
WebElement element = wait.until(ExpectedConditions.elementToBeClickable(By.css(""button[data-test=header-login]"")));
Selenium 将尝试每 500 毫秒查找一次按钮,最长 20 秒。 NoSuchElementExceptions 将被忽略,直到找到按钮或经过 20 秒。如果 20 秒后仍未找到按钮,将抛出超时异常。