Search code examples
javaselenium-webdriverautomated-tests

Automation Testing using Selenium, TestNT, Java - Reddit.com - Log In button in Pop-Up


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.

Screenshot of button I'm using

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();

Solution

  • 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());