[rspec-users] [Cucumber, Rails] Testing arbitrary post action parameters

James Byrne lists at ruby-forum.com
Sat Jan 17 23:20:25 EST 2009


Matt Wynne wrote:

> If you think you know the URL you want, why not try hard-coding it for
> a while in the step until you get the desired effect on the
> controller? Then you can add a spec for your routing which proves that
> the call to users_url() with the parameters you're trying gives you
> the same hard-coded value. Then you'll have discovered for yourself
> exactly the right parameters to use to send the right PUT request all
> the way to the controller.


I took your advice and, after a very long session of trial and error 
(mostly error), I derived this formulation:

  post account_url, { :user=> { "administrator" => true }, :action => 
"update", :commit => "Update", :_method => "put" }

Now, this has the following effect in the tests:

> Processing UsersController#update (for 127.0.0.1 at 2009-01-17 22:58:54) 
> [PUT]
> Parameters: {"commit"=>"Update", "_method"=>"put", "action"=>"update", 
> "controller"=>"users", "user"=>{"administrator"=>"true"}}

That seems to be what I was trying to pass.

The stuff that follows next is authlogic updating the last_request_at 
field in the users table:

> User Load (0.0ms)   SELECT * FROM "users" WHERE ("users"."id" = 3) LIMIT 1
> User Update (0.0ms)   UPDATE "users" SET "updated_at" = '2009-01-18 03:58:54',
> "last_request_at" = '2009-01-17 22:58:54' WHERE "id" = 3
> User Exists (0.0ms)   SELECT "users".id FROM "users" WHERE (
> "users"."perishable_token" = 'TuHra3ozvoDVJLEtFQIX' AND "users".id <> 3)
> LIMIT 1
> User Exists (0.0ms)   SELECT "users".id FROM "users" WHERE (
> "users"."username" = 'myuser' AND "users".id <> 3) LIMIT 1
> User Exists (0.0ms)   SELECT "users".id FROM "users" WHERE (
> "users"."email" = 'myuser at example.com' AND "users".id <> 3) LIMIT 1

This is the magic SQL statement I was trying to produce:

> User Update (0.0ms)   UPDATE "users" SET "perishable_token" = 
> 'TuHra3ozvoDVJLEtFQIX', "administrator" = 't' WHERE "id" = 3

This next bit seems to be right too:

> Redirected to http://www.example.com/account
Completed in 0ms (DB: 0) | 302 Found [http://www.example.com/account]
  User Load (0.0ms)   SELECT * FROM "users" WHERE ("users"."username" = 
'myuser'
) LIMIT 1

AND... The next feature step fails as desired:


When /user named "(.*)" should not be an administrator/ do |name|
  my_user = User.find_by_username!(name)
  fail if my_user.administrator
end

    Then the user named "myuser" should not be an administrator      # 
features/
app/models/users/step_definitions/user_steps.rb:41
       (RuntimeError)
      ./features/app/models/users/step_definitions/user_steps.rb:43:in 
`Then /us
er named "(.*)" should not be an administrator/'
      features/app/models/users/user.feature:45:in `Then the user named 
"myuser"
 should not be an administrator'

So, I now have my failing test and can write (uncomment) the code needed 
to protect against it.

Thanks for the help.  It was extremely valuable in leading me to the 
right answer.
-- 
Posted via http://www.ruby-forum.com/.


More information about the rspec-users mailing list