Read more

Controller specs do not persist the Rails session across requests of the same spec

Arne Hartherz
April 10, 2013Software engineer at makandra GmbH

In specs, the session never persists but is always a new object for each request. Data put into the session in a previous request is lost. Here is how to circumvent that.

What's going on?

Illustration web development

Do you need DevOps-experts?

Your development team has a full backlog? No time for infrastructure architecture? Our DevOps team is ready to support you!

  • We build reliable cloud solutions with Infrastructure as code
  • We are experts in security, Linux and databases
  • We support your dev team to perform
Read more Show archive.org snapshot

You are making ActionController::TestRequests in your specs, and their #initialize method Show archive.org snapshot does this:

self.session = TestSession.new

This means that each time you say something like "get :index", the session in your controller will just be a new one, and you won't see anything you put into your session in a previous request.

Working around the issue

You can avoid that behavior by stubbing the controller's session and querying that stub:

persisted_session = ActionController::TestSession.new
controller.stub :session => persisted_session
# do things
persisted_session[:something].should ...

Apply this workaround only when you need it. Stubbing controller.session is not entirely the same, but good enough in most cases.

Example

If you, for example, had code that increments a "page_views" entry for every request you make, you could then test it like this:

get :index
persisted_session[:page_views].should == 1 # session[:page_views] is 1, so that would still work

get :index
persisted_session[:page_views].should == 2 # session[:page_views] would be 1, even though it works in the real world
Posted by Arne Hartherz to makandra dev (2013-04-10 15:08)