STEVE FREEMAN: So this came from a talk I did--
MALE SPEAKER: This looks like revenge.
STEVE FREEMAN: Sorry?
MALE SPEAKER: This looks like revenge.
STEVE FREEMAN: Yes.
Some months ago.
And it's the clash of two metaphors.
One is the thing about test smells, and the other thing is
about listening to your tests.
So synesthesia is when you get a clash of a combination of
different senses.
And it's about, basically, what we've learned over the
years is to listen to the tests.
And when we find difficulties in testing, quite often that's
a hint that something else is going on, and that the real
problem is actually in the code, not in the tests.
This is work I did with my colleague Nat Pryce.
This is a 45 minute talk in five.
Right.
So here's one, don't mock internals.
The point about mocking is you're supposed to be mocking
your external relationships with your peer objects, not
the stuff that goes on inside.
What's internal, what's external is your peers are
objects that are accessible from outside.
Maybe they're passed in, or maybe they're pushed out or
something, but we have some classifications to help think
about this that we've written up on the website.
But that's one of the ways of getting down the dependencies,
and focusing on what really matters in a test. And quite
often, what you find is that one of the problems is that
your object has ended up confused.
A classic one is you've passed in 1,000 parameters to your
constructor, because you think they're all of your
dependencies.
And one of the things that might mean, for example, is
that there's an abstraction somewhere in those
dependencies that's missing, and that you should collapse
that, at which point you have fewer and fewer
parameters to play with.
Or maybe the class should be broken up.
Maybe the reason it's got all those dependencies is it's
doing too much.
And it's a sign of not having good cohesion within the code.
Another one we've scene is where everything turns into a
mock object.
And again, this is because you've kind of lost focus.
What you should be concentrating on is thinking
about the relationship between this object and your
[? neighbor's. ?]
And maybe you're mocking the wrong things.
We don't tend to mock value objects, because they should
be mutable.
You're going off in the wrong direction.
Another thing we've seen is, for example, when you just
have too many expectations in a test, which is rather like
having too many assertions.
And again, it means that the chances are, that you're not
thinking clearly enough about what's really important about
this test, and why you're putting everything here,
rather than breaking it up and expressing your intent.
One that's very common--
we get a lot, a lot of discussion about this--
is where the tests just end up with a shadow copy of what's
in the production code, which is both brittle and pointless.
Some of it is about expecting all the right things, and
stopping the things that don't matter.
But often that's a sign that the code that you're testing
is procedural code hidden inside an object, and that the
right thing to do is to break it up and move some of that
procedural code into another object, where the
responsibility actually belongs.
And when you get the responsibilities and the right
collaborators, quite often the class sort of collapses.
Here's one that there's something raging in the .net
world at the moment-- or the .net test driven world at the
moment-- is there are assorted libraries for doing very
clever things for replacing things with AOP and the like.
An attempt to sort of break the dependencies, but not
break the dependencies in the code.
So from our point of view, what that says is that there's
a dependency there waiting to be broken, and that the static
dependencies that you've got hidden around the back,
[UNINTELLIGIBLE PHRASE], actually still need
to be broken up.
One thing, quickly.
I'm going to get hit, aren't I?
Ready?
I'll just go to this.
Keep knowledge local.
If it's explicit, if you make things explicit, you can name
it, you can talk about it.
What we find is, when you have more names, you have more
demand information, and that it gets better.
And what we tend to find is we ended up passing
behavior, not data.
And that's all on there.
MALE SPEAKER: Yay, well done.