[rspec-devel] artificial sugar causes cancer

David Chelimsky dchelimsky at gmail.com
Sun Nov 19 08:29:48 EST 2006


If you look at http://rubyforge.org/tracker/index.php?func=detail&aid=6760&group_id=797&atid=3149
 you'll see that Chad (the submitter) found the source of the bug.
Unfortunately, the source of *this* bug is the *solution* to a
*previous bug* in which Rails was replacing RSpec's method missing
with its own.

When we settled on underscores, my one reservation was that we'd keep
running into this particular problem - RSpec's method_missing
conflicting with others.

I have a proposition that preserves the underscore syntax, makes some
examples even more clear, and eliminates this problem once and for

1. Eliminate reliance on method missing to handle expectations by
adding all of the documented should_x_y_z methods directly to Object.
These would all delegate off to Spec::Expectations::Should, ::Not,
::Have, etc, so the design wouldn't change much and Object itself,
though bloated w/ methods, would not be bloated w/ implementation.

This would also give us a single expectations module that we add to
Object, providing several benefits including:
# more clarity in the API
# a place to put meaningful rdoc
# a potential formal plugin point

2. Change should_be to ONLY handle arbitrary predicates (not serve as
an alias for should_equal):

subject.should_be :empty => passes if subject.empty?
subject.should_be :instance_of, SomeClass => passes if
subject.instance_of? SomeClass

In my opinion (feel free to disagree), this actually makes these
examples more readable. Consider these two:

@bdd_framework.should_be_adopted_quickly #current
@bdd_framework.should_be :adopted_quickly #proposed

In my view, these read equally well from a language perspective AND
they make it easier for a developer to mentally separate the
expectation (should_be) from the expected value (adopted_quickly?).

This WOULD require changes to existing specs. I think for those of you
who don't wrap expectation args in parens that a trivial script would
handle this for you. If you do use parens, the script might be more
complex. Perhaps if we *do* choose this direction, one of you would
like to contribute such a script.

I fully recognize that this would cause some pain, but it is my
feeling that not addressing this leaves us in a crippled position in
which we commit to being sidetracked by this issue constantly
returning instead of focusing on enhancing the API.

I also think that this is a better option than any of the following
that also crossed my mind:
* revert to dots
* figure out a sexy way to intercept all attempts to rewrite method
missing and re-inject RSpec's method missing in its place (perhaps
this does sound sexy, but I doth believe that there is a venereal
disease hiding in its midst)
* leave things as they are and continue to add ugly hacks like
NilClass.handle_underscores_for_rspec! (that's MY ugly hack so I get
so call it that)
* hang myself from the nearest bridge

Of course, if you have any solutions to propose, I'm all eyes.



More information about the rspec-devel mailing list