Oops... forgot to CC to group. Adrian.
Begin forwarded message:
> From: Adrian Howard <[EMAIL PROTECTED]>
> Date: Sun Jun 16, 2002 08:25:37 pm Europe/London
> To: Michael G Schwern <[EMAIL PROTECTED]>
> Subject: Re: Test::Class... comments?
>
> On Sunday, June 16, 2002, at 09:07 am, Michael G Schwern wrote:
>
>> On Sun, Jun 16, 2002 at 12:14:59AM +0100, Adrian Howard wrote:
>>> 0) Do other people find this vaguely sane? Even <gasp> possibly
>>> useful?
>>
>> Yes! xUnit with a Perl spin is something I've wanted for a long time.
> [snip]
>
> Not just me then. Good :-)
>
>>> 3) The fact that num_method_tests() uses the class it was called
>>> from,
>>> rather that the one it was applied to, seems kind of gnarly. However,
>>> it did seem the neatest solution to the inheritance problem mentioned
>>> in the documentation. How offensive do people find this, and is there
>>> a better solution?
>>
>> I don't quite follow the problem. Could you clarify?
>
> Rather contrived illustration follows:
>
> Consider a test method that runs a variable number of test:
>
> package Base::Test;
> use base qw(Test::Class);
> use Test::More;
>
> sub foo : Test(no_plan) {
> my $self = shift;
> my $objects = $self->{objects};
> isa_ok($_, 'Foo') foreach @$objects;
> };
>
> Doing:
>
> Base::Test->new(objects => [Foo->new, Foo->new])->runtests;
>
> gives us
>
> ok 1 - The object isa Foo
> ok 2 - The object isa Foo
> 1..2
>
> This works fine, but since having a predetermined number of tests is a
> Good Thing we want to let Test::Class know how many tests the method
> should run. Since we don't know this until the test object is created we
> override new() and set the number of tests then.
>
> sub new {
> my $class = shift;
> my $self = $class->SUPER::new(@_);
> my $num_objects = @{$self->{objects}};
> $self->num_method_tests('foo', $num_objects);
> diag("Base::Test foo in $self now runs $num_objects tests");
> return($self);
> };
>
> which will give us something like
>
> # Base::Test foo in Base::Test=HASH(0x11734) now runs 2 tests
> 1..2
> ok 1 - The object isa Foo
> ok 2 - The object isa Foo
>
> Now, consider what happens when we extend check_fooness in a subclass:
>
> package Another::Test;
> use base qw(Base::Test);
> use Test::More;
>
> # add one more test to the expected # of tests for foo
> sub foo : Test(+1) {
> my $self = shift;
> $self->SUPER::foo;
> ok(1==1, 'pointless test');
> };
>
> What we want to happen is for Test::Class to figure out that the total
> number of tests that foo() should run in Another::Test is the number of
> objects in $self->{objects}, plus one.
>
> Test::Class does manage this so:
>
> Another::Test->new(objects => [Foo->new, Foo->new])->runtests;
>
> will give us
>
> # Base::Test foo in Another::Test=HASH(0x1174c) now runs 2 tests
> 1..3
> ok 1 - The object isa Foo
> ok 2 - The object isa Foo
> ok 3 - pointless test
>
> Now, the way I do this at the moment is have num_method_tests() walk up
> the callstack until it finds a package that also isa Test::Class (in
> this
> case Base::Test) and then assume that is the class containing the method
> whose # tests it should alter.
>
> While this works, it just seems a trifle evil. When I coded it my
> thoughts went something like "Gosh. That's a greasy hack... must fix
> that later". When later eventually came around the other solutions I
> came up with seemed even worse.
>
> I just have a sneaking feeling that there's a more elegant (for some
> definition of "elegant") way of handling changing the number of tests
> for test methods that will cope with inheritance nicely.
>
> Make sense?
>
> Adrian
--
Adrian Howard <[EMAIL PROTECTED]>
phone: 01929 550720 fax: 0870 131 3033 www.quietstars.com
>