From 061f16fe52bc06764b5d523df92aea2ab3b08492 Mon Sep 17 00:00:00 2001
From: Re-Kayle <52598902+1109471432@users.noreply.github.com>
Date: Mon, 17 Jul 2023 16:29:52 +0800
Subject: [PATCH 1/2] integrate selenoid (#3191)
* feat: fix bug 3187
* feat: Integrate selenoid
* feat: update serenity-selenoid version to 3.9.2-SNAPSHOT
* feat: update serenity-selenoid remove Date API
* Update serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/SerenitySelenoidUtil.java
Co-authored-by: sonatype-lift[bot] <37194012+sonatype-lift[bot]@users.noreply.github.com>
---------
Co-authored-by: kayle <1109481432@qq.com>
Co-authored-by: sonatype-lift[bot] <37194012+sonatype-lift[bot]@users.noreply.github.com>
---
pom.xml | 1 +
serenity-selenoid/pom.xml | 68 +++++++++++++++++++
.../selenoid/AfterASelenoidScenario.java | 18 +++++
.../selenoid/BeforeASelenoidScenario.java | 50 ++++++++++++++
.../selenoid/SerenitySelenoidUtil.java | 57 ++++++++++++++++
.../WhenAddingSelenoidCapabilities.java | 49 +++++++++++++
6 files changed, 243 insertions(+)
create mode 100644 serenity-selenoid/pom.xml
create mode 100644 serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/AfterASelenoidScenario.java
create mode 100644 serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/BeforeASelenoidScenario.java
create mode 100644 serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/SerenitySelenoidUtil.java
create mode 100644 serenity-selenoid/src/test/java/net/serenitybdd/plugins/selenoid/WhenAddingSelenoidCapabilities.java
diff --git a/pom.xml b/pom.xml
index 190501355..6deff9cb2 100644
--- a/pom.xml
+++ b/pom.xml
@@ -761,6 +761,7 @@
serenity-cli
serenity-screenplay-playwright
serenity-bitbar
+ serenity-selenoid
diff --git a/serenity-selenoid/pom.xml b/serenity-selenoid/pom.xml
new file mode 100644
index 000000000..f04dd5287
--- /dev/null
+++ b/serenity-selenoid/pom.xml
@@ -0,0 +1,68 @@
+
+
+ 4.0.0
+
+ net.serenity-bdd
+ serenity-bdd
+ 3.9.2-SNAPSHOT
+
+
+ serenity-selenoid
+ jar
+ Serenity Screenplay selenoid Integration
+
+
+
+ UTF-8
+
+
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-jar-plugin
+
+
+
+ com.serenitybdd.serenityselenoid
+
+
+
+
+
+
+
+
+ ${project.groupId}
+ serenity-core
+ ${project.version}
+
+
+
+ junit
+ junit
+ test
+
+
+ ${project.groupId}
+ serenity-junit
+ ${project.version}
+ test
+
+
+ org.junit.jupiter
+ junit-jupiter-api
+ test
+
+
+ org.junit.vintage
+ junit-vintage-engine
+ test
+
+
+
+
\ No newline at end of file
diff --git a/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/AfterASelenoidScenario.java b/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/AfterASelenoidScenario.java
new file mode 100644
index 000000000..70520f530
--- /dev/null
+++ b/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/AfterASelenoidScenario.java
@@ -0,0 +1,18 @@
+package net.serenitybdd.plugins.selenoid;
+
+import net.serenitybdd.core.webdriver.RemoteDriver;
+import net.serenitybdd.core.webdriver.enhancers.AfterAWebdriverScenario;
+import net.thucydides.core.model.TestOutcome;
+import net.thucydides.core.util.EnvironmentVariables;
+import org.openqa.selenium.WebDriver;
+
+public class AfterASelenoidScenario implements AfterAWebdriverScenario {
+
+ @Override
+ public void apply(EnvironmentVariables environmentVariables, TestOutcome testOutcome, WebDriver driver) {
+ if ((driver == null) || (!RemoteDriver.isARemoteDriver(driver))) {
+ return;
+ }
+
+ }
+}
diff --git a/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/BeforeASelenoidScenario.java b/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/BeforeASelenoidScenario.java
new file mode 100644
index 000000000..41d9e1dc1
--- /dev/null
+++ b/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/BeforeASelenoidScenario.java
@@ -0,0 +1,50 @@
+package net.serenitybdd.plugins.selenoid;
+
+import net.serenitybdd.core.webdriver.driverproviders.CapabilityValue;
+import net.serenitybdd.core.webdriver.enhancers.BeforeAWebdriverScenario;
+import net.thucydides.core.model.TestOutcome;
+import net.thucydides.core.util.EnvironmentVariables;
+import net.thucydides.core.webdriver.SupportedWebDriver;
+import org.openqa.selenium.MutableCapabilities;
+import org.openqa.selenium.remote.CapabilityType;
+import org.openqa.selenium.remote.DesiredCapabilities;
+
+import java.util.*;
+
+import static net.serenitybdd.plugins.selenoid.SerenitySelenoidUtil.SELENOID;
+
+public class BeforeASelenoidScenario implements BeforeAWebdriverScenario {
+
+ public static final List capability = Arrays.asList(CapabilityType.BROWSER_NAME, CapabilityType.BROWSER_VERSION, CapabilityType.PLATFORM_NAME);
+
+
+ @Override
+ public MutableCapabilities apply(EnvironmentVariables environmentVariables, SupportedWebDriver driver, TestOutcome testOutcome, MutableCapabilities capabilities) {
+
+ if (driver != SupportedWebDriver.REMOTE) {
+ return capabilities;
+ }
+ Map SELENOID_PROPERTIES_MAP = new HashMap<>();
+ String name = SerenitySelenoidUtil.getName(testOutcome);
+ SELENOID_PROPERTIES_MAP.put("name", name);
+ SELENOID_PROPERTIES_MAP.put("videoName", SerenitySelenoidUtil.getVideoName(name));
+
+ DesiredCapabilities desiredCapabilities = new DesiredCapabilities();
+ Properties selenoidProperties = environmentVariables.getPropertiesWithPrefix(SELENOID);
+ for (String propertyName : selenoidProperties.stringPropertyNames()) {
+ String unPrefixedPropertyName = SerenitySelenoidUtil.unprefixed(propertyName);
+ Object value = CapabilityValue.fromString(selenoidProperties.getProperty(propertyName));
+ capability.stream().filter(k -> k.equalsIgnoreCase(unPrefixedPropertyName)).forEach(k -> desiredCapabilities.setCapability(k, value));
+ SELENOID_PROPERTIES_MAP.put(unPrefixedPropertyName, value);
+ }
+
+ SerenitySelenoidUtil.linkVideoToSerenityReport(testOutcome, SerenitySelenoidUtil.getVideoName(name));
+
+
+ capabilities.setCapability("selenoid:options", SELENOID_PROPERTIES_MAP);
+ capabilities.merge(desiredCapabilities);
+ return capabilities;
+ }
+
+
+}
diff --git a/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/SerenitySelenoidUtil.java b/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/SerenitySelenoidUtil.java
new file mode 100644
index 000000000..ac41cc9bc
--- /dev/null
+++ b/serenity-selenoid/src/main/java/net/serenitybdd/plugins/selenoid/SerenitySelenoidUtil.java
@@ -0,0 +1,57 @@
+package net.serenitybdd.plugins.selenoid;
+
+import net.thucydides.core.environment.SystemEnvironmentVariables;
+import net.thucydides.core.model.ExternalLink;
+import net.thucydides.core.model.TestOutcome;
+import net.thucydides.core.util.EnvironmentVariables;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.net.MalformedURLException;
+import java.net.URL;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+
+
+public class SerenitySelenoidUtil {
+
+ private static final Logger LOGGER = LoggerFactory.getLogger(SerenitySelenoidUtil.class);
+
+ public static final String SELENOID = "selenoid.";
+
+ public static EnvironmentVariables env = SystemEnvironmentVariables.currentEnvironmentVariables();
+
+ public static String getName(TestOutcome testOutcome) {
+ return String.format("%s-%s-%s", getVideoDataPrefix(), testOutcome.getStoryTitle(), testOutcome.getTitle());
+
+ }
+
+ public static String getVideoName(String name) {
+ return String.format("%s%s", name, getVideoNameSuffix());
+ }
+
+ public static String getVideoDataPrefix() {
+ String dataFormat = env.getProperty(SELENOID + "videoDataPrefixFormat", "yyyy-MM-dd");
+ return DateTimeFormatter.ofPattern(dataFormat).format(LocalDateTime.now(ZoneId.systemDefault()));
+ }
+
+ public static String getVideoNameSuffix() {
+ return env.getProperty(SELENOID + "videoSuffix", ".mp4");
+ }
+
+ protected static void linkVideoToSerenityReport(TestOutcome testOutcome, String link) {
+ try {
+ URL url = new URL(env.getProperty("webdriver.remote.url"));
+ String videoLinkPrefix = env.getProperty(SELENOID + "videoLinkPrefix", String.format("%s:%s:8080/video", url.getProtocol(), url.getHost()));
+ testOutcome.setLink(new ExternalLink(String.format("%s/%s", videoLinkPrefix, link), "BrowserStack"));
+ } catch (MalformedURLException e) {
+ LOGGER.error("Set video link error. {}", e.getMessage());
+ }
+
+ }
+
+ protected static String unprefixed(String propertyName) {
+ return propertyName.replace(SELENOID, "");
+ }
+
+}
diff --git a/serenity-selenoid/src/test/java/net/serenitybdd/plugins/selenoid/WhenAddingSelenoidCapabilities.java b/serenity-selenoid/src/test/java/net/serenitybdd/plugins/selenoid/WhenAddingSelenoidCapabilities.java
new file mode 100644
index 000000000..298240fdb
--- /dev/null
+++ b/serenity-selenoid/src/test/java/net/serenitybdd/plugins/selenoid/WhenAddingSelenoidCapabilities.java
@@ -0,0 +1,49 @@
+package net.serenitybdd.plugins.selenoid;
+
+import net.serenitybdd.core.webdriver.driverproviders.AddCustomDriverCapabilities;
+import net.thucydides.core.environment.MockEnvironmentVariables;
+import net.thucydides.core.model.Story;
+import net.thucydides.core.model.TestOutcome;
+import net.thucydides.core.util.EnvironmentVariables;
+import net.thucydides.core.webdriver.SupportedWebDriver;
+import org.junit.Test;
+import org.openqa.selenium.remote.DesiredCapabilities;
+
+import java.util.HashMap;
+
+import static org.assertj.core.api.Assertions.assertThat;
+
+public class WhenAddingSelenoidCapabilities {
+
+ EnvironmentVariables environmentVariables = new MockEnvironmentVariables();
+
+ @Test
+ public void shouldAddTheNameOfTheTest() {
+
+ // Given
+ DesiredCapabilities capabilities = new DesiredCapabilities();
+ TestOutcome testOutcome = TestOutcome.forTestInStory("serenity_selenoid_test", Story.called("Sample story"));
+ String name = SerenitySelenoidUtil.getName(testOutcome);
+
+ AddCustomDriverCapabilities.from(environmentVariables)
+ .withTestDetails(SupportedWebDriver.REMOTE, testOutcome)
+ .to(capabilities);
+ Object capability = capabilities.getCapability("selenoid:options");
+ assertThat(((HashMap) capability).get("name")).isEqualTo(name);
+ }
+
+ @Test
+ public void shouldAddZaleniumPropertiesFromTheEnvironmentConfiguration() {
+
+ // Given
+ DesiredCapabilities capabilities = new DesiredCapabilities();
+ TestOutcome testOutcome = TestOutcome.forTestInStory("serenity_selenoid_test", Story.called("Sample story"));
+ environmentVariables.setProperty("selenoid.enableVNC", "true");
+
+ AddCustomDriverCapabilities.from(environmentVariables).withTestDetails(SupportedWebDriver.REMOTE, testOutcome).to(capabilities);
+ Object capability = capabilities.getCapability("selenoid:options");
+ assertThat(((HashMap) capability).get("enableVNC")).isEqualTo(true);
+
+ }
+
+}
From a46a7df058972dc916326f7b4dd6f32e84cc6c35 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Andr=C3=A9=20Becker?=
Date: Mon, 17 Jul 2023 10:30:55 +0200
Subject: [PATCH 2/2] enable list matcher to be used with Check class (#3182)
---
.../main/java/net/serenitybdd/screenplay/conditions/Check.java | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/serenity-screenplay/src/main/java/net/serenitybdd/screenplay/conditions/Check.java b/serenity-screenplay/src/main/java/net/serenitybdd/screenplay/conditions/Check.java
index 87c993d07..30135c183 100644
--- a/serenity-screenplay/src/main/java/net/serenitybdd/screenplay/conditions/Check.java
+++ b/serenity-screenplay/src/main/java/net/serenitybdd/screenplay/conditions/Check.java
@@ -12,7 +12,7 @@ public static ConditionalPerformable whether(Question condition) {
return new ConditionalPerformableOnQuestion(condition);
}
- public static ConditionalPerformable whether(Question question, Matcher matcher) {
+ public static ConditionalPerformable whether(Question extends T> question, Matcher matcher) {
Question condition = actor -> matcher.matches(question.answeredBy(actor));
return new ConditionalPerformableOnQuestion(condition);