00:00:19.800
hi everyone
00:00:21.550
my name is John I want to make one thing
00:00:23.919
very clear for certain members in the
00:00:25.539
audience I am NOT in fact Australian I'm
00:00:31.659
actually from a small cold - island
00:00:34.180
nation off the coast of Europe called
00:00:35.949
Britain I now live in Sydney which is a
00:00:40.780
very large country in fact you can see
00:00:42.579
Britain is percentage-wise
00:00:44.769
a very small part of the sort of size of
00:00:47.140
Australia and the reason why I'm here
00:00:50.260
talking to you today is I have the
00:00:52.539
honour of being one of the core team
00:00:55.420
members for r-spec so first off hands up
00:01:00.940
if you've used have you've heard of
00:01:02.559
r-spec that's a good percentage concept
00:01:06.850
if you use r-spec okay cable going well
00:01:12.000
hands up who's heard of version 3 still
00:01:17.140
a good number good the marketing is
00:01:18.880
working hands up if you've used version
00:01:22.420
3 that is actually a good percentage of
00:01:26.470
you I'm glad so why is this important
00:01:31.720
why is aspect 3 important in particular
00:01:35.190
so have you all heard of semantic
00:01:38.020
versioning hands up again
00:01:39.870
good so we all know that in patch
00:01:42.700
releases we should only be able fixing
00:01:44.410
bugs in minor releases we can add new
00:01:46.810
features but we must not make any
00:01:48.430
breaking changes and we know that in
00:01:50.830
major versions we get to make those
00:01:52.930
breaking changes so just just quickly
00:01:57.580
going over the history of aspect because
00:01:59.920
it is actually quite an old and
00:02:01.420
venerable project at this stage released
00:02:05.500
in 2005 was aspect 0 versions so these
00:02:09.460
are the very first sort of minor
00:02:11.230
versions that were
00:02:12.430
quite frankly a little bit of a hack
00:02:15.150
this is way before my time on the
00:02:17.829
project I'm way before most people who
00:02:20.019
currently maintain its time on the
00:02:21.370
project that's been through several sets
00:02:22.840
of maintained errs and it wasn't until
00:02:26.019
2007 a couple of years later that aspect
00:02:29.799
one was released and it became stable
00:02:32.230
you could use it people actually tested
00:02:35.170
products and shipped cool stuff and it
00:02:39.459
took another three years until a spec 2
00:02:42.370
was released which is the version that
00:02:44.019
most of you are probably most familiar
00:02:46.810
with at this point in time when it was
00:02:49.359
released we actually reached about 85
00:02:52.299
different contributors to a spec at this
00:02:57.040
point it had most of the features we all
00:02:59.319
know and love and it was during this
00:03:02.409
time of course that rails 3 came out and
00:03:04.209
our spec is sort of grown in usage as
00:03:07.000
rails has grown in usage so if we fast
00:03:10.870
forward to 2014 now we actually have at
00:03:15.129
this point a couple of hundred
00:03:16.660
contributors have committed stuff to a
00:03:18.760
spec and we finally released version 3
00:03:21.699
which is actually been the product of
00:03:23.560
more than a year's work so why should
00:03:29.199
you care the issues among you will have
00:03:32.919
noticed of course that this talk title
00:03:34.540
contains a pun we expect you to care and
00:03:37.359
even more astute if you will notice that
00:03:39.340
I slipped up and said should you care
00:03:42.150
I'm sorry there was no happy accident it
00:03:45.459
was in fact the product of engineering
00:03:47.500
for this talk yeah it's because it's the
00:03:50.470
most recent most visible change that
00:03:52.780
we've sort of made especially around 3
00:03:57.150
it's not the only change that's in
00:04:00.220
theory but it's the one that most people
00:04:01.720
are now actually noticing the expect
00:04:04.690
syntax if the if this was a blog post
00:04:08.139
the TLDR
00:04:09.940
of this talk would be the releasing
00:04:12.909
version 3 is about cleaning house about
00:04:14.799
removing deprecated things and making
00:04:16.900
painful recommendations the expect
00:04:20.109
syntax is that one of those painful
00:04:21.789
recommendations a year or two ago I
00:04:25.090
would have been happy
00:04:26.710
should syntax I would have been more
00:04:30.820
than happy to write should you care for
00:04:33.280
this talk just a quick show of hands who
00:04:35.950
actually uses the expect syntax and who
00:04:39.340
uses the syntax hi Konstantin
00:04:48.160
so we all know what the expects intake
00:04:50.630
looks like so you generally expect
00:04:52.640
something to match some matcher and we
00:04:56.000
all know that the should syntax is it's
00:04:58.220
a slightly shorter and we expect some
00:05:00.560
object to should match the expect syntax
00:05:06.110
is not actually that new a lot of people
00:05:09.320
refer to it as the new expect syntax it
00:05:11.600
was actually released in July 2012 in
00:05:14.210
aspect 2.11 somehow that kind of escape
00:05:18.530
to other people's notice and even before
00:05:20.810
that you could use it to write block
00:05:22.790
expectations in fact you had to if you
00:05:25.370
wanted to test that you were raising
00:05:26.510
errors currently but in three-point mile
00:05:31.460
x as we've 33.0 series it becomes the
00:05:35.930
recommend a recommended syntax it now
00:05:39.380
has full equivalents with the should
00:05:41.420
syntax something that didn't have prior
00:05:43.610
to 3.0 and this talk is about why you
00:05:48.470
should care about that so just quickly
00:05:51.130
object or should become suspect object
00:05:53.630
to matter object or should receive
00:05:55.220
becomes expect object to receive object
00:05:58.940
or stub becomes allow to receive should
00:06:03.140
receive some vowels we initially weren't
00:06:04.850
because wasn't going to replace this
00:06:06.260
syntax but we have people complain so we
00:06:08.570
have given you receive messages and
00:06:10.960
we've had a lot of people complaining
00:06:13.310
about should being deprecated a fun fact
00:06:18.170
about should being deprecated it's not
00:06:24.460
what's happened with aspect three is
00:06:27.200
that we've deprecated the usages should
00:06:29.810
automatically we are trying to get away
00:06:33.500
from you just assuming everything will
00:06:35.720
always work it the big scary warning
00:06:39.440
message it creates forces people to
00:06:41.600
think it's deprecated I should actually
00:06:43.190
apologize for that
00:06:44.270
that's something we slipped up on we
00:06:45.590
didn't think that people would you know
00:06:47.120
kind of this you people read the message
00:06:48.680
but not just see should deprecated and
00:06:51.160
it's caused a lot of people to switch to
00:06:53.330
expect which we like but what actually
00:06:55.640
made us change this recommendation
00:06:59.220
the answer to that is monkey-patching
00:07:02.340
most rubyists are familiar with this
00:07:04.720
expression we open a classroom module
00:07:07.300
and we insert some code this syntax is
00:07:10.740
monkey-patching it's putting should onto
00:07:14.620
every object in the system and it can go
00:07:17.080
horribly wrong the original reason for
00:07:19.509
writing the expect syntax well as cases
00:07:22.690
like this which is a proxy object when
00:07:27.789
the expectant that's was introduced this
00:07:29.860
actually would have tried to be tested
00:07:32.020
like this and it wouldn't work because
00:07:36.460
the way that absurd is monkey patched
00:07:40.479
into kernel overrides on the object and
00:07:43.530
be fuzzy tries to match against the
00:07:46.000
fuzzy question mark turns out they go
00:07:49.060
false back to the method missing and you
00:07:50.620
get a error about the method not
00:07:51.940
actually existing on the object your
00:07:53.770
proxying to is supposed to on the
00:07:55.090
property itself that bug was fixed when
00:07:57.580
expects was introduced in preparation
00:08:00.490
for this talk I had to make sure that
00:08:01.900
this was fixed and I actually found that
00:08:04.240
3.0 has a subtle bug whereby we are
00:08:06.699
deprecating parts of the predicate
00:08:10.930
matches with private methods this
00:08:12.789
actually trips up to pry the method
00:08:14.650
warning so I'm going to have to fix that
00:08:16.150
later in the conference and there was
00:08:19.599
also rather nasty bugs surrounding
00:08:21.550
active record where proxy objects for
00:08:24.699
collections would actually remove should
00:08:26.320
and people would complain that I should
00:08:29.259
it's not defined on my method anymore
00:08:30.729
and you're like well why is that so
00:08:33.810
realistically the reason why we're
00:08:35.950
deprecating the usage of automatic
00:08:38.200
should is to get rid of this chap the
00:08:40.180
evil monkey in the closet our drive as I
00:08:44.980
said we want to remove as much monkey
00:08:47.320
patching from our spec as possible and
00:08:50.610
that nesset ated a change to our syntax
00:08:53.380
so that we can provide the right
00:08:54.670
aesthetics so that we can banish the
00:08:56.920
evil monkey from our closet and that's
00:08:59.350
what the deprecation measure is telling
00:09:00.550
you we're telling you that we want you
00:09:01.959
to tell us when you want us to monkey
00:09:03.880
badge we want that to eventually be the
00:09:06.100
default it's not where we are now at the
00:09:10.390
moment monkey patching is still
00:09:11.620
automatically
00:09:12.400
included but we want it not to be we
00:09:17.440
want to extract an isolate our code from
00:09:20.410
your code to help you test your code and
00:09:23.160
this has actually led to one of the
00:09:25.270
other new features in aspect so
00:09:27.400
previously of course the you no DSL look
00:09:30.910
starts with a describe and you have
00:09:32.170
context and that's actually monkey
00:09:33.820
patched into main it's only monkey
00:09:36.250
patched into main it's not exposed into
00:09:38.530
our elf we go to a lot of effort to try
00:09:40.240
and reduce that surface API but in
00:09:44.020
aspect three you can now do this which
00:09:45.820
is simple for later change in the top
00:09:48.340
left hand corner you can now actually
00:09:50.290
have a completely non monkey patch mode
00:09:53.250
you can enable that with very nice
00:09:56.230
config disable monkey but it's not the
00:09:59.380
default because of backwards
00:10:00.760
compatibility so for the moment zero
00:10:03.400
monkey patching mode is an opt-in but
00:10:05.650
we'd really like it to be the default
00:10:09.700
eventually so part of this philosophy is
00:10:13.720
just trying to keep our stuff out of
00:10:16.180
your way one of the net other biggest
00:10:19.510
changes not spit three surrounds the
00:10:20.950
formatters they said these have probably
00:10:24.130
the biggest extensions for a spec this
00:10:27.970
is what most people will actually get
00:10:29.470
just so and they extend from everything
00:10:32.680
from custom formatted for CI to Nang cap
00:10:40.390
so hands up if you over has used a
00:10:42.640
custom formatter it's anyone written a
00:10:46.180
custom formatter here that's good so the
00:10:50.529
new aspect 3 puts a lot of modulation
00:10:52.690
into the format's of stuffs we're
00:10:53.980
actually now using notification objects
00:10:56.440
to send to for mattes which we weren't
00:10:57.820
before
00:10:58.329
because we'd like you to be able to ride
00:10:59.800
for matters like this then there's no
00:11:02.140
inheritance here we're not including any
00:11:03.820
modules this is the purest sort of pyro
00:11:07.300
formatting you can write all you've got
00:11:10.240
to do is tell aspect what notifications
00:11:12.490
you expect and then you receive
00:11:14.230
notification value objects all of this
00:11:16.930
is documented in our Doc's of course but
00:11:19.959
I just wanted to sort of touch on that
00:11:21.250
because it leads me into this was the
00:11:22.510
philosophy of where we're actually
00:11:24.220
trying to take a speck it's we're trying
00:11:29.500
to sort of look at other thing isolate
00:11:31.209
all of our code from York over trying to
00:11:33.100
you know drive down the various API so
00:11:36.820
that they're easier to use and we're
00:11:38.079
trying to help you write better tests
00:11:41.350
which leads me to my next so that this
00:11:43.420
is one of the contentious points in as
00:11:45.579
well does anyone use its so it's in
00:11:51.790
aspect three he's been extracted into a
00:11:53.410
separate gem when I say it's I don't
00:11:56.829
mean the one line syntax I don't mean it
00:11:59.769
should and incidentally this actually
00:12:02.320
isn't monkey patching because we own the
00:12:04.029
context of a spec we weren't even going
00:12:06.430
to replace this with an expect syntax
00:12:08.140
equivalent until everyone complained so
00:12:10.630
we made it expected I guess a bit of
00:12:13.990
feedback from everyone helps make
00:12:15.190
everyone's life easier but no when I say
00:12:17.230
it's I'm talking about the value test
00:12:19.899
they've always been a bit of a personal
00:12:21.880
style some people like them some people
00:12:23.230
don't
00:12:24.269
we've taken the decision to extract into
00:12:27.640
a gem because we don't think it fits
00:12:29.050
with the core philosophy of aspect as a
00:12:31.050
behavior driven tool it's they tend to
00:12:37.269
lie to you in how they end up documented
00:12:41.380
himself so with a quick example if you
00:12:45.610
had were to have an object and you were
00:12:47.560
to implement his name method like this
00:12:50.730
got Bob Jones and the test here is
00:12:52.529
saying it's name is expected to equal
00:12:54.870
Bob Jones this test the implementation
00:12:58.110
is fine the problem is with the output
00:13:03.829
the output of this dot because it's on
00:13:06.029
it because it's literally taking your
00:13:08.040
code and printing it is alive that's not
00:13:12.870
what the name method actually does it's
00:13:16.829
not we're always going to return Bob
00:13:18.480
Jones with a little bit of refactoring
00:13:23.810
this test becomes something more like
00:13:26.010
this all I've done is changed the doc
00:13:28.199
string the implementation of the test is
00:13:30.269
roughly the same but now when we run
00:13:33.990
that documentation output we get
00:13:37.560
compiled in first and last so now the
00:13:40.170
test is expressing the behavior of the
00:13:44.160
test and not what the actual value is
00:13:46.620
and that's why we've chosen to recommend
00:13:49.560
that aspect it's method be not used
00:13:55.079
that's why it extraction is there Jen
00:13:56.550
you're still welcome to use us but it's
00:13:57.899
it's still maintained by the core team
00:13:59.279
but we don't want it to be by default so
00:14:03.300
now that we're talking about behavior
00:14:05.010
that segways been nicely into talking
00:14:07.740
about verified doubles this is an all
00:14:13.050
new feature for r-spec 3 it was actually
00:14:15.660
mostly ported from xavier Shay's aspect
00:14:17.970
fire xavier Shady's now on the core team
00:14:20.010
to help us maintain it it's awesome and
00:14:22.589
I'm super excited about these because
00:14:24.899
they're essentially contract tests for
00:14:27.000
free so just quickly if you were to
00:14:30.389
write a instance double this is how you
00:14:32.610
invoke a verified double this is no
00:14:36.899
different to writing double named values
00:14:40.829
the same as you were done in aspect two
00:14:43.100
because in isolation it doesn't do
00:14:45.329
anything it's like okay sure
00:14:47.100
you've expressed yourself but when you
00:14:49.230
load in a definition for that object
00:14:53.329
r-spec and will now say all hang on a
00:14:55.589
minutes we know about this object you've
00:14:58.319
just stubbed out this method but it
00:15:01.079
doesn't exist
00:15:03.389
the double will verify that you have
00:15:05.189
actually met the method contract so when
00:15:10.319
we implement that it will now pass the
00:15:14.189
only caveat here is that it doesn't
00:15:16.439
actually verify the output against the
00:15:20.399
method Albert
00:15:21.149
so because Ruby's dynamic and it's not
00:15:23.309
going to check that a string if you've
00:15:25.319
stubbed it to be a string and it
00:15:27.089
actually returns true it's not going to
00:15:28.319
go and invoke the method for you because
00:15:29.790
that's would be expensive and that would
00:15:32.009
defeat sort of speed part of using marks
00:15:34.139
in the first place so it's not quite
00:15:35.910
true contract testing because it doesn't
00:15:37.709
deal with the sort of type signature but
00:15:40.439
it does do a pretty good job of making
00:15:41.819
sure you haven't type out your method
00:15:43.230
names a common use case is to sort of
00:15:45.899
you know have your mocs in your unit
00:15:47.519
tests and then when you load the whole
00:15:49.019
suite for integration all of your unit
00:15:51.329
tests will then automatically check that
00:15:53.369
the methods exist on the real objects
00:15:55.549
and we can do this with already existing
00:15:59.309
partial objects too this will actually
00:16:01.470
pass because even though object doesn't
00:16:03.209
receive other this is an opt-in feature
00:16:05.149
so that passes straight off the bat but
00:16:08.249
if I tell it to verify partial doubles
00:16:10.679
that's what we call stubbing on an
00:16:13.410
existing object it will again fail
00:16:16.199
correctly so that's all about verifying
00:16:20.759
your behavior and yeah that's all about
00:16:27.119
verifying your behavior now most of the
00:16:29.790
other things in Aspen 3 are really about
00:16:31.399
cleaning house as I said there are four
00:16:36.749
years of development that's happened on
00:16:38.309
- and in for most of those four years
00:16:39.779
we've been carrying around backwards
00:16:41.339
compatibility for a spec one so in a
00:16:45.239
spec three we are removing methods like
00:16:47.189
stub bang it's always been the same as
00:16:49.799
stub it's never done anything
00:16:51.389
differently but we're gonna remove it
00:16:54.350
similarly because we want to reduce
00:16:56.189
confusion we're removing both stub and
00:16:59.189
mock as ways of creating doubles if
00:17:03.179
they've always been a test double for
00:17:05.069
some reason we had three methods for the
00:17:07.019
same thing so we just moved to them
00:17:09.779
we've made sure we try to sort of reduce
00:17:12.270
some confusion so we now disallow
00:17:13.949
statements like this
00:17:15.990
which you used to be able to specify
00:17:17.939
that um you could receive a message at
00:17:20.159
least zero times which is kind of a
00:17:22.770
confusing English statement so we're
00:17:24.990
trying to Eve remove that this one is
00:17:28.140
slightly contentious you can no longer
00:17:29.549
specify that you can't raise a specific
00:17:32.429
error sorry the inverse so you can
00:17:35.820
specify that you raise a certificate but
00:17:37.590
you can't specify you don't raise a
00:17:38.970
specific error it's so confusing I'm
00:17:41.070
leaving it in my tongue-tied actually
00:17:42.510
trying to say it if you want to sort of
00:17:44.429
specify that something doesn't raise a
00:17:45.600
specific error you're better off
00:17:46.710
rescuing it yourself and expecting the
00:17:48.809
bright thing has been raised but this
00:17:50.700
wallows a lot of bugs cuz it's like well
00:17:53.850
okay my code blown up it's blown up with
00:17:55.890
an argument error but I was expecting a
00:17:58.350
record invalid error and oh well I guess
00:18:01.350
that failures not important so we've
00:18:04.140
removed that we've removed some of the
00:18:06.990
older aspect mount sort of integration
00:18:09.419
magic sounds like auto test support
00:18:10.789
because well most people either use God
00:18:14.399
or something else or they don't and it's
00:18:17.130
kind of something that shouldn't live
00:18:18.480
within the core gem if there's any
00:18:21.270
textmate fans and the audience I'm
00:18:22.620
afraid we've removed the textmate
00:18:23.820
formatter I'm not sure there's anyone
00:18:26.070
left who use this text me any one one
00:18:29.100
person
00:18:31.510
but one of the hell they said this is
00:18:35.260
another contentious one we've so as
00:18:37.990
everyone can everyone read that that's a
00:18:40.810
before all hook accessing a letter
00:18:42.370
that's now disabled because that is
00:18:45.520
sharing state amongst instances of your
00:18:47.410
tests and we disallowed that to try and
00:18:50.940
increase the isolation of tests so now
00:18:54.460
if you try to do that you'll get a nasty
00:18:57.550
error message please read it is
00:18:59.530
explained so how to fix it and duplicate
00:19:05.740
slide we've similarly we've we've
00:19:08.590
disallowed access to double the two
00:19:11.280
partial doubles inside mocks sorry
00:19:15.070
inside before all hooks the reason for
00:19:17.260
this is again trying to prevent you from
00:19:18.850
sharing states between tests if you need
00:19:22.420
to sort of do that then you we give you
00:19:27.760
a temporary scope if you need to do some
00:19:29.500
mocking and stubbing so you can do some
00:19:30.820
one-time setup before a sweet but we
00:19:32.680
don't want those doubles leaking between
00:19:34.900
examples so if anyone uses those
00:19:38.590
features I'm sorry but it's for your own
00:19:40.120
good
00:19:42.330
so all of these sort of different things
00:19:45.100
that we've changed and you know we made
00:19:46.720
it a pain for you and I'm sorry
00:19:48.730
so let's talk about upgrading from two
00:19:52.630
to three so a lot of you said you were
00:19:55.480
using three how many of you still have
00:19:56.710
projects that are running too and how
00:20:00.880
many of you have had problems upgrading
00:20:02.410
those sweets sounds good so we went
00:20:07.240
through the whole process of inventing
00:20:08.620
$2.99 and then three to nine is
00:20:12.430
officially the last release in the two
00:20:13.840
series which is designed so you upgrade
00:20:16.480
to $2.99
00:20:17.290
you run that your suite will still run
00:20:20.140
is still fully compatible of 214 but
00:20:22.300
you'll get a ton of warnings telling you
00:20:23.530
what's changed you fix those warnings
00:20:25.480
then you can do upgrade to three and
00:20:27.460
it'll run a green now that sounds like a
00:20:30.550
pain for some people so one marvelous
00:20:34.000
person who is now on the aspect core
00:20:35.860
team invented transparent who's heard of
00:20:38.890
trance back right all of the rest of you
00:20:42.330
go to github when you've got some stable
00:20:44.680
Wi-Fi
00:20:45.400
and look up transparent transparent
00:20:46.420
automatic dynamic analysis tool it runs
00:20:49.300
with your specs and converts all your
00:20:51.250
specs to aspect 3 compatible you have to
00:20:54.550
be on $2.99 for it to work properly
00:20:56.260
because it will only translate stuff
00:20:59.170
that works so if you're running 214 into
00:21:01.420
Transpac it will just update to the
00:21:02.800
latest but if you're running $2.99 it'll
00:21:05.860
convert everything into announced by
00:21:06.970
three compatible so if we look at a
00:21:08.890
quick example this is a random speck on
00:21:12.430
file I made up we've got a couple of
00:21:14.770
things that disallowed we've got the
00:21:16.030
it's we've got we're using the
00:21:18.010
syntax we've got an equals equals
00:21:19.600
operator that's no longer allowed and a
00:21:22.600
few other bits and pieces
00:21:23.620
if we run Transpac you get an output
00:21:26.260
similar to this which basically run a
00:21:29.140
spec and it's checked a little green and
00:21:32.110
then it's gone okay so what if you
00:21:33.340
actually tried to test and then you get
00:21:36.550
a list of conversions and it's so it
00:21:38.620
returns our previous example into this
00:21:42.690
which is the only oddity here is what
00:21:45.400
it's done to a spec hits you'll notice
00:21:48.190
it's rather than including the gem it's
00:21:50.440
describing length and actually going to
00:21:52.330
the effort the fact that it can figure
00:21:53.650
that out is magic it's awesome it's a
00:21:57.880
little bit strange but it's awesome so
00:22:00.850
if you take away one thing from this
00:22:02.470
talk is that Transpac is awesome and you
00:22:03.940
should all use it so hopefully that's
00:22:06.940
outlined and clarified some of the
00:22:08.740
decisions we've made behind that things
00:22:10.990
nice but three I'm really keen to avoid
00:22:14.110
cargo cult in our testing culture I
00:22:16.390
think it's what leads to us to making
00:22:18.430
brittle tests and trying to avoid then
00:22:22.720
needing to you know self aggrandizing
00:22:24.040
blog post about TDD is dead I think that
00:22:26.200
something is to do with lack of
00:22:27.940
understanding of what perhaps we're
00:22:29.650
always doing so I really encourage you
00:22:32.140
to sort of research decisions in testing
00:22:34.540
and not just cargo cult and I just want
00:22:37.810
to say thank you to all for listening
00:22:39.840
thank you to every single one of these
00:22:41.890
people for contributing to our spec and
00:22:44.800
I hope you've enjoyed
00:22:52.789
I'm more of a mini test person but I
00:22:55.740
just wanted to say that I respect your
00:22:57.720
work I have to give Aaron credit for the
00:23:05.429
last-minute puns on the before and after
00:23:07.649
talk slides they were initially
00:23:09.120
introduction and concluding until a
00:23:11.370
spare till he made the pun I just want
00:23:14.159
to thank you actually pretty amazing to
00:23:21.049
see how some it was from $2.99 up to
00:23:24.090
three I'm glad