I'm a Java-developer toying with Ruby, and loving it. I have understood that because of Ruby's metaprogramming facilities my unit-tests become much cleaner and I don't need nasty mocking frameworks. I have a class which needs the File
class's services and in my test I don't want to touch my real filesystem. In Java I would use some virtual file system for easier "seams" to pass fake-objects in but in Ruby that's obviously overkill. What I come up seems already really nice compared to the Java-world. In my class under test I have an optional constructor parameter:
def initialize(file_class=File)
When I need to open files within my class, I can then do this:
@file_class.open(filename)
And the call goes to either the real File-class, or in case of my unit-test, it goes to a fake-class which doesn't touch the filesystem. I know there must be a better way to do this with metaprogramming?
Mocha (http://mocha.rubyforge.org/) is a very good mocking library for ruby. Depending on what you're actually wanting to test (i.e. if you want to just fake out the File.new call to avoid the file system dependency or if you want to verify that the correct arguments are passed into File.new) you could do something like this:
require 'mocha'
mock_file_obj = mock("My Mock File") do
stubs(:some_instance_method).returns("foo")
end
File.stubs(:new).with(is_a(String)).returns(mock_file_obj)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With