Sunday, May 3, 2009

Sorting by Date (Non-Default Order)

‹prev | My Chain | next›

Note: date sorting as described here only works when using ISO 8601 date format.

I have sorting and pagination playing nicely together at this point:



Up next is sorting by date. It is treated differently than other sorting because the default sort order is descending rather than ascending. By default, the newest recipes should be shown (descending order). All other sorting should be in alphabetically ascending order ("a" comes before "b", "b" comes before "c", etc.).

The "Then" step describing the first page of descending date results will include "2008-06-17" and "2008-06-16" (day 50 and 49, as measured from day 1, "2008-04-29"). Thanks to Cucumber / Webrat, this is easy to describe as:
Then /^the results should be ordered by date in descending order$/ do
response.should have_selector("tr:nth-child(2) .date",
:content => "2008-06-17")
response.should have_selector("tr:nth-child(3) .date",
:content => "2008-06-16")
end
As expected, this step fails, so it is time to wade into the code to get it working as desired.

In order to instruct the sort_link helper to reverse by default, I add an optional 4th parameter:
  it "should link to descending sort if instructed to reverse" do
sort_link("Foo",
"sort_foo",
@current_results,
:query => "query",
:reverse => true).
should have_selector("a",
:href => "/recipes/search?q=query&sort=sort_foo&order=desc")
end
I also make the query part of the optional argument hash (since it is included, albeit stemmed, in the couchdb-lucene results). The implementation that makes this and other examples work:
    def sort_link(text, sort_field, results, options = { })
id = "sort-by-#{text.downcase}"

query = options[:query] || results['query']

# Current state of sort on the requested field
sort_field_current =
results["sort_order"] &&
results["sort_order"].detect { |sort_options|
sort_options["field"] == sort_field
}

if sort_field_current
order = sort_field_current["reverse"] ? "" : "&order=desc"
elsif options[:reverse]
order = "&order=desc"
end

url = "/recipes/search?q=#{query}&sort=#{sort_field}#{order}"
%Q|<a href="#{url}" id="#{id}">#{text}</a>|
end
With descending by default date sorting working properly, I can work my way back out to the feature description, which is now passing. Implementing a similar step for clicking the "Date" column header twice gets me down to the last 4 steps in the search scenario:



Almost there.

No comments:

Post a Comment