Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rails: how to test before_save callbacks

Given a typical ActiveRecord model, I often have before_save callbacks that parse input, for instance taking something like time_string from the user and parsing it into a time field.

That setup might look like this:

before_save :parse_time
attr_writer :time_string

private
def parse_time
  time = Chronic.parse(time_string) if time_string
end

I understand that it's considered best practice to make callback methods private. However, if they're private, then you can't call them individually to test them in isolation.

So, for you seasoned Rails testers out there, how do you handle testing this kind of thing?

like image 833
Andrew Avatar asked Dec 19 '12 21:12

Andrew


2 Answers

In Ruby, Private methods are still available via Object#send

You can exploit this for your unit testing like so:

project = Project.new
project.time_string = '2012/11/19 at Noon'
assert_equal(project.send(:parse_time), '2012-11-19 12:00:00')
like image 117
Unixmonkey Avatar answered Oct 16 '22 13:10

Unixmonkey


What I would do is save the state of an new or build instance of your object, save the object and make the assertion or expectation based on the value of the attribute that was changed by before_save

post = Post.new
post.time_string = '2012/11/19'
expected_time = Chronic.parse(post.time_string)
post.save
assert_equal(post.time, expected_time)

That way you are testing the behavior of how the object should act and not necessarily the implementation of the method.

like image 4
Leo Correa Avatar answered Oct 16 '22 14:10

Leo Correa