diff --git a/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduEventManager.java b/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduEventManager.java index b81ad645..417490b3 100644 --- a/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduEventManager.java +++ b/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduEventManager.java @@ -129,14 +129,21 @@ public class OpenViduEventManager { // 'eventNumber' is accumulative for event 'eventName' for one page while it is // not refreshed public void waitUntilEventReaches(String eventName, int eventNumber) throws Exception { + this.waitUntilEventReaches(eventName, eventNumber, this.timeOfWaitInSeconds, true); + } + + public void waitUntilEventReaches(String eventName, int eventNumber, int secondsOfWait, boolean printTimeoutError) + throws Exception { CountDownLatch eventSignal = new CountDownLatch(eventNumber); this.setCountDown(eventName, eventSignal); try { - if (!eventSignal.await(this.timeOfWaitInSeconds * 1000, TimeUnit.MILLISECONDS)) { + if (!eventSignal.await(secondsOfWait * 1000, TimeUnit.MILLISECONDS)) { throw (new TimeoutException()); } } catch (InterruptedException | TimeoutException e) { - e.printStackTrace(); + if (printTimeoutError) { + e.printStackTrace(); + } throw e; } } diff --git a/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduTestAppE2eTest.java b/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduTestAppE2eTest.java index 5dcd60ee..4a7f0ab6 100644 --- a/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduTestAppE2eTest.java +++ b/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/OpenViduTestAppE2eTest.java @@ -23,6 +23,8 @@ import static org.openqa.selenium.OutputType.BASE64; import static org.slf4j.LoggerFactory.getLogger; import java.io.File; +import java.nio.file.Path; +import java.nio.file.Paths; import java.util.Arrays; import java.util.Iterator; import java.util.List; @@ -143,6 +145,18 @@ public class OpenViduTestAppE2eTest { user.getEventManager().startPolling(); } + void setupChromeWithFakeVideo(Path videoFileLocation) { + this.user = new ChromeUser("TestUser", 50, videoFileLocation); + user.getDriver().get(APP_URL); + WebElement urlInput = user.getDriver().findElement(By.id("openvidu-url")); + urlInput.clear(); + urlInput.sendKeys(OPENVIDU_URL); + WebElement secretInput = user.getDriver().findElement(By.id("openvidu-secret")); + secretInput.clear(); + secretInput.sendKeys(OPENVIDU_SECRET); + user.getEventManager().startPolling(); + } + @AfterEach void dispose() { user.dispose(); @@ -1353,6 +1367,127 @@ public class OpenViduTestAppE2eTest { gracefullyLeaveParticipants(2); } + @Test + @DisplayName("Video filter events test") + void videoFilterEventsTest() throws Exception { + + setupChromeWithFakeVideo(Paths.get("/home/pablo/Desktop/barcode.y4m")); + + log.info("Video filter events test"); + + // Configure publisher + user.getDriver().findElement(By.id("add-user-btn")).click(); + user.getDriver().findElements(By.cssSelector("#openvidu-instance-0 .subscribe-checkbox")).get(0).click(); + user.getDriver().findElements(By.cssSelector("#openvidu-instance-0 .send-audio-checkbox")).get(0).click(); + user.getDriver().findElement(By.id("session-settings-btn-0")).click(); + Thread.sleep(1000); + + WebElement allowedFilterInput = user.getDriver().findElement(By.id("allowed-filter-input")); + allowedFilterInput.clear(); + allowedFilterInput.sendKeys("ZBarFilter"); + + user.getDriver().findElement(By.id("add-allowed-filter-btn")).click(); + user.getDriver().findElement(By.id("save-btn")).click(); + Thread.sleep(1000); + + // Configure moderator (only subscribe) + user.getDriver().findElement(By.id("add-user-btn")).click(); + user.getDriver().findElement(By.cssSelector("#openvidu-instance-1 .publish-checkbox")).click(); + user.getDriver().findElement(By.id("session-settings-btn-1")).click(); + Thread.sleep(1000); + + user.getDriver().findElement(By.id("radio-btn-mod")).click(); + user.getDriver().findElement(By.id("save-btn")).click(); + Thread.sleep(1000); + + List joinButtons = user.getDriver().findElements(By.className("join-btn")); + for (WebElement el : joinButtons) { + el.sendKeys(Keys.ENTER); + } + + user.getEventManager().waitUntilEventReaches("connectionCreated", 4); + user.getEventManager().waitUntilEventReaches("accessAllowed", 1); + user.getEventManager().waitUntilEventReaches("streamCreated", 2); + user.getEventManager().waitUntilEventReaches("streamPlaying", 2); + + try { + System.out.println(getBase64Screenshot(user)); + } catch (Exception e) { + e.printStackTrace(); + } + + Assert.assertEquals(user.getDriver().findElements(By.tagName("video")).size(), 2); + // Assert no audio track only for the moderator incoming video + Assert.assertTrue(user.getEventManager().assertMediaTracks( + user.getDriver().findElements(By.cssSelector("#openvidu-instance-1 video")), false, true)); + + // Publisher applies ZBarCode filter to itself + user.getDriver().findElement(By.cssSelector("#openvidu-instance-0 .filter-btn")).click(); + Thread.sleep(500); + WebElement input = user.getDriver().findElement(By.id("filter-type-field")); + input.clear(); + input.sendKeys("ZBarFilter"); + input = user.getDriver().findElement(By.id("filter-options-field")); + input.clear(); + input.sendKeys("{}"); + user.getDriver().findElement(By.id("apply-filter-btn")).click(); + user.getWaiter().until( + ExpectedConditions.attributeContains(By.id("filter-response-text-area"), "value", "Filter applied")); + + user.getEventManager().waitUntilEventReaches("streamPropertyChanged", 2); + + // Publisher subscribes to CodeFound event for his own stream + input = user.getDriver().findElement(By.id("filter-event-type-field")); + input.clear(); + input.sendKeys("CodeFound"); + user.getDriver().findElement(By.id("sub-filter-event-btn")).click(); + user.getWaiter().until(ExpectedConditions.attributeContains(By.id("filter-response-text-area"), "value", + "Filter event listener added")); + + user.getEventManager().waitUntilEventReaches("filterEvent", 2); + + // Publisher unsubscribes from "CodeFound" filter event + user.getDriver().findElement(By.id("unsub-filter-event-btn")).click(); + + try { + // If this active wait finishes successfully, then the removal of the event + // listener has not worked fine + user.getEventManager().waitUntilEventReaches("filterEvent", 3, 3, false); + Assert.fail("'filterEvent' was received. Filter.removeEventListener() failed"); + } catch (Exception e) { + System.out.println("Filter event removal worked fine"); + } + + user.getDriver().findElement(By.id("close-dialog-btn")).click(); + Thread.sleep(500); + + // Moderator subscribes to CodeFound event for the Publisher's stream + user.getDriver().findElement(By.cssSelector("#openvidu-instance-1 .filter-btn")).click(); + Thread.sleep(500); + input = user.getDriver().findElement(By.id("filter-event-type-field")); + input.clear(); + input.sendKeys("CodeFound"); + user.getDriver().findElement(By.id("sub-filter-event-btn")).click(); + user.getWaiter().until(ExpectedConditions.attributeContains(By.id("filter-response-text-area"), "value", + "Filter event listener added")); + + user.getEventManager().waitUntilEventReaches("filterEvent", 4); + + // Moderator removes the Publisher's filter + user.getDriver().findElement(By.id("remove-filter-btn")).click(); + user.getWaiter().until( + ExpectedConditions.attributeContains(By.id("filter-response-text-area"), "value", "Filter removed")); + user.getEventManager().waitUntilEventReaches("streamPropertyChanged", 4); + + try { + // If this active wait finishes successfully, then the removal of the filter has not worked fine + user.getEventManager().waitUntilEventReaches("filterEvent", 5, 3, false); + Assert.fail("'filterEvent' was received. Stream.removeFilter() failed"); + } catch (Exception e) { + System.out.println("Filter removal worked fine"); + } + } + private void listEmptyRecordings() { // List existing recordings (empty) user.getDriver().findElement(By.id("list-recording-btn")).click(); diff --git a/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/browser/ChromeUser.java b/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/browser/ChromeUser.java index 376072fa..043ec072 100644 --- a/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/browser/ChromeUser.java +++ b/openvidu-test-e2e/src/test/java/io/openvidu/test/e2e/browser/ChromeUser.java @@ -20,6 +20,7 @@ package io.openvidu.test.e2e.browser; import java.io.IOException; import java.net.MalformedURLException; import java.net.URL; +import java.nio.file.Path; import java.util.concurrent.TimeUnit; import org.openqa.selenium.chrome.ChromeDriver; @@ -35,26 +36,17 @@ public class ChromeUser extends BrowserUser { } public ChromeUser(String userName, int timeOfWaitInSeconds, String screenToCapture) { - super(userName, timeOfWaitInSeconds); + this(userName, timeOfWaitInSeconds, generateScreenChromeOptions(screenToCapture)); + } + public ChromeUser(String userName, int timeOfWaitInSeconds, Path fakeVideoLocation) { + this(userName, timeOfWaitInSeconds, generateFakeVideoChromeOptions(fakeVideoLocation)); + } + + private ChromeUser(String userName, int timeOfWaitInSeconds, ChromeOptions options) { + super(userName, timeOfWaitInSeconds); DesiredCapabilities capabilities = DesiredCapabilities.chrome(); capabilities.setAcceptInsecureCerts(true); - - ChromeOptions options = new ChromeOptions(); - // This flag avoids to grant the user media - options.addArguments("--use-fake-ui-for-media-stream"); - // This flag fakes user media with synthetic video - options.addArguments("--use-fake-device-for-media-stream"); - // This flag selects the entire screen as video source when screen sharing - options.addArguments("--auto-select-desktop-capture-source=" + screenToCapture); - - try { - // Add Screen Sharing extension - options.addExtensions(new ClassPathResource("ScreenCapturing.crx").getFile()); - } catch (IOException e) { - e.printStackTrace(); - } - capabilities.setCapability(ChromeOptions.CAPABILITY, options); String REMOTE_URL = System.getProperty("REMOTE_URL_CHROME"); @@ -74,4 +66,32 @@ public class ChromeUser extends BrowserUser { this.configureDriver(); } + private static ChromeOptions generateScreenChromeOptions(String screenToCapture) { + ChromeOptions options = new ChromeOptions(); + // This flag avoids to grant the user media + options.addArguments("--use-fake-ui-for-media-stream"); + // This flag fakes user media with synthetic video + options.addArguments("--use-fake-device-for-media-stream"); + // This flag selects the entire screen as video source when screen sharing + options.addArguments("--auto-select-desktop-capture-source=" + screenToCapture); + try { + // Add Screen Sharing extension + options.addExtensions(new ClassPathResource("ScreenCapturing.crx").getFile()); + } catch (IOException e) { + e.printStackTrace(); + } + return options; + } + + private static ChromeOptions generateFakeVideoChromeOptions(Path videoFileLocation) { + ChromeOptions options = new ChromeOptions(); + // This flag avoids to grant the user media + options.addArguments("--use-fake-ui-for-media-stream"); + // This flag fakes user media with synthetic video + options.addArguments("--use-fake-device-for-media-stream"); + // This flag sets the video input as + options.addArguments("--use-file-for-fake-video-capture=" + videoFileLocation.toString()); + return options; + } + } \ No newline at end of file