Question: Can selenium be used for real world testing? & Does it take longer than manual?

TLDR; Question: Can selenium be used for real world testing? And does it take longer to create different scenarios/permutations than just testing the system manually? A: Yes, Probably

I received the following Question via email from a reader, and since the answer expanded, I moved it to the blog.

Question: Can selenium be used in testing real world scenarios? And would spending time programming selenium to create different scenarios/permutations take longer than using the system manually creating scenarios through exploration?

Short Answers – Yes it can be used for Real World Scenarios. And probably takes longer than interacting manually.

Longer Answers…

Continue reading

Posted in WebDriver | Leave a comment

Q: Should you use Selenium 3? A: Probably. I have.

TLDR; moving between Selenium 2.53.1 and 3.0.1 takes very little effort. You should probably try it.

Wow, so Selenium 3.0.0 and then Selenium 3.0.1 in just a few days. Should you use it?

I have a fairly small set of tests that I use on my Selenium WebDriver Online Course and I’ve run these against pretty much every version of Selenium WebDriver and browser version released.

I spent time last week and this week running them against:

  • Selenium 2.53.1
  • Selenium 3.0.0
  • Selenium 3.0.1

To be honest, I wasn’t expecting Selenium 3 to move out of Beta so fast. I wasn’t expecting this extra work so soon. But having a stable version is all the better because now I don’t have to answer questions about beta software.

The most obvious difference between Selenium 3.0.1 and Selenium 3.0.0, for me, was that HTMLUnit (v 2.23) works in Selenium 3.0.1. So I wouldn’t use Selenium 3.0.0.

Now my choice is between 2.53.1 or 3.0.1

Getting Started

Creating instructions to help people get started with WebDriver is a painful job when the version keeps changing and drivers keep changing names so I’m happy for some stability

I’ve updated my Start Using Selenium WebDriver project:

https://github.com/eviltester/startUsingSeleniumWebDriver

  • to use 3.0.1 in the pom.xml
  • updated the speedrun install notes

I’ve left instructions for 2.53.1 in there, but I’ll phase those out after a few point releases of Selenium 3.

I recommend that people starting to learn Selenium WebDriver use Selenium 3.0.1 and use ChromeDriver as their default browser.

  • you’ll be up to date
  • you’re more likely to receive support rather than “upgrade to Selenium 3.0.1”

Why ChromeDriver?

Because it is much more mature than GeckoDriver, and if you do want to drop back to Selenium 2.53.1 you won’t have to make any changes.

WebDriver in CI locally and with Cloud vendors

I have a simple CI project on github

I run this locally on a bunch of browsers through Jenkins, and on travis-ci, and against SauceLabs and BrowserStack.

I had to make minor code changes when starting Firefox to upgrade to Selenium 3 and I found no obvious issues.

So I have upgraded my wdci project to use Selenium 3.0.1

  • SauceLabs:
    • Windows 10 – Edge v 14.14393
    • Windows 10 – Chrome v 53.0
    • Windows 10 – IE v 11.103
    • Windows 10 – FIREFOX v 49.0
    • Apple Mac – OS X 10.11, Safari 9.0
  • BrowserStack:
    • Windows 10 – Edge v 13
    • Windows 10 – Chrome v 53.0
    • Windows 10 – IE v 11
    • Windows 10 – FIREFOX v 49.0
    • Apple Mac – “El Capitan”, Safari 9.1
  • Locally
    • Windows 10 – Edge v 13
    • Windows 10 – Chrome v 53.0
    • Windows 10 – IE v 11
    • Windows 10 – FIREFOX v 49.0
    • Windows 10 – HTMLUnit v 2.23
  • Travis-ci
    • Linux HTMLUnit v 2.23
    • Linux Firefox v 47.1

All I had to change was how I started Firefox browser. Now this isn’t a particularly large set of tests, or even complicated tests. So it might not be enough to convince you.

What about Grid?

I normally try and use remote grids and they worked fine.

I did try on a local grid and the only thing I had to change was the version number in the file name of the selenium jar. Everything else worked for me.

Admittedly I don’t ‘do’ much with the local grid. But for basic usage I found no issues.

In fact, GeckoDriver v 0.11.1 worked better from a grid node, than it did from calling directly.

What about bigger code bases?

I haven’t found any issues with ‘Selenium’ in my main code.

My issues tend to be cross-browser or ‘cross-driver’ related, rather than Selenium related. And mainly relate to synchronisation – the bane of cross-platform execution.

i.e. Moving from Selenium 2.53.1 to 3.0.1 made no obvious difference to Edge, IE, Chrome, Safari

For Firefox, clearly we have to change how we instantiate the driver, and GeckoDriver is still a work in progress. But the legacy Firefox driver in Selenium 3.0.1 works just as well as the one in 2.53.1 so if you’re still using the FirefoxDriver rather than GeckoDriver I don’t think you’ll notice a difference during execution.

Issue Conflation

The problem I found was my tendency to conflate ‘driver’ issues with ‘Selenium’ issues.

It is easy to do that since we tend to upgrade driver versions at the same time as Selenium, and – in the case of HTMLUnit, I had to update the driver when I updated selenium.

But by moving to Selenium 3, we will hopefully have less of that confusion since the separation between driver and Selenium becomes much cleaner.

Summary

  • I have updated all my teaching projects to Selenium 3.0.1
  • It doesn’t take much to upgrade to Selenium 3. Hopefully for most projects it is a small tweak to the driver abstraction layer and you’ll be up and running quickly.
  • And you can continue using FirefoxDriver in legacy mode if that is still your default browser and driver.
  • Remember not to conflate ‘driver’ issues with Selenium 3 ‘issues’.

Since it is so easy to upgrade, and drop back to 2.53.1 if you need to. I think it is worth trying.

 

NOTE: 20161020 – updated to say that local grid worked fine when I tried it too.

Posted in WebDriver | 2 Comments

Sometimes a headless browser might meet your needs

TLDR; Don’t rule out headless browsers like HTMLUnit, just because no-one uses them in the real world. They might make automating your task easier and faster.

Have you ever been told that HTMLUnit and PhantomJS (and insert any other headless browser in here) “are not real browsers, customers don’t use them, so we shouldn’t use them for testing”.

I don’t agree with that statement because I think the statement makes the overly broad assumption that “when we automate the browser to trigger functionality, we want to ‘test that it works in the browser’”

When we automate as part of our test process, we don’t have to do everything as though a customer did it.

Sometimes:

  • I don’t automate to ‘test that it works in a browser’.
  • I automate a task, not testing.
  • I don’t want to ‘test’ with the browser, I want to send a message, to the backend, that a browser would send.
  • I want to check that the server responds appropriately to a browser generated message.
  • I want to test the backend, not the frontend/backend integration in a specific browser.
  • I use the browser because I want to trigger a ‘form’ submission, and automating the form submission without a browser requires that I treat the “App as API” and that requires more work to mitigate the risk that: the ‘form’ I submit artificially matches the ‘form’ submitted by a browser.

The appropriateness of the automated manipulation approach depends on what part of the system we want to test.

When I want to check that Firefox submits the form correctly to the backend, and the backed processes it correctly and returns a message to Firefox, then I automate Firefox.

But when I want to check that the backed processes a submitted form correctly and returns a message to the sender, then I can automate using a headless browser, if that makes the job easier and faster.

I don’t always automate for ‘testing’

Sometimes I don’t automate to ‘test’. Sometimes I automate tasks.

Tasks that I would normally do through the GUI, but I only want to ‘use’, not ‘test’, the GUI :

  • setup data
  • bulk verify data in the system, prior to testing
  • etc.

When might I choose a headless browser?

Why might we choose a headless browser?

If some of the following evaluated to true and you viewed them as important:

  • faster to start
  • more reliable over repeated runs
  • easier to setup
  • easier to run as part of the CI process than a real browser
  • fewer side-effects to tidy up in the event of failure e.g. browser windows left open
  • the functionality uses such basic HTML that it doesn’t need a ‘full’ browser
  • run task in background without a browser popping up
  • etc.

…then a headless browser might meet your needs.

But I could do ‘this’ instead

Good.

You don’t have to use a headless browser to achieve these benefits:

  • you could use the API if it exists and does what you need
  • you could use an HTTP library if it doesn’t introduce more risk and more work
  • you might be able to chain cURL or Wget (or other) commands in a shell script
  • you might identify other approaches

Do consider other options.

Do not assume that you always have to use a ‘real’ browser.

Summary:

You will have good reasons to run specific scenarios through a ‘real’ browser, but don’t rule out headless browsers for all tasks.

  • Adopt the belief that ‘headless browsers’ fit some circumstances well.
  • We automate ‘web’ interfaces to test the back end server processing as well as the front end and specific browser front end interaction with the backend.
  • Use tools that support the most appropriate manipulation interface for the functionality under test.
  • You may not need to use a ‘real browser’, but could use a Headless browser with the ‘real browser automating’ tools that you already know how to use
Posted in WebDriver | Leave a comment

Update on Marionette GeckoDriver v0.11.1 – Q: Should you try it? A: Yes you should.

Geckodriver has improved.

Over the last few months Geckodriver and WebDriver 3 have been conflated together. Certainly I’ve only investigated Geckodriver updates when I was looking into Selenium WebDriver 3.

And with version 0.11.1 released, now it is time to have a fresh look at Geckodriver.

  • Q: Does Firefox Marionette GeckoDriver v0.11.1 support WebDriver 2.53.1?
  • Q: Does Selenium 3 make a difference for Marionette GeckoDriver?
  • Q: Any workarounds for any issues?
  • Q: But GeckDriver is still pretty bad right?
  • Q: Should I try it?

Q: Does Firefox Marionette GeckoDriver v0.11.1 support WebDriver 2.53.1

A: Yes

Regardless if you upgrade to Selenium 3.0.0 you should upgrade to GeckoDriver v 0.11.1 when working with Selenium WebDriver.

Q: Does Selenium 3 make a difference for Marionette GeckoDriver?

A: I did find some differences using Selenium 3.0.0 with GeckoDriver v0.11.1 rather than Selenium 2.53.1

  • Alert tests passed, Select tests passed in 3.0.0 but they failed in 2.53.1 so some internal difference took place that affected GeckoDriver.

Q: Any workarounds for any issues?

A: I was experiencing an issue with Frames, and I put down to a bug in GeckoDriver.

It might be, it might not be, but I have a workaround.

GeckoDriver handles frames fine. But… you can’t use getTitle to pick up the title of the frame until you:

driver.switchTo().defaultContent();

I don’t need to do this for any other browser driver, but it makes a difference for GeckoDriver.

I often synchronise on ‘wait for title’ when performing an action that switches between frames, this allows that approach to work.

Q: But GeckDriver is still pretty bad right?

A: No.

It depends what you’re doing. You should try it and see. You’ll probably find it works fine for you.

On my course:

  • I have 182 tests that pass in Firefox 49.0.1 with Geckodriver v 0.11.1
  • I have 13 tests that fail in Firefox 49.0.1 with Geckodriver v 0.11.1

These are fairly obscure edge cases that you might not encounter in the real world because they are a symptom of a hard to test application:

  • Window management – jumping between open windows
  • Cookie manipulation

Some issues you might, but I try and avoid these in the ‘real world’ anyway:

  • Key chords having an extra char inserted
  • User Action Drag and Drop and moveToElement

Some probably have workarounds (e.g. like the defaultContent mentioned above, that I simply haven’t investigated yet).

Some of my issues were synchronisation issues – true, they don’t happen with other drivers, but cross browser, and cross driver, work sometimes means new synchronisation required.

e.g.

  • instead of

WebElement element= driver.findElement(By.id("_value_id"));

  • I had to (only for geckodriver) use:

WebElement element = wait.until(elementToBeClickable(By.id("_value_id")));

That’s just how it is sometimes.

I suspect my cookie issues might have workarounds that I just haven’t investigated yet.

Q: Should I try it?

A: Yes

Geckodriver works fine for ‘most things’.

Try it and see if it works for you.

You can use version 0.11.1 with 2.53.1 and 3.0.0 so you don’t have to change anything – just the driver.

 

20161021 NOTE: I get better results with 0.11.1 when used in a grid node. I don’t receive any errors closing it down when it is used from a node, but when used directly my tests sometimes fail closing down the browser.

Posted in WebDriver | 2 Comments

Upgrading to Selenium 3 with My First Selenium Project

TLDR; set version to 3.0.1, stop using MarionetteDriver, download geckodriver v 0.11.1

Selenium 3 is out and you can read the big announcement.

You can also start to use it.

I’ll be checking my course against Selenium 3 later today, but for the moment, here are the steps you need to take to upgrade.

Upgrading to Selenium 3.0

Using startUsingSeleniumWebDriver as an example.

Change the pom.xml

        <dependency>
            <groupId>org.seleniumhq.selenium</groupId>
            <artifactId>selenium-java</artifactId>
            <version>2.53.1</version>
        </dependency>

Becomes:

        <dependency>
            <groupId>org.seleniumhq.selenium</groupId>
            <artifactId>selenium-java</artifactId>
            <version>3.0.1</version>
        </dependency>

Tadah!

Not quite Tadah

For Marionette, we need to update to the most recent version.

https://github.com/mozilla/geckodriver/releases

At the time of writing – version 0.11.1

With Selenium 3, MarionetteDriver is deprecated.

My test MyFirstTestFF48 uses MarionetteDriver.

I can see that MarionetteDriver is deprecated

But it still works, provided I have Marionette geckodriver setup correctly.

It works if I install v 0.11.1 of Marionette Driver and have it named as geckodriver.exe on the path. But I should migrate away from using MarionetteDriver in my code because it is deprecated.

Back to FirefoxDriver

FirefoxDriver now defaults to use the Marionette driver.

So I can use Marionette by running my FirefoxDriver test.

Which uses FirefoxDriver

Selenium 3, by default.

  • FirefoxDriver now uses Marionette.
  • No longer have to rename geckodriver.exe to wires.exe
  • now use geckodriver.exe

If you want to switch between 2.53.1 and 3.0.1 I’d add the Marionette driver folder to the path and:

  • have v 0.9.0 named as wires.exe
  • have v 0.11.1 named as geckodriver.exe

My firefox test:

mvn test -Dtest=MyFirstTest

Works if I install v 0.11.1 of Marionette Driver and have it named as geckodriver.exe on the path and I use FirefoxDriver to instantiate the driver.

Firefox Marionettte Summary:

To use Marionette geckodriver.exe for Firefox with Selenium 3:

Legacy Firefox?

What if you want to use the built in FirefoxDriver e.g. for Firefox Extended Support Release or portable Firefox?

Well, you still can, you just have to:

  • set the Firefox driver capability “marionette” to false
  • set the firefox_binary capability to the path of your legacy firefox

e.g.

DesiredCapabilities capabilities = DesiredCapabilities.firefox();
capabilities.setCapability("marionette", false);
capabilities.setCapability("firefox_binary",
       new File(System.getProperty("user.dir"),
       "/tools/FirefoxPortable/FirefoxPortable.exe").
              getAbsolutePath());
WebDriver driver = new FirefoxDriver(capabilities);

Work to do

I have some work to do to update the startUsingSeleniumWebDriver and check my course tests against Selenium 3. If I have to update anything I’ll blog about it here.

Summary

  • Update pom.xml to use <version>3.0.0</version>
  • download the latest version of geckodriver.exe
  • add geckodriver.exe to the path
  • use FirefoxDriver in your code
  • set "marionette" capability to false if we want to use legacy FirefoxDriver

Posted in WebDriver | 6 Comments

Updated WebDriver SpeedRun Install Videos

Because I know that some people just want help getting started quickly.

I created the Selenium WebDriver SpeedRun Install page. This has:

  • A simple WebDriver project that you can download and run
  • A check list of instructions for installing Java and WebDriver
  • Some tutorial videos showing how to install on Windows and Mac

I have just updated this to cover:

  • Firefox, Marionette, GeckoDriver
  • Chrome, ChromeDriver
  • Maven 3.3.9
  • IntelliJ 2016.2
  • Windows
  • Mac

If there is a faster and easier set of ‘getting started’ videos for Windows and Mac then let me know so I can improve.

If you haven’t started working with Selenium WebDriver yet, give the install videos and checklist a try.

 

 

Posted in Get Started | Leave a comment

How to Select a Web Element with an id containing ‘.’

TLDR: \.

Lesson learned.

I was working with a site and trying to select an element via its id e.g.

<p id="select.me.by.id">Select Me By My id</p>

Simples thought me:

  • #select.me.by.id

Nope.

So I did what all good Selenium debuggers do… I tried in the browser but Chrome didn’t match it.

Tempted though I was to blame Chrome, I tried with XPath, and that worked fine:

  • //p[@id='select.me.by.id']

After a bit of web searching, the solution was clear.

In CSS I wasn’t saying, find the id select.me.by.id

I was saying find the id select with class me by id which was not at all what I wanted.

Fortunately CSS offers escaping, which I didn’t realise.

Until the app is fixed I can locate the id using CSS with:

  • #select\.me\.by\.id

Posted in FAQ, Selenium Simplified | Leave a comment

How to Debug WebDriver JavascriptExecutor in Java

TLDR; JavascriptExecutor requires us to learn JavaScript and use the Browser Console, and check your locator assumptions using FirePath

A common theme when debugging WebDriver code is the need to jump between breakpoints, evaluate and browser dev tools.

And we shall do exactly that in this ‘how to’, when we look at debugging JavascriptExecutor. This is a hypothetical set of actions built around a sample test I was sent by a blog reader. And I’m walking through a debug process to illustrate some points. It is not the most efficient debug process, but very often, we don’t know what the problem is, so our process isn’t efficient. And when you start working with a ‘block of existing code’ it often is not efficient.

Assume we have this test:

private static WebDriver driver;

@Before
public void setDriver() {
    driver = new FirefoxDriver();
}

@Test
public void inputText() throws Exception {
    driver.get("http://compendiumdev.co.uk/selenium/testpages/html5_html_form.html" );

    WebElement textField = driver.findElement(By.name("number_field"));

    writeText(textField, "");
    Assert.assertEquals("", textField.getAttribute("value"));
    writeText(textField, "35");
    Assert.assertEquals("35", textField.getAttribute("value"));

    driver.findElement(By.id("submitButton")).click();
    Assert.assertEquals("35", driver.findElement(By.id("_valuenumber_field")).getText());
}

public void writeText(WebElement textField, String text) {
    ((JavascriptExecutor) driver).executeScript("arguments[0].value='" +
            text + "';", textField);
}

And it doesn’t work. The second Assertfails, so we suspect probably something wrong with the Javascript, but we didn’t get an error, so it isn’t a syntax error.

What do we do?

Well, we could hack about a bit with the writeText method and change the Javascript.

public void writeText(WebElement textField, String text) {
    //((JavascriptExecutor) driver).executeScript("arguments[0].value='" +
    //        text + "';", textField);
    ((JavascriptExecutor) driver).executeScript("arguments[0].setAttribute=('value','" +
                    text + "';", textField);
}

Nope, that gives a syntax error on the JavaScript.

I’ll rewrite that method to make it a little easier to read:

public void writeText(WebElement textField, String text) {
   
    String js;
    JavascriptExecutor exec = (JavascriptExecutor) driver;
   
    //js = String.format("arguments[0].value='%s';",text);
    //exec.executeScript(js, textField);

    js = String.format("arguments[0].setAttribute=('value','%s';",text);
    exec.executeScript(js, textField);
}

Note: this is now much easier for me to breakpoint, debug and evaluate, but I don’t think I’ll learn much here by doing that.

And the code is now more readable and it is obvious what the syntax error is, I missed off a ‘)’.

So I’ll fix the syntax error. And…

js = String.format("arguments[0].setAttribute=('value','%s');",text);

Yeah, and that’s not how you call setAttribute…

OK. Time to stop hacking about in Java and start debugging.

First use the console

First I’m going to execute the JavaScript in the console.

That means rewriting it.

I find the element using By.name in Java, so I’ll use the console and type:

document.getElementsByName("number_field")[0]

That is equivalent to the findElement(By.name("number_field"))

And it shows me:

<input type="number" value="12" name="number_field">

Which is the same as the input field on screen which defaults to 12.

So I’ll set the value using setAttribute

document.getElementsByName("number_field")[0].setAttribute('value','13');

Then check that the attribute is set

document.getElementsByName("number_field ")[0].value

And the console tells me “13” but the GUI stills says “12”.

Hmmm…

Thinking that I should use ‘value’ instead, just in case, I’ll try.

document.getElementsByName("number_field")[0].value='14';

And then check it was set:

document.getElementsByName("number_field ")[0].value

And the console tells me “14” but the GUI stills says “12”.

OK.

Let me check first assumptions and check the locator.

Using FirePath in Firefox:

[name="number_field"]

Oh. FirePath is showing me two fields with that name, both with a default value of ‘12’.

And the one I want is the second one.

Let me just try that JavaScript again.

document.getElementsByName("number_field")[1].value='15';

And that changed it on the GUI as well.

So I’ve found my problem.

Model the console JavaScript in the Java Code

First I’ll change the JavaScript method to be equivalent to what I did above.

public void writeText(WebElement textField, String text) {

    String js;
    JavascriptExecutor exec = (JavascriptExecutor) driver;

    js = String.format("arguments[0].value='%s';",text);
    exec.executeScript(js, textField);
}

And then I’ll change how I locate the element:

WebElement textField = driver.findElements(By.name("number_field")).get(1);

Which is actually pretty close to what I wrote in JavaScript.

And try the @Test

And it worked.

At this point I might want to try and refactor the locator to avoid a findElements but if that isn’t possible, I’ll leave it as it is. (for now).

But I’ll add a comment:

/* there are two inputs named “number_field” the first in a non-displayed, prototype form */

And either amend the web page or raise a bug against the system.

We were slightly unlucky that the non-displayed form had the same value in the “number_field: as the main form. Otherwise an early assertion on the value of the found element might have revealed the problem early in the code. But my real problem stemmed from inspecting the element, but not running the locator through FirePath. I didn’t test the locator early enough.

Summary

When working with JavascriptExecutor:

  • Write the JavaScript code with String.format because string concatenation makes it hard to read
  • Run your code in the console (you might have to amend it a bit)
  • Check results in the console

When working with WebDriver:

  • Check your assumptions (locators) by running the same locator in FirePath or Chrome ‘find’

When coding, if you aren’t writing Unit tests (and very often when we work with WebDriver we don’t):

  • Run your code as early as you can, to avoid writing a lot of code that you have to debug
  • Write code simply, e.g. inline, then ‘extract to method’ when it is working
  • Assert often, you can always remove redundant and irrelevant asserts early

 

Posted in WebDriver | Leave a comment

How to debug chained WebDriver `findElement` methods in Java

TLDR; split code across lines and breakpoint, and use browser dev tools to test the locators used.

Have you ever had an argument about fluent code? Discussions about “train wrecks” and “impossible to debug”?

WebDriver has the ability to chain findElement calls, and create such “train wrecks”. How do you debug it if you use it? (There is a summary video at the bottom of this post.)

Example:

WebElement element =
driver.findElement(By.id("a8")).findElement(By.name("pName8")).findElement(By.tagName("a"));

Each findElement returns a WebElement. Each WebElement has a findElement method. So we can chain them.

This allows us to find an element, then find a child of that element, and then find a child of that element.

Why?

That’s not really important right now since I’m discussing debugging, but …

  • might lead to easier to read code that a complicated CSS or XPath
  • we could store the results in variables and that might be easier to maintain
  • because… options. And having options is important.

But if something goes wrong… train wreck

“If something goes wrong it is impossible to debug.”

So I’ve been told.

But it doesn’t have to be impossible. Let’s consider some strategies.

Strategies

Intermediate Variables

If the WebElement returned from each call to findElement was stored in a variable then we could breakpoint each line, and add a ‘watch’ for each variable.

WebElement anchor = driver.findElement(By.id("a8"));
WebElement paragraph = anchor.findElement(By.name("pName8"));
WebElement finalAnchor = paragraph.findElement(By.tagName("a"));

This might also make it easier to see that we are looking for: anchor > paragraph > finalAnchor.

New Lines

What?

Yup, add a new line in the code so it looks like this:

WebElement element = driver.findElement(By.id("a8")).
                    findElement(By.name("pName8")).
                    findElement(By.tagName("a"));

Then we can add a breakpoint to each line.

You don’t get the benefit of being able to watch the early calls in the chain, but you can always use evaluate to run the code when breakpointed.

What about debugging locators?

And suppose we breakpoint it, and can see what goes wrong. How do we know what to change it to?

When debugging locators and location strategies we want to do that interactively in the browser. I tend to use the Firebug FirePath plugin, but we have similar features in Chrome and Firefox Browser Dev Tools.

e.g. in Chrome I can right click, ‘inspect’ and in the ‘Elements’ tab, can use find (ctrl+f) to search using Xpath, or CSS selectors.

@Test
public void findElementChaining(){
    WebDriver driver = new FirefoxDriver();

    driver.navigate().
    to("http://www.compendiumdev.co.uk/selenium/find_by_playground.php");
    
    WebElement element = driver.findElement(By.id("a8")).
                        findElement(By.name("pName8")).
                        findElement(By.tagName("a"));
    
    Assert.assertEquals("This is h paragraph text", element.getText());
}

And if I try the selectors in the example code above I can see that #a8 matches an anchor, which has no children. I can see that the chained By.name ([name="pName8"]) will never match anything, since it is the same element as the previous id locator.

Summary

  • It is important to have options with the code you write.
  • Learn to use the Evaluate Tool in IntelliJ
  • Split ‘chained’ method calls across new lines to add breakpoints
  • Using intermediate variables might make code easier to read
  • Test locators in the browser interactively using Browser Dev Tools

Posted in WebDriver | 2 Comments

Selenium WebDriver 3.0.0-beta2 and JUnit and GeckoDriver v 0.10.0

I started to have a look at `Selenium WebDriver 3.0.0-beta2`

And my `@Test` methods were running from the IDE, but not running on CI.

The effect in CI was, no tests executing at all:

 
 Running TestSuite
 Configuring TestNG with: org.apache.maven.surefire.testng.conf.TestNG652Configurator@77468bd
 Tests run: 0, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.424 sec

I don’t use TestNG, I use JUnit.

Since this only happened when I switched to 3.0.0-beta2, and not in beta1 or 2.53.1, I raised a defect on github.

Luke pointed out that we can use the dependency management in Maven to exclude some of the dependencies.

Making my maven include for Selenium WebDriver 3.0.0-beta2 the following:

<dependency>
    <groupId>org.seleniumhq.selenium</groupId>
    <artifactId>selenium-server</artifactId>
    <version>3.0.0-beta2</version>
    <exclusions>
        <exclusion>
            <groupId>org.testng</groupId>
            <artifactId>testng</artifactId>
        </exclusion>
    </exclusions>
</dependency>

So I changed the `pom.xml` make to my CI project to run beta2

I also upgraded the Marionette/Geckodriver executable.

David Burns has released a v 0.10.0 version of GeckoDriver to use with the v 3.0.0-betas

  • https://github.com/mozilla/geckodriver/releases

So upgrade to that when working with 3.0.0-betaX

 

 

 

 

Posted in WebDriver | Leave a comment