Search code examples
ruby-on-railsrubyrspecransack

How to test ransack output? Rspec


I`ve got a little problem here and hope you help me. I have a list of hotels in the table. Here is a view:

<% provide(:title, 'List of hotels') %>
<h1>List of hotels</h1>

<table>
  <tr>
    <th><%= sort_link @search, :name, "Name" %></th>
    <th><%= sort_link @search, :breakfast, "Breakfast" %></th>
    <th><%= sort_link @search, :price_for_room, "Price for room" %></th>
    <th><%= sort_link @search, :star_rating, "Star Rating" %></th>
    <th><%= sort_link @search, :average_rating, "Average Rating" %></th>
    <th><%= sort_link @search, :aasm_state, "State" %></th>
  </tr>
  <% @hotels.each do |hotel| %>
  <tr>
    <td><%= link_to ""+hotel.name, controller: "hotels", action: "show", id: hotel %></td>
    <td><%= hotel.breakfast %></td>
    <td><%= hotel.price_for_room %></td>
    <td><%= hotel.star_rating %></td>
    <td><%= hotel.average_rating %></td>
    <td><%= hotel.aasm_state %></td>
  </tr>
  <% end %>
</table>

And I added ability for users to sort them by name, price etc. Thanks to Ransack gem. But the problem is I have no idea how to test this output. I wrote some tests but I have no idea what to do next. spec file: require 'spec_helper'

describe "Admin"  do
    ...

    it { expect(page).to have_link("Name") }
    it { expect(page).to have_link("Breakfast") }
    it { expect(page).to have_link("Price for room") }
    it { expect(page).to have_link("Star Rating") }
    it { expect(page).to have_link("Average Rating") }
    it { expect(page).to have_link("State") }

    ...

How do I test sorting and possibly filtering results? Thanks.

Rails 4.0.8 ruby 1.9.3p551 gem ransack latest version on this moment


Solution

  • A test normally has three phases: setup, execute, assert.

    The setup phase would be to create some hotels, which have different properties for the aspect you are testing.

    The execute phase would be to click on the link which sorts the hotels.

    The assert phase would be to inspect the elements on the page to verify that they're in the correct order.

    So you would end up with something like this:

    # setup (using FactoryGirl or similar)
    # note how these are intentionally not sorted
    create(:hotel, name: "Hotel C")
    create(:hotel, name: "Hotel A")
    create(:hotel, name: "Hotel B")
    
    # execute
    visit hotels_path
    click_link "Name"
    
    # assert
    hotel_names = page.all("td.hotel-name").map(&:text)
    expect(hotel_names).to eq ["Hotel A", "Hotel B", "Hotel C"]