0

I have differing behaviour between Capybara tests when run with Selenium / geckodriver and Poltergeist / phantomjs drivers. Ultimately, I want to know why I'm seeing different CSS results being produced in one set of tests and how I can

Please excuse me if you feel that I have not articulated this problem very well. The problem exists in a current project I am developing to help me improve my RSpec/Capybara/JavaScript skills.

In brief, I have a page that allows a 3- or 6-digit hexadecimal value to be submitted on a page. The hexadecimal value, now as a query parameter value on the resulting page, is then assigned to a CSS property to colour the background of an element on the resulting page. JavaScript is responsible for passing the parameter value into the CSS property:

if (document.readyState === "complete") { processForm(); }
window.onload = function  processForm()
{
  var  url_parameters = location.search.substring(1).split("&");
  var  param_value = url_parameters[0].split("=");
  colour_value = decodeURI(param_value[1]);
  document.getElementById('html_custom_colour').innerHTML = colour_value.toString();
  var  html = document.getElementsByTagName('html')[0];
  html.style.cssText = "--custom-colour: #" + colour_value;
}

My Capybara tests are configured to submit the hexadecimal value, convert the value to an RGB value and then the RSpec matchers expect that RGB value as the CSS property that creates the background colour of an element on the resulting page:

I'm using the Selenium driver in this configuration:

Capybara.default_driver = :selenium
Capybara.javascript_driver = :poltergeist

When using the Selenium drivers, these tests pass, with the expected value matching that of the value on the resulting page. Using pp, I can output the result being fetched from the styling:

    And I should see the text "The selected colour is #<colour>"             # features/colours.feature:27

    Examples: 
      | colour |
{"background-color"=>"rgb(102, 0, 255)"}
      | 6600ff |
{"background-color"=>"rgb(255, 85, 0)"}
      | f50    |
{"background-color"=>"rgb(255, 255, 255)"}
      | ffffff |
3 scenarios (3 passed)
24 steps (24 passed)
0m3.881s

I've tested the tests with incorrect values for the matchers to be sure it can fail if not looking for the values the resulting page is producing.

When I switch to the Capybara.default driver to poltergeist, the tests fail. The expectation for the RGB value (now an rgba value) the same for every scenario example: rgba(0, 0, 0, 0), indicating the value has not been set correctly by the JavaScript:

colour_value 6600ff
{"background-color"=>"rgba(0, 0, 0, 0)"}
      | 6600ff |
      expected to find text "rgb(102, 0, 255)" in "{\"background-color\"=>\"rgba(0, 0, 0, 0)\"}" (RSpec::Expectations::ExpectationNotMetError)
      ./features/step_definitions/colours.rb:47:in `/^I should see the colour "(.*?)"$/'
      features/colours.feature:32:26:in `I should see the colour "6600ff"'
colour_value f50
{"background-color"=>"rgba(0, 0, 0, 0)"}
      | f50    |
      expected to find text "rgb(255, 85, 0)" in "{\"background-color\"=>\"rgba(0, 0, 0, 0)\"}" (RSpec::Expectations::ExpectationNotMetError)
      ./features/step_definitions/colours.rb:47:in `/^I should see the colour "(.*?)"$/'
      features/colours.feature:33:26:in `I should see the colour "f50"'
colour_value ffffff
{"background-color"=>"rgba(0, 0, 0, 0)"}
      | ffffff |
      expected to find text "rgb(255, 255, 255)" in "{\"background-color\"=>\"rgba(0, 0, 0, 0)\"}" (RSpec::Expectations::ExpectationNotMetError)
      ./features/step_definitions/colours.rb:47:in `/^I should see the colour "(.*?)"$/'
      features/colours.feature:34:26:in `I should see the colour "ffffff"'

Interestingly, the tests fail on the same results for the Selenium driver if I comment out the javascript_driver. Why is it now looking for an rgbavalue instead of rgb? Why is the value always rgba(0, 0, 0, 0)? I read the following articles, suspecting that it may be the way the elements are grabbed from the page in JavaScript: Javascript Error Null is not an Object Javascript - How to detect if document has loaded (IE 7/Firefox 3)

I thought I was loading the JavaScript in the correct way, but it seems that I am not really waiting for the page to reach the "complete" state before trying to grab the elements from the page due to the window.onload(): If I remove it so that the JavaScript must wait for the page state to be "complete", then the Selenium tests fail in the same way the poltergeist tests do.

So how can it pass with the Selenium driver but not the Poltergeist driver? Is the issue related to the drivers or the way the JavaScript is loaded? Or is it something else?

jimjamz
  • 59
  • 6

1 Answers1

0

Poltergeist depends on PhantomJS which today is equivalent to a > 5 year old version of Safari. It doesn't support modern CSS/JS, so I'm guessing you have something in your JS and/or CSS which it doesn't support. Trying to use poltergeist nowadays is going to be an exercise in frustration.

Thomas Walpole
  • 48,548
  • 5
  • 64
  • 78