How to automate shadow DOM elements using selenium?

12    Asked by AkanshaChawla in QA Testing , Asked on Dec 15, 2024

In a Java Selenium project, interacting with shadow DOM elements can be challenging because the findElement method in Selenium cannot directly access elements inside a shadow-root. Shadow DOM encapsulates part of the DOM, making elements within it inaccessible by default. For web pages containing multi-level shadow-root elements, how can you automate interactions with these elements using Selenium?

Answered by Aishwarya Jhadav

To interact with shadow DOM elements, you can use JavaScript execution through Selenium’s JavascriptExecutor. This allows you to traverse shadow roots and access encapsulated elements.


Steps to Access Shadow DOM Elements:

1. Using JavascriptExecutor to Access Shadow-Root

Here’s a method to interact with single-level or multi-level shadow DOM elements:

Example: Access Single-Level Shadow DOM

import org.openqa.selenium.By;

import org.openqa.selenium.JavascriptExecutor;

import org.openqa.selenium.WebDriver;

import org.openqa.selenium.WebElement;

import org.openqa.selenium.chrome.ChromeDriver;

public class ShadowDomExample {

    public static void main(String[] args) {

        WebDriver driver = new ChromeDriver();

        driver.get("https://example.com");

        // JavaScript to access shadow DOM

        JavascriptExecutor js = (JavascriptExecutor) driver;

        // Find the shadow host element

        WebElement shadowHost = driver.findElement(By.cssSelector("css-selector-of-shadow-host"));

        // Access the shadow root

        WebElement shadowRoot = (WebElement) js.executeScript("return arguments[0].shadowRoot", shadowHost);

        // Find an element inside the shadow root

        WebElement innerElement = shadowRoot.findElement(By.cssSelector("css-selector-inside-shadow-root"));

        innerElement.click(); // Perform actions on the element

        driver.quit();

    }

}

2. Access Multi-Level Shadow DOM

For deeply nested shadow roots, repeat the process to traverse multiple levels.

Example: Access Multi-Level Shadow DOM

WebElement shadowHost1 = driver.findElement(By.cssSelector("css-selector-of-first-shadow-host"));

WebElement shadowRoot1 = (WebElement) js.executeScript("return arguments[0].shadowRoot", shadowHost1);

// Find nested shadow host

WebElement shadowHost2 = shadowRoot1.findElement(By.cssSelector("css-selector-of-second-shadow-host"));

WebElement shadowRoot2 = (WebElement) js.executeScript("return arguments[0].shadowRoot", shadowHost2);

// Find element inside nested shadow root

WebElement nestedElement = shadowRoot2.findElement(By.cssSelector("css-selector-inside-second-shadow-root"));

nestedElement.click(); // Perform actions

Alternative: Use Open Source Libraries

For enhanced shadow DOM support, consider using third-party libraries like SeleniumEasy's Shadow DOM Handling or building utility functions to simplify repetitive shadow DOM interactions.

Key Considerations:

  1. JavaScript Dependency: Since Selenium does not natively support shadow DOM, JavascriptExecutor is required.
  2. CSS Selectors: Accurate cssSelector is crucial for locating shadow hosts and nested elements.
  3. Performance: Accessing deeply nested shadow DOM can slow down tests, so optimize traversals.
  4. Dynamic Shadow DOM: If elements inside the shadow DOM are dynamically loaded, ensure you use explicit waits (WebDriverWait) to handle synchronization.

This method allows seamless interaction with both single-level and multi-level shadow DOM elements in Selenium.



Your Answer

Interviews

Parent Categories