Skip to content

Commit

Permalink
feat(java): ✨ added shadow root support
Browse files Browse the repository at this point in the history
  • Loading branch information
WasiqB committed Jan 13, 2025
1 parent f1c9d72 commit 4e50575
Show file tree
Hide file tree
Showing 6 changed files with 579 additions and 401 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -83,8 +83,9 @@ public static List<WebElement> finds (final Locator locator, final WaitStrategy
final var driver = getSession ().getDriver ();
final List<WebElement> elements;
if (!isNull (locator.getParent ())) {
final var parent = find (locator.getParent (), waitStrategy);
elements = finds (driver, parent, locator);
final var parentLocator = locator.getParent ();
final var parent = find (parentLocator, waitStrategy);
elements = finds (driver, parent, parentLocator, locator);
} else {
waitForElement (locator, waitStrategy);
elements = finds (driver, locator);
Expand All @@ -93,20 +94,25 @@ public static List<WebElement> finds (final Locator locator, final WaitStrategy
}

private static <D extends WebDriver> List<WebElement> finds (final D driver, final WebElement parent,
final Locator locator) {
final Locator parentLocator, final Locator locator) {
LOGGER.traceEntry ();
final var platformLocator = locator.getLocator ();
if (isNull (platformLocator)) {
throwError (ELEMENT_NOT_FOUND, locator.getName (), getSession ().getPlatformType ());
}
return LOGGER.traceExit (!isNull (parent)
? parent.findElements (locator.getLocator ())
: driver.findElements (locator.getLocator ()));
if (!isNull (parent)) {
if (parentLocator.isShadowRoot ()) {
return parent.getShadowRoot ()
.findElements (locator.getLocator ());
}
return parent.findElements (locator.getLocator ());
}
return driver.findElements (locator.getLocator ());
}

private static <D extends WebDriver> List<WebElement> finds (final D driver, final Locator locator) {
LOGGER.traceEntry ();
return LOGGER.traceExit (finds (driver, null, locator));
return LOGGER.traceExit (finds (driver, null, null, locator));
}

private static void waitForElement (final Locator locator, final WaitStrategy waitStrategy) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,8 @@ public class Locator {
@NotNull
private String name;
private Locator parent;
@Builder.Default
private boolean shadowRoot = false;
private By web;

/**
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
/*
* MIT License
*
* Copyright (c) 2024, Boyka Framework
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*/

package io.github.boykaframework.testng.ui.theinternet;

import static io.github.boykaframework.actions.device.DeviceActions.onDevice;
import static io.github.boykaframework.actions.drivers.NavigateActions.navigate;
import static io.github.boykaframework.actions.drivers.WindowActions.onWindow;
import static io.github.boykaframework.actions.elements.ClickableActions.withMouse;
import static io.github.boykaframework.manager.ParallelSession.clearSession;
import static io.github.boykaframework.manager.ParallelSession.createSession;
import static io.github.boykaframework.testng.ui.theinternet.pages.ShadowRootPage.shadowRootPage;

import io.github.boykaframework.enums.PlatformType;
import org.testng.ITestResult;
import org.testng.annotations.AfterClass;
import org.testng.annotations.AfterMethod;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.Parameters;
import org.testng.annotations.Test;

/**
* Login Test class.
*
* @author Wasiq Bhamla
* @since 16-Sept-2023
*/
public class ShadowRootTest {
private static final String URL = "https://www.htmlelements.com/demos/menu/shadow-dom/index.htm";

/**
* Setup test method to take screenshot after each test method.
*/
@AfterMethod
public void afterMethod (final ITestResult result) {
if (!result.isSuccess ()) {
onWindow ().takeScreenshot ();
}
}

/**
* Setup test class by initialising driver.
*
* @param platformType Application type
* @param driverKey Driver config key
*/
@BeforeClass (description = "Setup test class")
@Parameters ({ "platformType", "driverKey" })
public void setupClass (final PlatformType platformType, final String driverKey) {
createSession (platformType, driverKey);
navigate ().to (URL);
}

/**
* Tear down test class by closing driver.
*/
@AfterClass (description = "Tear down test class")
public void tearDownClass () {
onDevice ().stopRecording ();
clearSession ();
}

@Test (description = "Test Login Flow")
public void testLogin () {
withMouse (shadowRootPage ().getMenu ("Encoding")).click ();
withMouse (shadowRootPage ().getMenuItem ("Encoding", "Encode in UTF-8")).click ();

withMouse (shadowRootPage ().getMenu ("Encoding")).click ();
withMouse (shadowRootPage ().getMenuItem ("Encoding", "Encode in UTF-8")).verifyProperty ("checked")
.isEqualTo ("true");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
/*
* MIT License
*
* Copyright (c) 2025, Boyka Framework
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*/

package io.github.boykaframework.testng.ui.theinternet.pages;

import static java.text.MessageFormat.format;
import static org.openqa.selenium.By.cssSelector;
import static org.openqa.selenium.By.tagName;

import io.github.boykaframework.builders.Locator;
import lombok.Getter;

/**
* Shadow example page.
*
* @author Wasiq Bhamla
* @since 13-Jan-2025
*/
@Getter
public class ShadowRootPage {
private static final ShadowRootPage SHADOW_ROOT_PAGE = new ShadowRootPage ();

/**
* Gets the page instance.
*
* @return Page instance
*/
public static ShadowRootPage shadowRootPage () {
return SHADOW_ROOT_PAGE;
}

private final Locator smartMenu = Locator.buildLocator ()
.name ("Smart Menu")
.web (tagName ("smart-ui-menu"))
.shadowRoot (true)
.build ();

private ShadowRootPage () {
// Singleton class
}

/**
* Gets menu.
*
* @param menuName Menu name
*
* @return Locator.
*/
public Locator getMenu (final String menuName) {
return Locator.buildLocator ()
.name (menuName)
.parent (this.smartMenu)
.web (cssSelector (format ("smart-menu-items-group[label=\"{0}\"]", menuName)))
.build ();
}

/**
* Gets menu item from the menu.
*
* @param menuName Menu name
* @param itemName Item name
*
* @return Locator.
*/
public Locator getMenuItem (final String menuName, final String itemName) {
return Locator.buildLocator ()
.name (itemName)
.parent (getMenu (menuName))
.web (cssSelector (format ("smart-menu-item[label=\"{0}\"]", itemName)))
.build ();
}
}
16 changes: 8 additions & 8 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -35,19 +35,19 @@
"@eslint/compat": "^1.2.5",
"@lerna/child-process": "^7.4.2",
"@release-it-plugins/lerna-changelog": "^7.0.0",
"@stylistic/eslint-plugin-js": "^2.12.1",
"@stylistic/eslint-plugin-ts": "^2.12.1",
"@types/node": "^22.10.5",
"@typescript-eslint/eslint-plugin": "^8.19.1",
"@typescript-eslint/parser": "^8.19.1",
"@stylistic/eslint-plugin-js": "^2.13.0",
"@stylistic/eslint-plugin-ts": "^2.13.0",
"@types/node": "^22.10.6",
"@typescript-eslint/eslint-plugin": "^8.20.0",
"@typescript-eslint/parser": "^8.20.0",
"commitlint": "^19.6.1",
"eslint": "^9.18.0",
"eslint-config-google": "^0.14.0",
"eslint-config-prettier": "^9.1.0",
"eslint-config-prettier": "^10.0.1",
"eslint-import-resolver-typescript": "^3.7.0",
"eslint-plugin-import": "^2.31.0",
"eslint-plugin-prettier": "^5.2.1",
"eslint-plugin-react": "^7.37.3",
"eslint-plugin-react": "^7.37.4",
"globals": "^15.14.0",
"husky": "^9.1.7",
"js-yaml": "^4.1.0",
Expand All @@ -63,7 +63,7 @@
"release-it": "^18.1.1",
"ts-node": "^10.9.2",
"typescript": "^5.7.3",
"typescript-eslint": "^8.19.1"
"typescript-eslint": "^8.20.0"
},
"scripts": {
"preinstall": "npx only-allow pnpm",
Expand Down
Loading

0 comments on commit 4e50575

Please sign in to comment.