I'm trying to figure out how to automate logging into Reddit via Java/Selenium.
I've gotten to Reddit.com > Log In > Pop-Up Window > Find and Fill Username & Password.
However, no matter what method I try, I cannot seem to focus and click the Log In button within the Pop-Up. I know the button is disabled until a password of appropriate length is entered, so I added a 1-second sleep to ensure that I'm not selecting the element before it's made available.
I continuously get a noSuchElement error.
package org.example;
import org.openqa.selenium.*;
import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.edge.EdgeDriver;
import org.openqa.selenium.firefox.FirefoxDriver;
import org.testng.annotations.Test;
import java.util.Iterator;
import java.util.Set;
public class TestCases {
String userName = "ThrowAwayTestingbot";
String password = "CEN4072!";
WebDriver create_driver( char browser){
if(browser == 'c'){
System.setProperty("webdriver.chrome.driver","C:\\Users\\pr0je\\Desktop\\Spring2024\\CEN4072 - Software Testing\\FinalGroupProject\\src\\main\\java\\org\\example\\chromedriver.exe");
return new ChromeDriver();
}else if(browser == 'f'){
System.setProperty("webdriver.gecko.driver","C:\\Users\\pr0je\\Desktop\\Spring2024\\CEN4072 - Software Testing\\FinalGroupProject\\src\\main\\java\\org\\example\\geckodriver.exe");
return new FirefoxDriver();
}else if(browser == 'e'){
System.setProperty("webdriver.chrome.driver","C:\\Users\\pr0je\\Desktop\\Spring2024\\CEN4072 - Software Testing\\FinalGroupProject\\src\\main\\java\\org\\example\\msedgedriver.exe");
return new EdgeDriver();
}
else System.out.println("Sorry, we could not start a browser. Attempting to start Chrome.");
return new ChromeDriver();
}
WebDriver driver = create_driver('c');
@Test
void test_sign_in() throws InterruptedException {
// Visit Reddit.com
driver.get("https://www.reddit.com");
driver.manage().window().maximize();
String mainWindow = driver.getWindowHandle();
String popUp = null;
WebElement button = driver.findElement(By.id("login-button"));
button.click();
Thread.sleep(2000);
// Get PopUp Info
Set<String> handles = driver.getWindowHandles();
Iterator<String> iterator = handles.iterator();
while(iterator.hasNext()){
popUp = iterator.next();
}
driver.switchTo().window(popUp);
driver.findElement(By.id("login-username")).sendKeys(userName);
Thread.sleep(250);
driver.findElement(By.id("login-password")).sendKeys(password);
Thread.sleep(1000);
} // End of Sign In Test
} // END OF TestCases Class
Here are some of my attempts:
// By Class
button = driver.findElement(By.className("login w-100\n" +
"button-large px-[var(--rem14)]\n" +
"button-brand\n" +
"\n" +
"\n" +
"\n" +
"items-center justify-center\n" +
"button inline-flex "));
button.click();
// By xPath
button = driver.findElement(By.xpath("//*[@id=\"login\"]/faceplate-tabpanel/auth-flow-modal[1]/div[2]/faceplate-tracker"));
button.click();
// By Selector
button = driver.findElement(By.cssSelector("login > faceplate-tabpanel > auth-flow-modal:nth-child(1) > div.w-100 > faceplate-tracker > button"));
button.click();
The button you are trying to access is buried in a bunch of nested shadow-roots.
Here's a simple example to get you started,
driver.get("http://watir.com/examples/shadow_dom.html");
WebElement shadowHost = driver.findElement(By.cssSelector("#shadow_host"));
SearchContext shadowRoot = shadowHost.getShadowRoot();
WebElement shadowContent = shadowRoot.findElement(By.cssSelector("#shadow_content"));
Assertions.assertEquals("some text", shadowContent.getText());