Firefox ESR Release Calendar
The linked table shows the support lifecycle for Firefox Extended Support Releases (ESR) which we sometimes need to support for enterprise customers.
The ESR cadence works something like this:
- Firefox ESR freezes the then-current Firefox version for a year.
- During this year Mozilla backports security patches to the current ESR, but does not add features.
- Two subsequent ESR releases overlap for three months. This way enterprises have a quarter to test the new version and migrate their clients.
How to solve Selenium focus issues
Selenium cannot reliably control a browser when its window is not in focus, or when you accidentally interact with the browser frame. This will result in flickering tests, which are "randomly" red and green. In fact, this behavior is not random at all and completely depends on whether or not the browser window had focus at the time.
This card will give you a better understanding of Selenium focus issues, and what you can do to get your test suite stable again.
Preventing accidental interaction with the Selenium window
--------------------...
RSpec & Devise: How to sign in users in request specs
You know that Devise offers RSpec test helpers for controller specs. However, in request specs, they will not work.
Here is a solution for request specs, adapted from the Devise wiki. We will simply use Warden's test helpers -- you probably already load them for your Cucumber tests.
First, we define sign_in
and sign_out
methods. These will behave just like ...
Geordi 1.5.1 released
- Improve
geordi cucumber
: Only attempt @solo run when the specified files contain the @solo tag, skip @solo run if any filename is passed with a line number (e.g.features/example.feature:3
) - Improve
geordi deploy
: Find stages by their prefix (e.g.s
-> staging,m
-> makandra), bundle if needed, check the selected stage exists - Improve
geordi server
: Takes port as argument (e.g.geordi ser 3001
), option--public
(-P
) starts the server with-b 0.0.0.0
to make it accessible from other machines in the local network, e.g. ...
RSpec: ". not_to include" behaves like ".to exclude"
RSpec is smart when using the include
-matcher in combination with .not_to
. One could assume that
.not_to include(3, 4, 5)
evaluates to:
NOT( .to include(3, 4, 5) )
However, it behaves like:
.to (NOT include(3) && NOT include(4) && NOT include(5) )
Warning
Using
.not_to
in combination with theinclude
-matcher doesn't logically negate the final truth value. It instead negates the individual include-expectations for each argument.
Proof
describe 'RSpec' do
it "doesn't use logical nega...
Delete all MySQL records while keeping the database schema
You will occasionally need to clean out your database while keeping the schema intact, e.g. when someone inserted data in a migration or when you had to kill -9
a frozen test process.
Old Capybara versions already have the Database Cleaner gem as dependency. Otherwise add database_cleaner
to your *Gemfile`. This lets you say this from the Rails console:
DatabaseCleaner.strategy = :truncation
DatabaseCleaner.cl...
Hide your Selenium browser window with a VNC server
This is now part of geordi. Please don't follow the instructions below, if you use geordi.
Inspired by the recent headless Selenium note, I found yet another solution for the problem to hide your selenium tests away.
This has the advantages
^
- not to require a gem (so you do not force this on others)
- to allow you to take a look at the running webdriver if necessary
Simply make a script th...
Run Chrome in a specific resolution or user agent with Selenium
When you want to test how an web-application reacts in a specific resolution, you can set up a specific Selenium driver for some tests:
Before('@chrome320x480') do
Capybara.current_driver = :chrome320x480
end
After('@chrome320x480') do
Capybara.use_default_driver
end
You can use either chromium or chrome beta (as of 2012.05 the Version "19.0.1084.41 beta" works), or any other member of the family. It only needs to supports the "--window-size" command-line switch. [See this list](http://peter.sh...
Testing setTimeout and setInterval with Jasmine
Jasmine has a jasmine.clock()
helper that you can use to travel through time and trigger setTimeout
and setInterval
callbacks:
beforeEach(function() {
timerCallback = jasmine.createSpy("timerCallback");
jasmine.clock().install();
});
afterEach(function() {
jasmine.clock().uninstall();
});
it("causes a timeout to be called", function() {
setTimeout(function() {
timerCallback();
}, 100);
expect(timerCallba...
Capybara: How to find a hidden field by its label
To find an input with the type hidden, you need to specify the type hidden
:
find_field('Some label', type: :hidden)
Otherwise you will see an exception :
find_field('Some label')
# => Capybara::ElementNotFound: Unable to find field "Some label" that is not disabled`.
Note: Usually you don't need to check the input of hidden fields in an integration test. But e.g. waiting for a datepicker library to write the expected value to this field before continuing the test, which prevents flaky tests, is a valid use case.
Upgrade guide for moving a Rails app from Webpack 3 to Webpack 4
Webpacker is Rails' way of integrating Webpack, and version 4 has been released just a few days ago, allowing us to use Webpack 4.
I successfully upgraded an existing real-world Webpack 3 application. Below are notes on everything that I encountered.
Note that we prefer not using the Rails asset pipeline at all and serving all assets through Webpack for the sake of consistency.
Preparations
- Remove version locks in
Gemfile
forwebpacker
- Remove version locks in
package.json
forwebpack
andwebpack-dev-server
- Install by ca...
Speed up RSpec by deferring garbage collection
Update: This trick probably isn't very useful anymore in Ruby 2.x. The Ruby GC has improved a lot over the years.
Joe Van Dyk discovered that running the Ruby garbage collector only every X seconds can speed up your tests. I found that deferring garbage collection would speed up my RSpec examples by about 15%, but it probably depends on the nature of your tests. I also tried applying it to Cucumber f...
Migration from the Asset Pipeline to Webpacker
This is a short overview of things that are required to upgrade a project from the Asset Pipeline to Webpacker. Expect this upgrade to take a few days even the diff is quite small afterwards.
Preparations
1. Find all libraries that are bundled with the asset pipeline. You can check the application.js
and the application.css
for require
and import
statements. The source of a library is most often a gem or a vendor directory.
2. Find an working example for each library in the application and write it down.
3. Find out the ver...
Don't call #node on a Capybara element
Capybara allows you to select DOM elements, e.g. by using field
, find_field(...)
or field_labeled(...)
:
role_select = field_labeled('Role')
In the example above, role_select
is now a Capybara::Driver::Node
. You can call a number of methods on such a node, e. g. in order to click it or to make a selection on its descendants. These methods should be the same regardless of the driver Capybara is using (drivers are e.g. the headless Rack::Test or Selenium).
It i...
Using Apache Benchmark (ab) on sites with authentication
Apache HTTP server benchmarking tool (ab
) is a nice tool to test performance on sites delivered by HTTP. If the site you're about to test is placed behind a login, follow these steps to successfully use ab
on it.
- Open the site to test in the browser of your choice. Do not login yet.
- Use developer tools to show all cookies used by the site. (Chrome: Ctrl+Shift+i, open the 'Resources' tab and click on the site below 'Cookies' on the left. Firefox: Right-click on the site, open 'We...
Use a special version of Chrome for selenium (and another for your everyday work)
Sometimes you need a special version of chrome because it has some features you need for testing, like in this card. You do not need to use that Version apart from tests, because you can tweek selenium to use a special version that you set in your environment:
# features/support/chrome.rb
require "selenium/webdriver"
Capybara.register_driver :chrome320x480 do |app|
if driver_path = ENV["CHROME_SELENIUM_BIN...
Implementing social media "like" buttons: Everything you never wanted to know
So you client has asked you to implement a row of buttons to like the URL on Facebook, Twitter and Google+. Here are some things you should know about this.
0. Security considerations
Each "like" button is implemented by including a Javascript on your site. This means you are running fucking remote code on your page. You are giving Facebook, Twitter and Google+ full permission to e. g. copy user cookies. Check with your client if she is cool with that. Also note that if you're site is suggesting security by operating under HTTPS ...
Running Rails 2 apps with modern MariaDB SQL server
You might have some trouble running a Rails LTS 2 app with MySQL 5.7.
If you don't want to hack Mysql 5.6 into your modern Ubuntu or use the MySQL sandbox, you might want to try MariaDB 10.x.
MariaDB 10.x should work with both old and new Rails applications.
[Switch to MariaDB](https://makandracards.com/makandra/468343-how-...
How to combine greps on log files opened with tail -f
In order to chain greps on log files that are opened via tail -f test.log
you have to use the --line-buffered
command line option for grep
.
Imagine you have the following content in your log file.
# content for log/test.log
test foo
bar
test foo bar baz
bla
Now if you would like to grep for lines that contain foo but not bar, you can use the following command chain:
$ tail -f log/test.log | grep --line-buffered "foo" | grep -v "bar"
Output:
test foo
Disabling Spring when debugging
Spring is a Rails application preloader. When debugging e.g. the rails
gem, you'll be wondering why your raise
, puts
or debugger
debugging statements have no effect. That's because Spring preloads and caches your application once and all consecutive calls to it will not see any changes in your debugged gem.
Howto
Disable spring with export DISABLE_SPRING=1
in your terminal. That will keep Spring at bay in that terminal session.
In Ruby, [you can only write environment variables that subproc...
Jasmine: Reset the location when testing code that uses pushState / replaceState
When testing code that uses pushState / replaceState, your browser will appear to navigate away from http://localhost:3000/specs
(or wherever you run your Jasmine tests). This is inconvenient, since reloading the document will no longer re-run the test suite.
To remedy this, copy the attached file to a place like spec/javascripts/helpers
and #= require
it from your tests. It will store the current location before every test and reset if afterwards (using location.replaceState
).
How to revert features for deployment, merge back, and how to stay sane
Removing features and merging those changes back can be painful. Here is how it worked for me.\
tl;dr: Before merging back: reinstate reverted features in a temporary branch, then merge that branch.
Scenario
Consider your team has been working on several features in a branch, made many changes over time and thus several commits for each feature.\
Now your client wants you to deploy while there are still stories that were rejected previously and can't be deployed.
...
Capybara 2.0 has been released
The gem author Jonas Nicklas highlights in a Google Groups post that the release
- is not backwards compatible to 1.x versions of Capybara
- does not support Ruby 1.8.x anymore
- removes confusion with Rails' built in integration tests (you put capybara rspec integration tests into the
spec/feature/...
folder) and the:type
metadata has been changed from:request
to:feature
- throws exceptions when trying to interact with an element whose identifier is...
Consul: Querying a power that might be nil
Consul 0.6.1+ gives your Power
class a number of static methods that behave neutrally in case Power.current
is nil
. This allows you to create authorization-aware models that still work when there is no user at the end of a web browser, e.g. on the console, during tests or during batch processes.
You will often want to access Power.current
from another model, to e.g. iterate through the list of accessible users:
class UserReport
def data
Power.current.users.c...