Reputation: 10558
Given the below code example, when running Main::main, if the eval block fails, I would assume that the 'after' block in the role would never run. However, I'm in the midst of debugging an intermittent and hard-to-pin-down error that would suggest this is not the case.
Could someone explain how the 'flattening' process works in this context, and if there are any conditions in which the eval would fail but the after block would run?
Thanks Josh
package MyRole;
use Moose::Role;
after 'main' => sub {
#some code that depends on main executing
};
package Main;
use Moose;
with 'MyRole';
sub main {
eval {
#main work
};
if ($@) {
die 'what happens now?';
}
}
Upvotes: 1
Views: 80
Reputation: 6798
MyRole::main() would normally execute after Main::main().
They are not exactly flattened into one method with one after the other in that what you return in Main::main() is still what gets returned and anything you return in MyRole::main() is ignored.
If 'main work' fails, MyRole::main() will not execute since you also die in the catch (if $@
) block, which means that the flow of execution dies before it reaches MyRole::main().
Upvotes: 2
Reputation: 62109
If main
dies, then the after modifier will not run. However, it is possible for an eval
to fail but $@
to be false. It sounds like that must be what's happening here. If the eval
fails, but $@
is false, your error handling code won't run and main
won't throw an exception. Thus, the after main
code will be run.
This is one of the things Try::Tiny protects you against.
Upvotes: 2