I have a bunch of Rails 3.1 controllers which all have very similar testing requirements. I have extracted out the common code (all Test::Unit style), e.g. the following three tests are completely reusable across all of them:
def create
new_record = { field_to_update => new_value }
create_params = { :commit => "Create", :record => new_record }
post :create, create_params
end
test "should_not_create_without_login" do
assert_no_difference(count_code) do create; end
assert_need_to_log_in
end
test "should_not_create_without_admin_login" do
login_as_non_admin
assert_no_difference(count_code) do create; end
assert_needs_admin_login
end
test "should_create" do
login_as_admin
assert_difference(count_code) do create; end
assert_redirected_to list_path
end
and I intended that it could go in an abstract class which inherits from ActionController::TestCase
. Then each functional test would only need to override the abstract methods, ending up pleasingly small and clean, e.g.
class Admin::AvailabilitiesControllerTest < Admin::StandardControllerTest
tests Admin::AvailabilitiesController
def model ; Availability end
def id_to_change ; availabilities(:maybe).id end
def field_to_update; :value end
def new_value ; 'maybe2' end
def list_path ; admin_availabilities_path end
end
However, when I try this, it appears that the framework tries to run the test methods directly from the abstract class, rather than from the inherited class:
E
===================================================================================================
Error:
test_should_not_create_without_login(Admin::ControllerTestBase):
NoMethodError: undefined method `model' for test_should_not_create_without_login(Admin::ControllerTestBase):Admin::ControllerTestBase
test/lib/admin_controller_test_base.rb:7:in `count_code'
test/lib/admin_controller_test_base.rb:68:in `block in <class:ControllerTestBase>'
===================================================================================================
I've heard that other testing frameworks and gems can provide mechanisms for meta-programming of tests, so maybe I'm going about this in entirely the wrong way. But I've tried several things and looked at RSpec, coulda, shoulda, context, contest ... and I still can't see a way to achieve what I'm after. Any ideas? Thanks!