We're using the
new FlashPolicyHelper(driver).addSite("https://your.site")
In order to bypass the getFlash prompt when trying to navigate to our websites that use Flash.
However this does not seem to work when executed remotely.
Current Implementation
Calling the FlashPolicyHelper Class
if(browser.driver instanceof ChromeDriver)
{
new FlashPolicyHelper((ChromeDriver) browser.driver).addSite(odysseyURL)
}
browser
public class FlashPolicyHelper
{
private final ChromeDriver driver;
public FlashPolicyHelper(ChromeDriver driver) {
this.driver = driver;
}
public FlashPolicyHelper addSite(String site) {
try {
this.driver.get("chrome://settings/content/siteDetails?site=" + site);
... rest of code for FlashPolicyHelper found here...
Allow Flash content in Chrome 69 running via chromedriver
I realized I needed to instantiate a Remote Web Driver in order to have functionality remotely. Solved.
if(browser.driver instanceof RemoteWebDriver)
{
new FlashPolicyHelper((RemoteWebDriver) browser.driver).addSite(odysseyURL)
}
browser
public class FlashPolicyHelper
{
private final RemoteWebDriver driver;
public FlashPolicyHelper(RemoteWebDriver driver) {
this.driver = driver;
}
public FlashPolicyHelper addSite(String site) {
try {
this.driver.get("chrome://settings/content/siteDetails?site=" + site);
... rest of code for FlashPolicyHelper found here...
Allow Flash content in Chrome 69 running via chromedriver
Related
I went through Selenium Jupiter manual and still cannot get the idea of how I can set multiple
browsers in Selenium Jupiter to run every test in every browser.
Should use Test Template for that purpose?
Again I did not see an example of how can I do it in Selenium Jupiter?
p.s. An example with RemoteDrivers on Selenium Grid.
Here is my attempt to do it:
public class BaseTestWithRemoteDrivers {
#RegisterExtension
static SeleniumExtension extension = new SeleniumExtension();
#BeforeAll
public static void setupAll() {
extension.getConfig().setSeleniumServerUrl("http://localhost:4444/wd/hub");
Browser chrome = BrowserBuilder.chrome().build();
Browser firefox = BrowserBuilder.firefox().build();
extension.addBrowsers(chrome, firefox);
}
#Test
public void testWithBrowser(WebDriver driver) {
driver.get("https://www.google.com");
}
#AfterAll
public static void tearDownAll(WebDriver driver) {
driver.quit();
}
Unfortunately, only the Chrome browser will open.
Upd: I also found that there is a message saying:
Browser list for context id is not found. Not sure how to set up Browsers List if it is needed.
So far I did not find multi browsers support except by explicitly putting the browsers type into mvn command like below:
mvn verify -Dtest=BaseTest
-Dsel.jup.selenium.server.url=http://localhost:4444/wd/hub
-Dsel.jup.default.browser=chrome
-Dsel.jup.default.version=80.0.3987.106
#ExtendWith(SeleniumExtension.class)
public class BaseTest {
#Test
public void testNumber1(RemoteWebDriver driver) throws {
driver.get("https://www.google.com/");
}
#AfterAll()
public static void tearDown(RemoteWebDriver driver) {
driver.quit();
}
}
Update:
I figured out the way I can do it with Test Template too.
Below is the working example:
public class MultiBrowserTestTemplate {
#RegisterExtension
static SeleniumExtension extension = new SeleniumExtension();
#BeforeAll
static void setup() {
String browsersList = System.getProperty("prop.browsers.list");
List<String> browsers = Arrays.asList(browsersList.split(","));
if (browsers.contains("chrome")) {
extension.addBrowsers(BrowserBuilder.chrome().version("80.0.3987.106").build());
}
if (browsers.contains("firefox")) {
extension.addBrowsers(BrowserBuilder.firefox().version("73.0").build());
}
}
}
public class MultiBrowserDemoTest extends MultiBrowserTestTemplate {
#TestTemplate
public void testInMultipleBrowsers(WebDriver driver) {
driver.get("https://www.google.com/");
WebElement search = driver.findElement(By.name("q"));
search.sendKeys("JUnit5 extensions");
search.submit();
}
And the maven command goes like this:
mvn verify -DMultiBrowserDemoTest
-Dsel.jup.selenium.server.url=http://localhost:4444/wd/hub
-Dprop.browsers.list=chrome,firefox
I have a parent web test which is called by the test class like this:
public class Webtest
{
protected static WebDriver driver;
#BeforeMethod
public static WebDriver openUrl(String URL)
{
driver = new FirefoxDriver();
driver.get(URL);
System.out.println("Driver started :"+ driver);
return driver;
}
public static WebDriver closeDriver(){
driver.quit();
System.out.println("Driver closed :"+ driver);
}
}
Now I implement the above in a test class extending it.
public class testClass extends WebTest
{
#Test
public void TC01()
{ System.out.println("Test1:" + driver);
// Do something using driver
}
#Test
public void TC02()
{
System.out.println("Test2:" + driver);
// Do something
}
}
Now the results:
Driver started :FirefoxDriver: firefox on MAC (dfe4e055-4555-0d4d-8a83-a9a802159ea7)
Test1:FirefoxDriver: firefox on MAC (dfe4e055-4555-0d4d-8a83-a9a802159ea7)
Driver closed :FirefoxDriver: firefox on MAC (dfe4e055-4555-0d4d-8a83-a9a802159ea7)
Driver started :FirefoxDriver: firefox on MAC (1370df47-483b-574c-9792-9bb5fa077364)
Test2:FirefoxDriver: firefox on MAC (1370df47-483b-574c-9792-9bb5fa077364)
[Error] resulted in an exception: The FirefoxDriver cannot be used after quit() was called.
Basically, I assume the test2 is using the previous driver. I haven't called the second driver to quit yet but am getting the error. I did put sleep in between every method and tried to but nothing worked. Any help? I am using firefox 46.
Since you defined your openUrl method as a #BeforeMethod it is being called before all other methods, so when your testClass calls TC01, it opens a new browser first. Then when you call TC02, the #BeforeMethod gets invoked again and another, new WebDriver is created. That does not explain the last line error, though. I'm not sure why it would ever execute the quit method since the closeDriver method never seems to be called.
Here is the solution to your Question:
You need to address a lot of issues in your code as follows:
In Webtest class, within closeDriver() method, you are quit the driver driver.quit() still you trying to get WebDriver in return public static WebDriver closeDriver().
So change it to public static void closeDriver()
In testClass class, you are trying to extend WebTest but your base class is Webtest.
So change it to public class testClass extends Webtest
To work with Selenium 3.4.0 along with geckodriver v 0.16.1 & latest Mozilla Firefox 53.x you need to download the latest gecko driver and mention the absolute path in your code theough System.setProperty before you initialise the driver as follows:
System.setProperty("webdriver.gecko.driver", "C:\\your_directory\\geckodriver.exe");
driver = new FirefoxDriver();
In Webtest I can see your are accepting the URL as an argument public static WebDriver openUrl(String URL) but I dont see you passing it from Webtest. Keep it simple, define the String URL within openUrl() method as follows:
String URL = "http://gmail.com";
System.setProperty("webdriver.gecko.driver", "C:\\Utility\\BrowserDrivers\\geckodriver.exe");
driver = new FirefoxDriver();
driver.get(URL);
In closeDriver() you are quitting the driver by driver.quit(); next if you System.out.println("Driver closed :"+ driver); you won't get any realtime value of the driver instance but only null.
Finally, the entire chaos is created because you have added #BeforeMethod annotation to open the driver but haven't released it closeDriver() method using #AfterMethod annotation. Add the annotation #AfterMethod.
Here is your own working code along with some simple tweaks:
class Webtest :
public class Webtest
{
protected static WebDriver driver;
#BeforeMethod
public static WebDriver openUrl()
{
String URL = "http://gmail.com";
System.setProperty("webdriver.gecko.driver", "C:\\Utility\\BrowserDrivers\\geckodriver.exe");
driver = new FirefoxDriver();
driver.get(URL);
System.out.println("Within openUrl() - Driver started :"+ driver);
return driver;
}
#AfterMethod
public static void closeDriver()
{
driver.quit();
System.out.println("Driver closed :"+ driver);
}
}
class testClass :
public class testClass extends Webtest
{
#Test
public void TC01()
{
System.out.println("Within TC01 - Test1:" + driver);
// Do something using driver
}
#Test
public void TC02()
{
System.out.println("Within TC02 - Test2:" + driver);
// Do something
}
}
Let me know if this Answers your Question.
I started encountering problems when I use static objects reference for WebDriver and run the tests in parallel.
public static WebDriver driver;
Hence I decided to use non-static object reference for the WebDriver.
private WebDriver driver;
Now when I use POM with Page Factory, my understanding is that everytime I create a Test I will have to be creating a new Object in the test class as shown below.
/* Constructor in the Page Object class */
private WebDriver driver;
public LoginPage(WebDriver driver) {
this.driver = driver;
PageFactory.initElements(driver, this);
}
2 testcases as shown below in the same class.
private LoginPage loginPage;
#Test
public void testCase1() {
loginPage = new LoginPage(getDriver());
loginPage.sendkeys("sometext");
}
#Test
public void testCase2() {
loginPage = new LoginPage(getDriver());
loginPage.sendkeys("sometext");
}
My question here is a
Am I right in creating page object for every test cases?
Is there any way I can optimize this? Because One doubt I got is that non-static object reference may be getting overridden and causing problems in one of the methods if I run them in parallel.
Sorry if my query is naive. Any help would be appreciated.
You do not need to initialize it again. Also, initialize the pages in #BeforeTest rather than in test cases.
Here i would like to give you example of Page object model. Hope you can relate this.
My Main test:
#Before
public void SelectBrowser(){
driver = WebUtils.SelectBrowser(driver,"Chrome");
}
#Test
public void LoginToGmail() throws InterruptedException{
//WebDriver driver = new FirefoxDriver();
//MAximize the Screen
driver.manage().window().maximize();
//Go to Gmail Login Page
SignInPage SignInPage = new SignInPage();
WebUtils.GoToSignInPageForPropertyFile(driver, "URL");
//Click on Next
SignInPage.ClickToLogin(driver, By.cssSelector("input[id='next']"));
Now Supporting class:
GoToSignInPageForPropertyFile method will be in WebUtils
Whatever i write in Webutils will be used by each page object class.
For e.g.
public class WebUtils {
public static pageobject.SignInPage GoToSignInPageForPropertyFile(WebDriver driver, String URL) {
ReadFileData File = new ReadFileData();
Properties Values = File.ReadFile();
driver.get(Values.getProperty("URL"));
return PageFactory.initElements(driver, pageobject.SignInPage.class);
}
}
Now the method ClickToLogin is defined under SignInPage class as:
public class SignInPage {
public EmailViewPage ClickToLogin(WebDriver driver, By by) {
WebUtils.Click(driver, by);
return PageFactory.initElements(driver, EmailViewPage.class);
}
}
Which will further be in Webutils
public class WebUtils {
public static void Click(WebDriver driver, By by) {
WebElement Element = driver.findElement(by);
Element.click();
}
}
I had tried to run below JUnit (Selenium WebDriver) test case to open Google in Chrome browser, but it is failing with error message as
"The path to the ChromeDriver executable must be set by the
webdriver.chrome.driver system property; for more information, see
http://code.google.com/p/selenium/wiki/ChromeDriver."
As specified in that website, I downloaded ChromeDriver.exe but don't know,
Which PATH should I place that? or
How to set ChromeDriver path in webdriver.chrome.driver?
Please Advise.
My JUnit test case (changed the Firefox Driver to Chrome Driver):
import org.junit.*;
import org.openqa.selenium.*;
import org.openqa.selenium.chrome.*;
public class Chrome_Open_Google {
private WebDriver driver;
private String baseUrl;
#Test
public void Test_Google_Chrome() throws Exception {
driver = new ChromeDriver();
baseUrl = "http://www.google.co.uk/";
driver.get(baseUrl);
}
#After
public void tearDown() throws Exception {
driver.quit();
}
}
I believe you have several options:
Either specify the folder (in which your chromedriver binary is) in your PATH system variable - here's how
Or give you application webdriver.chrome.driver as a system property by calling it with -Dwebdriver.chrome.driver=the/path/to/it parameter.
Or the same programatically: System.setProperty("webdriver.chrome.driver", "your/path/to/it");
Or this:
private static ChromeDriverService service;
private WebDriver driver;
#BeforeClass
public static void createAndStartService() {
service = new ChromeDriverService.Builder()
.usingChromeDriverExecutable(new File("path/to/my/chromedriver"))
.usingAnyFreePort()
.build();
service.start();
}
#Before
public void createDriver() {
driver = new RemoteWebDriver(service.getUrl(), DesiredCapabilities.chrome());
}
#After
public void tearDown() throws Exception {
driver.quit();
}
#AfterClass
public static void createAndStopService() {
service.stop();
}
System.setProperty("webdriver.chrome.driver", "your\path\to\it");
For Eg :
System.setProperty("webdriver.chrome.driver", "C:\\Selenium\\driver\\chromedriver.exe");
driver = new ChromeDriver();
driver.manage().window().maximize();
I want easy way to launch Selenium webdriver instance and run various tests on it. I'm trying to do this in Suite file, but it doesn't work. Instance is killed instantly. Is there any alternatives on how to do this?
Potentially I want to add more drivers (IE, Chrome) in this suite and if possible launch separately. Any suggestions welcome.
namespace NUnit.Tests
{
public class AllTests
{
private static IWebDriver _Driver;
[TestFixtureSetUp]
public void SuiteSetUp()
{
_Driver = new FirefoxDriver();
}
[TestFixtureTearDown]
public void SuiteTearDown()
{
try
{
_Driver.Quit();
}
catch (Exception)
{
// Ignore errors if unable to close the browser
}
}
[Suite]
public static TestSuite Suite
{
get
{
LoginTest lt = new LoginTest { Driver=_Driver };
suite.Add(lt);
AnotherTest at = new AnotherTest { Driver=_Driver };
suite.Add(at);
return suite;
}
}
}
}
I did this in Java, I made a base class, declared the webdriver as static, put my startup/config methods in this class and then extended it in to each test class i made.
Im sure its the same for C#.
Trying to run this with base class / extended classes failed. As webdriver instance didn't get initialized properly and couldn't be killed properly. Instead I created SetupIE(), SetupChrome(), SetupFirefox() methods in Suite and also created teardown method that would work as last test for suite.
Here is the code:
namespace TestNamespace
{
using System;
using NUnit.Framework;
using NUnit.Core;
using SeleniumTests;
using OpenQA.Selenium;
using OpenQA.Selenium.IE;
using OpenQA.Selenium.Firefox;
using OpenQA.Selenium.Chrome;
using OpenQA.Selenium.Support.UI;
class AllTests
{
public static IWebDriver WebDriver { get; private set; }
[Suite]
public static TestSuite Suite
{
get
{
TestSuite suite = new TestSuite("All Tests");
//Setup a Web driver (see methods below for different browsers) - SetupIE(), SetupChrome(), SetupFirefox()
SetupIE();
// Add tests to suite
suite.Add(new FlashLoadedTest { Driver = WebDriver });
// Tear down a Web driver
suite.Add(new TearDownTest { DriverToTearDown = WebDriver });
// return suite to NUnit
return suite;
}
}
// Method that's initialises FireFox Driver
private static void SetupFireFox()
{
WebDriver = new FirefoxDriver();
}
// Method that's initialises IE Driver
private static void SetupIE()
{
WebDriver = new InternetExplorerDriver();
}
// Can't get this working, but this is how its supposed to work
private static void SetupChrome()
{
WebDriver = new ChromeDriver(#"C:\Users\<user>\AppData\Local\Google\Chrome\Application");
}
// Class with a test that tears down browser instance
[TestFixture]
class TearDownTest
{
public IWebDriver DriverToTearDown;
[Test]
public void TearDownBrowser()
{
if (DriverToTearDown == null)
Assert.Fail("No Browser to Tear Down");
try
{
DriverToTearDown.Close();
DriverToTearDown.Dispose();
}
catch
{
Assert.Fail("Browser failed to tear down");
}
}
}
}
}
I appreciate this is a little late but may prove useful for future readers.
I created a base class containing a firefox driver with the following and it works perfectly for me. You can then simply reference the base class (Driver in this instance) from your derived test class. Worth noting I'm using C# and Nunit.
Code for base class is:
namespace yournamespace
{
public class Driver
{
public IWebDriver driver;
public StringBuilder verificationErrors;
public Driver()
{
driver = new FirefoxDriver(); //replace with required driver
verificationErrors = new StringBuilder();
}
}
}
Then simply called the 'Driver' class from my test class:
[TestFixture]
public class IMSLogin : Driver
{
//.. all the usual bits and bobs!