Author rbcollins
Recipients gregory.p.smith, michael.foord, pitrou, rbcollins
Date 2009-04-05.04:46:34
SpamBayes Score 2.52492e-12
Marked as misclassified No
Message-id <1238906768.2700.373.camel@lifeless-64>
In-reply-to <1238886469.6865.30.camel@fsol>
Content
On Sat, 2009-04-04 at 23:06 +0000, Antoine Pitrou wrote:
> Antoine Pitrou <pitrou@free.fr> added the comment:
> 
> > The main use case for addCleanup is resource allocation in tests. Why
> > does this require clean ups to be executed before tearDown?
> 
> If your cleanup relies on something which has been set up during setUp
> and will be dropped during tearDown (a database connection, a temp dir,
> an ssh session, whatever), then the cleanup must be run before the
> teardown.

I don't think you can sensibly define an ordering between setup/teardown
and cleanups that works for all cases.

Either cleanups happen after teardown, and then you can use them when
allocating things in setup/run/teardown, or they happen before teardown
and you cannot safely use them except in run because things setup by a
child will not have been torn down when cleanups run. [see the two
where-it-breaks sequences below]. The issue is that cleanups are not
connected to the inheritance heirarchy. They are safe and trivial to use
with resources that are not connected to each other *however* they are
defined, but the interaction with things being freed in tearDown cannot
meet all cases unless you have per-class-in the-MRO-queues (which is
overly complex).

I assert that its better to be able to use cleanups in all three test
methods rather than only in run, all other things being equal.

Our experience in bzr (we use this heavily, and migrated to it
incrementally across our 17K fixture suite) is that we rarely need to
use cleanups on dependent resources, and when we need to it has been
very easy to migrate the dependent resource to use cleanups as well.

-Rob

sequence 1: cleanup after teardowns prevents using cleanups on things
freed in teardown:

setup
  self.foo = thing()
run
  self.bar = something(self.foo)
  self.addCleanUp(free, self.bar)
teardown
  unthing(self.foo)
cleanups
  free(self.bar) *boom* self.foo is already gone

sequence 2: cleanup before teardown prevents using cleanups in base
class setup methods

base.setup
  self.foo = thing()
  self.addCleanup(unthing, self.foo)
setup
  super.setup()
  self.bar = something(self.foo)
run
  assertWhatever
cleanups
  unthing(self.foo)
teardown
  free(self.bar) *boom* self.foo is already gone
History
Date User Action Args
2009-04-05 04:46:45rbcollinssetrecipients: + rbcollins, gregory.p.smith, pitrou, michael.foord
2009-04-05 04:46:42rbcollinslinkissue5679 messages
2009-04-05 04:46:35rbcollinscreate