Beefy Boxes and Bandwidth Generously Provided by pair Networks
laziness, impatience, and hubris
 
PerlMonks  

Help with Try::Tiny and Catalyst::Authentication::Realm::Progressive

by ghenry (Vicar)
on Dec 13, 2011 at 00:03 UTC ( #943212=perlquestion: print w/ replies, xml ) Need Help??
ghenry has asked for the wisdom of the Perl Monks concerning the following question:

Hi all,

Been a while. I've been banging my head for ages and can't work out why changing the following makes prove fail

[http://cpansearch.perl.org/src/BOBTFISH/Catalyst-Plugin-Authenticatio +n-0.10018/lib/Catalyst/Authentication/Realm/Progressive.pm] if ( my $obj = $realm->authenticate( $c, $auth ) ) { $c->set_authenticated( $obj, $realm->name ); return $obj; } Changes: 139 my $auth_obj; 140 my $error = try { 141 $auth_obj = $realm->authenticate( $c, $auth ); 142 } 143 catch { return $_; }; 144 145 if ($auth_obj) { 146 $c->set_authenticated( $auth_obj, $realm->name ); 147 return $auth_obj; 148 }

[ghenry@dax-xen Catalyst-Plugin-Authentication]$ cat t/live_app_realms +_progressive.t use strict; use warnings; use Test::More; use lib 't/lib'; use Catalyst::Test qw/AuthRealmTestAppProgressive/; ok(get("/progressive"), "get ok"); done_testing; [ghenry@dax-xen Catalyst-Plugin-Authentication]$ cat t/lib/AuthRealmTe +stAppProgressive/Controller/Root.pm package AuthRealmTestAppProgressive::Controller::Root; use warnings; use strict; use base qw/Catalyst::Controller/; __PACKAGE__->config(namespace => ''); use Test::More; use Test::Exception; sub progressive : Local { my ( $self, $c ) = @_; foreach my $realm ( keys %AuthRealmTestAppProgressive::members ) { while ( my ( $user, $info ) = each %{$AuthRealmTestAppProgress +ive::members{$realm}} ) { my $ok = eval { $c->authenticate( { username => $user, password => $info->{password} + }, ); }; diag $@; diag $ok; ok( !$@, "authentication passed." ); ok( $ok, "user authenticated" ); ok( $c->user_in_realm($realm), "user in proper realm" ); } } $c->res->body( "ok" ); } 1; [ghenry@dax-xen Catalyst-Plugin-Authentication]$ prove -l t/live_app_r +ealms_progressive.t t/live_app_realms_progressive.t .. # # undef t/live_app_realms_progressive.t .. 1/? # Failed test 'user authenticated' # at t/lib/AuthRealmTestAppProgressive/Controller/Root.pm line 24. # Failed test 'user in proper realm' # at t/lib/AuthRealmTestAppProgressive/Controller/Root.pm line 25. # # undef # Failed test 'user authenticated' # at t/lib/AuthRealmTestAppProgressive/Controller/Root.pm line 24. # Looks like you failed 3 tests of 7. t/live_app_realms_progressive.t .. Dubious, test returned 3 (wstat 768 +, 0x300) Failed 3/7 subtests Test Summary Report ------------------- t/live_app_realms_progressive.t (Wstat: 768 Tests: 7 Failed: 3) Failed tests: 2-3, 5 Non-zero exit status: 3 Files=1, Tests=7, 7 wallclock secs ( 0.09 usr 0.00 sys + 4.14 cusr + 0.09 csys = 4.32 CPU) Result: FAIL

I'm trying to patch Catalyst::Authentication::Realm::Progressive to allow multiple realms with Basic HTTP auth, as the credential HTTP plugin calls ->detach which means other realms never get tried.
Thanks.

Walking the road to enlightenment... I found a penguin and a camel on the way.....
Fancy a yourname@perl.me.uk? Just ask!!!

Comment on Help with Try::Tiny and Catalyst::Authentication::Realm::Progressive
Select or Download Code
Replies are listed 'Best First'.
Re: Help with Try::Tiny and Catalyst::Authentication::Realm::Progressive (catch { return })
by tye (Cardinal) on Dec 13, 2011 at 00:30 UTC

    You can't make your outer sub return by saying 'return' within the (implied) sub that you passed to 'catch'. catch { return } is the same as &catch( sub { return } ) so the 'return' simply returns from the anonymous sub.

    - tye        

      Thanks. I've realised that from the docs and doing more tests now, but why, without catch does $auth_obj = $realm->authenticate( $c, $auth ); not work as expected like the original code? Nothing else has changed.

      Walking the road to enlightenment... I found a penguin and a camel on the way.....
      Fancy a yourname@perl.me.uk? Just ask!!!
Re: Help with Try::Tiny and Catalyst::Authentication::Realm::Progressive (local $@)
by tye (Cardinal) on Dec 13, 2011 at 07:42 UTC

    By running it through prove instead of just running it directly, you make it harder to understand the output. But...

    my $ok = eval { $c->authenticate( { username => $user, password => $info->{password} + }, ); }; diag $@; diag $ok; [...] t/live_app_realms_progressive.t t/live_app_realms_progressive.t .. # # undef [...] # # undef

    Shows that the eval is failing (setting $ok to undef) but also leaving $@ as the empty string. Devel::EvalError explains how this can happen -- some of this has changed in the most recent versions of Perl (somewhat for the better, somewhat for the worse).

    Devel::EvalError will even add a __DIE__ handler for you so that you can see the lost $@ value. The syntax of that module is stupidly ugly (the author was foolishly thinking that he had to avoid 'try { ... }' syntax because you can't "return" from it when the fact is that you can't "return" from 'eval { ... }' in exactly the same way and what he needed to avoid was only the obnoxious 'catch { ... }' syntax), so you can also just add your own __DIE__ handler simply enough.

    Update: Oops. That is only one possible explanation. But it is more likely that the method call is just returning undef. I'd write that as:

    my $res; my $ok= eval { $res= $c->...; 1; };

    so the distinction is clear.

    - tye        

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://943212]
Approved by GrandFather
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others surveying the Monastery: (9)
As of 2015-07-30 21:46 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    The top three priorities of my open tasks are (in descending order of likelihood to be worked on) ...









    Results (273 votes), past polls