Stub that returns hash values

Is it possible to create a stub that returns hash values.

For example I would like to convert this:
@siteItem = stub(‘plmSiteItem’, :one => “uno”)

To something like this:
@siteItem = stub(‘plmSiteItem’, {‘one’ => ‘uno’, ‘two’ => ‘dos’} )

So that I can do this:
@siteItem[‘one’] should == ‘uno’
@siteItem[‘two’] should == ‘dos’

Actually I first tried to use method double instead of stub - even
though I still don’t know when each is preferred - but double raised a
missing method error for some reason.

On 20 Oct 2009, at 17:36, Carl G. wrote:

@siteItem[‘two’] should == ‘dos’
Hi Carl

In Ruby, code like my_object[“foo”] is implemented with the method []
eg:

class Thing
def
# …
end
end

So in RSpec you have to stub :[] like this:

describe “stub hash” do
it “quacks like a hash” do
stub_hash = stub(“hash”)
stub_hash.stub(:[]).with(“one”).and_return(“uno”)
stub_hash.stub(:[]).with(“two”).and_return(“dos”)
stub_hash[“one”].should == “uno”
stub_hash[“two”].should == “dos”
end
end

Actually I first tried to use method double instead of stub - even
though I still don’t know when each is preferred - but double raised
a missing method error for some reason.

Can you post your code?

HTH

Ashley


http://www.patchspace.co.uk/
http://www.linkedin.com/in/ashleymoran

Ashley M. wrote:

stub_hash[“one”].should == “uno”
Can you post your code?

HTH

Ashley

Thanks Ashley that works perfect :slight_smile:

wait why do you want to do this?? Just use a regular hash and do
state-based assertions on it. Or determine the role that this
hash-like thing is doing, and use a mock to define a proper interface.
Ashley’s solution works but I am very skeptical that the approach is
a good one. Can you post some code?

Pat

On 21 Oct 2009, at 08:41, Pat M. wrote:

wait why do you want to do this?? Just use a regular hash and do
state-based assertions on it. Or determine the role that this
hash-like thing is doing, and use a mock to define a proper interface.
Ashley’s solution works but I am very skeptical that the approach is
a good one. Can you post some code?

I had wondered the same thing myself… but I figured if my suspicions
were right, a fallout problem would be posted soon enough :slight_smile:

Ashley


http://www.patchspace.co.uk/
http://www.linkedin.com/in/ashleymoran

Hi Carl,

Some thoughts below…

On 21 Oct 2009, at 18:12, Carl G. wrote:

end
@plmItm.sites[‘CH’].name.should == ‘CH-site’
@plmItm.sites[‘CH’].attr[‘NAME’].should == ‘CH-site’
@plmItm.sites[‘NB’].attr[‘NAME’].should == ‘NB-site’
end

In truth, due to my inexperience and confusion, mocks seem to slow
my development more than just creating real objects. But since there
has been so much effort to put these into testing frameworks, I
think it must be important to try and learn when it is appropriate
to use them.

The real point of mock objects (which most people miss) is to give you
a lightweight way to sketch out the behaviour of another object that
the object you’re currently building will collaborate with - without
having to commit to actually building the collaborator yet. This
allows you to play out design ideas about the relationship between the
two objects and get them right before you sit down and write the
implementation of the collaborator.

In this case, it seems you’ve actually got very little behaviour in
the class you’re apparently testing (the ErpItemMasterRec class) -
it’s pretty much just a container for this list of sites, which are
all being set up in the before block. Where will this list of sites
come from when the code runs in production? Would it make more sense
to pass that in to the ErpItemMasterRec constructor?

If you really want to get your head around this stuff, I highly
recommend
http://www.mockobjects.com/book/

(though the examples are in Java)

state-based assertions on it. Or determine the role that this


rspec-users mailing list
[email protected]
http://rubyforge.org/mailman/listinfo/rspec-users

cheers,
Matt

+447974 430184

On 21 Oct 2009, at 19:18, Stephen E. wrote:

into American football, every Michael Bay movie, and Windows Vista.
QED.

To be fair, Carl did say he wanted to “learn when it is appropriate to
use them” as opposed to just using them indiscriminately. And the
answer may be “never”. I suppose it’s quite possible that mocks do
suck, and we just haven’t realised yet. But that’s ok, they suck less
than inspecting instance variables, so I’m happy, at least.

What I would suggest is to not try to learn how to use mocks on
production code*, unless you have pretty thorough means of integration
testing. Incorrect mocking leads to brittle specs* and that leads to
hidden bugs* and thrashing during refactoring*.

In fact, if you don’t use a tool such as Cucumber, I’d recommend
learning that over mocking first. (You don’t need to use Cucumber,
but it’s more suited for high-level descriptions than RSpec.) As
RSpec lets you refactor without risk of breaking units of code,
Cucumber lets you refactor your code and specs across units. That
gives you a metric on how well you’re using mocks - unexpected
Cucumber failures indicate a faulty assumption somewhere. Of course,
that assumes your Cucumber features are solid…

Just my coin of small denomination. Other learning strategies are
available.

Ashley

  • which was my situation


http://www.patchspace.co.uk/
http://www.linkedin.com/in/ashleymoran

On Wed, Oct 21, 2009 at 1:12 PM, Carl G. [email protected] wrote:

In truth, due to my inexperience and confusion, mocks seem to slow my
development more than just creating real objects. But since there has been
so much effort to put these into testing frameworks, I think it must be
important to try and learn when it is appropriate to use them.

That is a fallacious line of reasoning. A lot of effort has also gone
into American football, every Michael Bay movie, and Windows Vista.
QED.

My suggestion on any technology is not to use it in serious practice
unless you have a good idea why you’re using it and what it can
offer you. “I want to play with this and determine what the fuss is”
can be a good reason – provided you have the leisure to do so – but
“All the hotshot programmers say it’s important” is not sufficient and
durable reason in itself. If you don’t know why they say it, find
out. If you’re not sure you grok it, try it both ways, but be
objective about the results. Don’t hold onto a practice blindly.

If your testing so far seems to be going just fine without mocks and
you haven’t hit any snags, great. Maybe you’re not hitting use cases
where they’re really helpful. Maybe you’ve figured out how to address
the same problems in other ways. Heck, maybe everyone else is wrong
about them. (This does in fact happen in software culture, though
it’s easy to overestimate the likelihood.) Do what works, as long as
it works.

When it stops working for you, or you advance enough in your own
proficiency that things you hadn’t thought about before start to seem
questionable or annoying, be prepared to adapt and to try things.
Maybe at that point, mocks will be just what you need.


Have Fun,
Steve E. ([email protected])
ESCAPE POD - The Science Fiction Podcast Magazine
http://www.escapepod.org

Well i just started using RSpec about a week ago and mostly I was just
trying to learn how to use mocks as I could have easily just created the
real object in this case.

Anyway, I had a real object, that needed to contain a hash of a yet to
be created object, which itself contained a hash of attributes.

Here is the code that I used to get the tests to past - but it simulated
a method called “name” in the mock that returned a string value instead
of a hash of string values I desired.

##################
describe ErpItemMasterRec do
context “initializing” do
before(:each) do
@itemNo = ‘004-907019-004’
@plmItm = ErpItemMasterRec.new(@itemNo)
[‘GT’,‘CH’,‘NB’].each do |site|
plmSiteItem = stub(‘plmSiteItem’, :name => “#{site}-site”)
@plmItm.sites[site] = plmSiteItem
end
end

it “should create new instance when receiving a valid item number as a
string” do
@itemNo.should be_instance_of(String)
@plmItm.should be_instance_of(ErpItemMasterRec)
end

it “should store item data from each mfg site that contains the valid
item number” do
@plmItm.sites[‘GT’].name.should == ‘GT-site’
@plmItm.sites[‘CH’].name.should == ‘CH-site’
@plmItm.sites[‘NB’].name.should == ‘NB-site’
end
end
##################

I wanted the last part to be more like:

it “should store item data from each mfg site that contains the valid
item number” do
@plmItm.sites[‘GT’].attr[‘NAME’].should == ‘GT-site’
@plmItm.sites[‘CH’].attr[‘NAME’].should == ‘CH-site’
@plmItm.sites[‘NB’].attr[‘NAME’].should == ‘NB-site’
end

In truth, due to my inexperience and confusion, mocks seem to slow my
development more than just creating real objects. But since there has
been so much effort to put these into testing frameworks, I think it
must be important to try and learn when it is appropriate to use them.

Thanks,
Carl