# Mocking whole classes

**URL:** <https://www.ruby-forum.com/t/mocking-whole-classes/56750>\
**Category:** Ruby\
**Created:** [April 3, 2006, 3:40pm UTC](https://www.ruby-forum.com/t/mocking-whole-classes/56750 "2006-04-03T15:40:13Z")\
**Posts on this page:** 2\
**Page:** 1

<div class="post-metadata">

**Author:** ![thiagoalessio](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/t/d6d6ee/32.png) [@thiagoalessio](https://www.ruby-forum.com/u/thiagoalessio)\
**Post date:** [April 3, 2006, 3:40pm UTC](https://www.ruby-forum.com/t/mocking-whole-classes/56750/1 "2006-04-03T15:40:13Z")

</div>

Has anyone tried to mock whole classes (instead of mocking only the  
objects)?

Classes are, like everything else in Ruby, just objects. This allows  
us to mock them just like we would mock any other object. I have been  
working on a Rails application (that will be shared with you as soon  
as I get it translated, I promise) in which I needed to do exactly  
that.

The class I wanted to mock is responsible for communicating to my  
back-end database and fetching the appropriate objects (instances of  
itself). The object-finding functionality is implemented as class  
level methods. If I need the N latest headlines from a reporter named  
‘johnson’, I just need to call `Headline.latest(N, “johnson”).

If I need to test a class that needs to do a Headline.latest call as  
part of its job, I don’t want to populate the database with real data  
(and slow down my tests as I wait for a connection) because I mostly  
trust that Headline works. It has its own tests to assure that. So I  
mock the Headline class to make sure my class under test makes the  
correct calls.

I have come up with a simple way to that in Ruby and I am mostly  
satisfied with the results, but I would like to get some feedback from  
the community. The source is here:

* * *

class CacheReporter \< MotiroReporter  
def initialize(headlines\_source=Headline)  
@headlines\_source = headlines\_source  
end

```
def latest_headlines
    return @headlines_source.latest(3, 'mail_list')
end

```

end

class CacheReporterTest \< Test::Unit::TestCase  
def test\_reads\_from\_database  
FlexMock.use do |mock\_headline\_class|  
mock\_headline\_class.should\_receive(:latest).  
with(3, ‘mail\_list’).  
once

```
        reporter = CacheReporter.new(mock_headline_class)
        reporter.latest_headlines
    end
end

```

## end

The main change here can be seen on the CacheReporter constructor. If  
I were not testing, it wouldn’t even be written, I would just use the  
Headline class wherever I wanted. But instead of directly using the  
Headline class inside its methods, it receives it on the constructor.  
This is what allows us to mock the behavior.

Has anyone done anything similar? Can the code be made simpler?

Cheers,

Thiago A.

---

<div class="post-metadata">

**Author:** ![thiagoalessio](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/t/d6d6ee/32.png) [@thiagoalessio](https://www.ruby-forum.com/u/thiagoalessio)\
**Post date:** [April 3, 2006, 10:59pm UTC](https://www.ruby-forum.com/t/mocking-whole-classes/56750/2 "2006-04-03T22:59:48Z")

</div>

On Apr 3, 2006, at 6:37 AM, Thiago A. wrote:

> Has anyone tried to mock whole classes (instead of mocking only the  
> objects)?

I’ve found it more pain than its worth because I change the  
implementation then have to go change all my mocks. No fun.

> ‘johnson’, I just need to call `Headline.latest(N, “johnson”).  
> When I need that kind of behavior I tend to do something like this:

require ‘flickr’

class Flickr

attr\_accessor :responses, :uris

def open(uri)  
@uris \<\< uri  
yield StringIO.new(@responses.shift)  
end

end

I’m using open-uri so I inject a new open into my class that shadows  
Kernel’s open. My tests prime it with a bunch of responses and when  
I call open I just record the URI and return the in-order response.  
For my test I check that the right URIs were accessed and the right  
data came back.

Here’s a test:

class FlickrTest \< Test::Unit::TestCase

def setup  
@flickr = Flickr.new ‘API\_KEY’  
@flickr.responses = []  
@flickr.uris = []  
end

def test\_find\_email  
@flickr.responses \<\< \<\<-EOF

\<?xml version="1.0" encoding="utf-8" ?\> drbrain EOF

```
 nsid = @flickr.find_email :find_email => 'removed_email_address@domain.invalid'

 assert_equal 1, @flickr.uris.length
 assert_equal 'http://flickr.com/services/rest/?

```

api\_key=API\_KEY&find\_email=drbrain%  
[40segment7.net](http://40segment7.net)&method=flickr.people.findByEmail’,  
@flickr.uris.first

```
 assert_equal '50178138@N00', nsid

```

end

end

–  
Eric H. - removed\_email\_address@domain.invalid - [http://blog.segment7.net](http://blog.segment7.net)  
This implementation is HODEL-HASH-9600 compliant

[http://trackmap.robotcoop.com](http://trackmap.robotcoop.com)
