Getting tired of seeing your Test::Class driver classes look like this?
#!/usr/bin/perl -wT use lib 't/tests', 't/lib'; use Test::Class; use Tests::My::This; use Tests::My::That; use Tests::My::Big::Fat::Cheese; # # ... 26 dull, boring lines go by, never to be remembered # use Tests::Did::I::Remember::To::Include::All::Of::My::Test::Classes; Test::Class->runtests;
Well, Adrian has released Test::Class 0.13, which now allows you to replace that with this:
use Test::Class::Load qw(t/tests t/lib); Test::Class->runtests;
No more remembering to keep your driver script in synch with your test classes.
I usually use one driver script per test class. What are the benefits of glomming them all together, besides having fewer files?
Re:Never Been a Problem for Me
Ovid on 2006-09-30T20:25:34
You can still do one driver script per class, but there are two benefits to Test::Class::Load. When I'm writing a Test::Class program, I run those tests by typing
,t in vim. However, if I do that, it's easy to forget to write a helper script. A developer could easily check in test code which never gets run. The second benefit accrues as you're writing larger test suites. Let's say you've written thirty test classes. Let's say that those thirty classes load an average of twenty modules each (this is really easy to do, even if the classes you're testing only appear to use a couple of other modules). If you've written thirty corresponding driver scripts (and the thought of that duplication bothers me), then when you run prove over them, you've loaded up perl thirty times and done six hundred module loads! But it can easily get worse. Establishing database connections and similar tasks can be expensive, so often you only want this done once, but with thirty driver scripts, you generally have to do this multiple times.
With Test::Class and one driver script, you generally load perl once and most modules once. Expensive behaviors can also be minimized. As your system grows, Test::Class can speed up large test suites dramatically. In fact, solving this problem for a company is part of why Adrian wrote Test::Class in the first place.
Re:Never Been a Problem for Me
chromatic on 2006-09-30T22:45:19
Establishing database connections and similar tasks can be expensive, so often you only want this done once, but with thirty driver scripts, you generally have to do this multiple times.I can understand that, but it's never been an issue for me. The largest test suite I have still takes only three or four minutes to run, and I like having the process boundary between separate tests.
Maybe it's my inexperience with this approach, but I distrust the lack of separation between units.
Re:Never Been a Problem for Me
Adrian on 2006-10-02T13:26:49
I can understand that, but it's never been an issue for me. The largest test suite I have still takes only three or four minutes to runWhile three or four minutes isn't too bad (and I've seen Perl tests suites that take more than 90m to complete) my general feeling towards test suites is the shorter time they run - the more often I will run them. The quicker I can make that feedback loop the happier I am.
Maybe it's my inexperience with this approach, but I distrust the lack of separation between units.Why (he asks curiously)?
Re:Never Been a Problem for Me
Ovid on 2006-10-02T13:35:21
Actually, I do agree with chromatic on that one. If you don't realize that your state is changing between test methods, having tests run in alphabetical order can mask hidden assumptions in your tests. The obvious example is not doing proper setup and teardown on test databases. But a more subtle example is when naughty code decides to change a global's value. That can be extremely difficult to debug.
Re:Never Been a Problem for Me
Adrian on 2006-10-02T14:04:50
True. But you can have the opposite sort of bugs where the lack of a persistent test environment hides bugs caused by changes in global state.
I generally find that these are more common than bugs hidden by a persistent environment. Maybe this is a side effect of my development style.
In general, in developer test land, I find tests involving lots of state cause more problems than they solve. Having tests that can run independently of each other is lovely.
You're spot on however with Test::Class's alphabetical ordering occasionally causing problems... it's on the list:-) Re:Never Been a Problem for Me
Adrian on 2006-10-02T12:54:50
In addition to the points that Ovid raised it makes grouping related test suites together easier. Have all your customer tests in one hierarchy, all your unit tests in another, all the slow ones in a third, etc.
(of course breaking things up like this by class isn't ideal - but finer grained breakdowns are on the to do list)
Re:I wonder
Adrian on 2006-10-02T13:45:29
Does the lib pragma try to convert those paths to the native file systemYup. See perldoc lib
:-) Re:I wonder
jk2addict on 2006-10-02T13:57:55
Well, I have, but it reads non clear in a clear but not clear sort of way.:-) In the future, this module will likely use File::Spec for determining paths, as it does now for Mac OS (where Unix-style or Mac-style paths work, and Unix-style paths are converted properly to Mac-style paths before being added to @INC).
This is from Perl 5.8.8. "In the future". Lot's of mention of MacOS. Nothing that leads me to believe that it's totally safe "now" vs. "in the future".:-) Re:I wonder
Adrian on 2006-10-02T14:11:00
In order to keep lib.pm small and simple, it only works with Unix filepaths. This doesn't mean it only works on Unix, but non-Unix users must first translate their file paths to Unix conventions.seems pretty clean to me
:-) Re:I wonder
jk2addict on 2006-10-02T14:33:49
Sigh. You're out of the club. What about VMS users.;-) Re:I wonder
Ovid on 2006-10-02T14:39:39
VMS users know that stuff doesn't work on their system, so it's OK to ship them broken code
;) Re:I wonder
jk2addict on 2006-10-02T14:41:17
Sad, but probably absolutely true.:-) Re:I wonder
schwern on 2007-03-29T09:20:55
Using Unix paths with lib works on VMS. In fact, its even mentioned in the docs.
# VMS users wanting to put [.stuff.moo] into
# their @INC would write
use lib 'stuff/moo';