Fix, test, document
Tomas Doran [Sun, 5 Feb 2012 18:41:16 +0000 (18:41 +0000)]
Changes
lib/Catalyst/Authentication/Credential/HTTP.pm
t/live_app.t

diff --git a/Changes b/Changes
index 803ad7c..ff12897 100644 (file)
--- a/Changes
+++ b/Changes
@@ -1,3 +1,6 @@
+   - Add require_ssl configuration setting.
+   - Add no_unprompted_authorization_required configuration setting.
+
 1.013 2010-12-14
    - Call store_digest_authorization_nonce() instead of $c->cache->set()
      in authenticate_digest() (RT#63669) (rjk)
index 13defab..629c7b9 100644 (file)
@@ -53,7 +53,7 @@ sub authenticate {
     my $auth;
 
     $self->authentication_failed( $c, $realm, $auth_info )
-        if $self->require_ssl ? $c->req->scheme ne 'https' : 0;
+        if $self->require_ssl ? $c->req->base->scheme ne 'https' : 0;
 
     $auth = $self->authenticate_digest($c, $realm, $auth_info) if $self->_is_http_auth_type('digest');
     return $auth if $auth;
@@ -66,7 +66,7 @@ sub authenticate {
 
 sub authentication_failed {
     my ( $self, $c, $realm, $auth_info ) = @_;
-    unless (!$self->no_unprompted_authorization_required) {
+    unless ($self->no_unprompted_authorization_required) {
         $self->authorization_required_response($c, $realm, $auth_info);
         die $Catalyst::DETACH;
     }
@@ -578,7 +578,7 @@ C<< $c->cache >>.
 
 =head1 CONFIGURATION
 
-All configuration is stored in C<< YourApp->config(authentication => { yourrealm => { credential => { class => 'HTTP', %config } } } >>.
+All configuration is stored in C<< YourApp->config('Plugin::Authentication' => { yourrealm => { credential => { class => 'HTTP', %config } } } >>.
 
 This should be a hash, and it can contain the following entries:
 
@@ -616,6 +616,23 @@ run through $c->uri_for(). Use this configuration option if your application is
 of your domain, and you want to ensure that authentication credentials from your application are not shared with
 other applications on the same server.
 
+=item require_ssl
+
+If this configuration key has a true value then authentication will be denied
+(and a 401 issued in normal circumstances) unless the request is via https.
+
+=item no_unprompted_authorization_required
+
+Causes authentication to fail as normal modules do, without calling
+C<< $c->detach >>. This means that the basic auth credential can be used as
+part of the progressive realm.
+
+However use like this is probably not optimum it also means that users in
+browsers ill never get a HTTP authenticate dialogue box (unless you manually
+return a 410 response in your application), and even some programatic
+user agents (for APIs) will not send the Authorization header without
+specific manipulation of the request headers.
+
 =back
 
 =head1 RESTRICTIONS
index fc07156..40e2ced 100644 (file)
@@ -14,13 +14,12 @@ BEGIN {
     }
       or plan skip_all =>
       "Test::WWW::Mechanize::Catalyst is needed for this test";
-    plan tests => 4;
 }
 use HTTP::Request;
 
 use Test::More;
-use Test::WWW::Mechanize::Catalyst qw/AuthTestApp/;
-my $mech = Test::WWW::Mechanize::Catalyst->new;
+use Test::WWW::Mechanize::Catalyst;
+my $mech = Test::WWW::Mechanize::Catalyst->new(catalyst_app => 'AuthTestApp');
 $mech->get("http://localhost/moose");
 is( $mech->status, 401, "status is 401" ) or die $mech->content;
 $mech->content_lacks( "foo", "no output" );
@@ -30,3 +29,18 @@ $mech->request($r);
 is( $mech->status, 200, "status is 200" );
 $mech->content_contains( "foo", "foo output" );
 
+AuthTestApp->get_auth_realm('test')->credential->no_unprompted_authorization_required(1);
+$mech = Test::WWW::Mechanize::Catalyst->new(catalyst_app => 'AuthTestApp');
+$mech->get("http://localhost/moose");
+isnt( $mech->status, 401, "status isnt 401" ) or die $mech->content;
+
+AuthTestApp->get_auth_realm('test')->credential->no_unprompted_authorization_required(0);
+AuthTestApp->get_auth_realm('test')->credential->require_ssl(1);
+$mech = Test::WWW::Mechanize::Catalyst->new(catalyst_app => 'AuthTestApp');
+$r = HTTP::Request->new( GET => "http://localhost/moose" );
+$r->authorization_basic(qw/foo s3cr3t/);
+$mech->request($r);
+is( $mech->status, 401, "status is 401" );
+
+done_testing;
+