kcott has asked for the wisdom of the Perl Monks concerning the following question:
require describes inserting hooks into @INC.
I've been testing this out for use in a module I'm writing. Here's a very cutdown version of the code:
package RequireHookTest; use 5.032; use warnings; use Moose; use namespace::autoclean; sub dynamic_require { my ($self, $ns_extension) = @_; { my $class = join '::', __PACKAGE__, $ns_extension; my $source = <<~EOF; package $class; use Moose; extends 'RequireHookTest'; use namespace::autoclean; __PACKAGE__->meta->make_immutable; 1; EOF my sub for_inc { my ($coderef, $filename) = @_; return \$source }; my $for_inc_ref = \&for_inc; push @INC, $for_inc_ref; eval "require $class;"; } return; } __PACKAGE__->meta->make_immutable; 1;
Calling dynamic_require() worked a treat at first; however, when testing with an additional call, I got the quite unexpected message: Can't locate object method "new" ... for the second call (the first call still worked fine).
Here's an SSCCE:
#!perl use 5.032; use warnings; use FindBin; use lib "$FindBin::Bin/lib"; use Test::More tests => 6; use RequireHookTest; my $rht = RequireHookTest::->new(); is(defined $rht, 1, 'Test RequireHookTest::->new()'); isa_ok($rht, 'RequireHookTest', 'Test RequireHookTest::->new() ISA'); $rht->dynamic_require('Test1'); my $rht_test1 = RequireHookTest::Test1->new(); is(defined $rht_test1, 1, 'Test RequireHookTest::Test1->new()'); isa_ok($rht_test1, 'RequireHookTest::Test1', 'Test RequireHookTest::Te +st1->new() ISA'); $rht->dynamic_require('Test2'); my $rht_test2 = RequireHookTest::Test2->new(); is(defined $rht_test2, 1, 'Test RequireHookTest::Test2->new()'); isa_ok($rht_test2, 'RequireHookTest::Test2', 'Test RequireHookTest::Te +st2->new() ISA');
Example run:
$ prove -v sscce_require_hook_test.t sscce_require_hook_test.t .. 1..6 ok 1 - Test RequireHookTest::->new() ok 2 - 'Test RequireHookTest::->new() ISA' isa 'RequireHookTest' ok 3 - Test RequireHookTest::Test1->new() ok 4 - 'Test RequireHookTest::Test1->new() ISA' isa 'RequireHookTest:: +Test1' Can't locate object method "new" via package "RequireHookTest::Test2" +at sscce_require_hook_test.t line 23. # Looks like your test exited with 255 just after 4. Dubious, test returned 255 (wstat 65280, 0xff00) Failed 2/6 subtests Test Summary Report ------------------- sscce_require_hook_test.t (Wstat: 65280 Tests: 4 Failed: 0) Non-zero exit status: 255 Parse errors: Bad plan. You planned 6 tests but ran 4. Files=1, Tests=4, 0 wallclock secs ( 0.00 usr 0.03 sys + 0.20 cusr + 0.09 csys = 0.33 CPU) Result: FAIL
If I swap the last two blocks of code around, "Test2" works and "Test1" has the new() problem:
... ok 3 - Test RequireHookTest::Test2->new() ok 4 - 'Test RequireHookTest::Test2->new() ISA' isa 'RequireHookTest:: +Test2' Can't locate object method "new" via package "RequireHookTest::Test1" +at sscce_require_hook_test.t line 23. ...
In the module code, I tried pushing an ARRAYREF, instead of a CODEREF, onto @INC:
push @INC, [ $for_inc_ref ];
but the result was the same.
I've also tried various versions where use namespace::autoclean; and/or __PACKAGE__->meta->make_immutable; were excluded just in case that made any difference: it didn't.
This one's got me stumped. Any help would be very much appreciated.
Note: My (real) code is using version 5.32.0 so I've left that specified.
— Ken
|
---|
Replies are listed 'Best First'. | |
---|---|
Re: require() @INC hooks problem [SOLVED]
by kcott (Archbishop) on Dec 28, 2020 at 00:40 UTC | |
Re: require() @INC hooks problem
by LanX (Saint) on Dec 27, 2020 at 20:56 UTC | |
by kcott (Archbishop) on Dec 27, 2020 at 21:12 UTC | |
Re: require() @INC hooks problem
by LanX (Saint) on Dec 27, 2020 at 20:18 UTC | |
by kcott (Archbishop) on Dec 27, 2020 at 21:06 UTC | |
by LanX (Saint) on Dec 27, 2020 at 21:11 UTC | |
by kcott (Archbishop) on Dec 27, 2020 at 21:52 UTC | |
by choroba (Cardinal) on Dec 27, 2020 at 22:24 UTC | |
| |
by kcott (Archbishop) on Dec 27, 2020 at 21:18 UTC | |
by LanX (Saint) on Dec 27, 2020 at 21:28 UTC | |
Re: require() @INC hooks problem
by LanX (Saint) on Dec 28, 2020 at 06:28 UTC | |
by kcott (Archbishop) on Dec 28, 2020 at 10:22 UTC | |
by LanX (Saint) on Dec 28, 2020 at 13:14 UTC | |
by kcott (Archbishop) on Dec 28, 2020 at 16:13 UTC | |
by LanX (Saint) on Dec 28, 2020 at 16:24 UTC | |
|