Put this into the tag/0.14 initially (which isn't actually a tag). This should be...
[catagits/Catalyst-Authentication-Credential-OpenID.git] / lib / Catalyst / Authentication / Credential / OpenID.pm
index fa6b2d0..560f931 100644 (file)
@@ -1,17 +1,15 @@
 package Catalyst::Authentication::Credential::OpenID;
 use strict;
-use warnings;
-no warnings "uninitialized";
+# use warnings; no warnings "uninitialized"; # for testing, not production
 use parent "Class::Accessor::Fast";
 
 BEGIN {
     __PACKAGE__->mk_accessors(qw/ _config realm debug secret /);
 }
 
-our $VERSION = "0.03";
+our $VERSION = "0.14";
 
 use Net::OpenID::Consumer;
-use UNIVERSAL::require;
 use Catalyst::Exception ();
 
 sub new : method {
@@ -34,14 +32,13 @@ sub new : method {
                                                             );
 
     $secret = substr($secret,0,255) if length $secret > 255;
-    $self->secret( $secret );
+    $self->secret($secret);
     $self->_config->{ua_class} ||= "LWPx::ParanoidAgent";
 
-    eval {
-        $self->_config->{ua_class}->require;
-    }
-    or Catalyst::Exception->throw("Could not 'require' user agent class " .
-                                  $self->_config->{ua_class});
+    my $agent_class = $self->_config->{ua_class};
+    eval "require $agent_class"
+        or Catalyst::Exception->throw("Could not 'require' user agent class " .
+                                      $self->_config->{ua_class});
 
     $c->log->debug("Setting consumer secret: " . $secret) if $self->debug;
 
@@ -74,13 +71,16 @@ sub authenticate : method {
         my $identity = $csr->claimed_identity($claimed_uri)
             or Catalyst::Exception->throw($csr->err);
 
+        $identity->set_extension_args(@{$self->_config->{extension_args}})
+            if $self->_config->{extension_args};
+
         my $check_url = $identity->check_url(
             return_to  => $current . '?openid-check=1',
             trust_root => $current,
             delayed_return => 1,
         );
         $c->res->redirect($check_url);
-        return;
+        $c->detach();
     }
     elsif ( $c->req->params->{'openid-check'} )
     {
@@ -98,6 +98,10 @@ sub authenticate : method {
             # This is where we ought to build an OpenID user and verify against the spec.
             my $user = +{ map { $_ => scalar $identity->$_ }
                 qw( url display rss atom foaf declared_rss declared_atom declared_foaf foafmaker ) };
+            
+            for(keys %{$self->{_config}->{extensions}}) {
+                $user->{extensions}->{$_} = $identity->signed_extension_fields($_);
+            }
 
             my $user_obj = $realm->find_user($user, $c);
 
@@ -126,15 +130,15 @@ __END__
 
 =head1 NAME
 
-Catalyst::Authentication::Credential::OpenID - OpenID credential for L<Catalyst::Plugin::Authentication> framework.
+Catalyst::Authentication::Credential::OpenID - OpenID credential for Catalyst::Plugin::Authentication framework.
 
 =head1 VERSION
 
-0.03
+0.13
 
 =head1 SYNOPSIS
 
-In MyApp.pm.
+In MyApp.pm-
 
  use Catalyst qw/
     Authentication
@@ -143,24 +147,21 @@ In MyApp.pm.
     Session::State::Cookie
  /;
 
-Somewhere in myapp.conf.
+Somewhere in myapp.conf-
 
  <Plugin::Authentication>
      default_realm   openid
      <realms>
          <openid>
-             ua_class   LWPx::ParanoidAgent
              <credential>
-                 <store>
-                     class   OpenID
-                 </store>
                  class   OpenID
              </credential>
+             ua_class   LWPx::ParanoidAgent
          </openid>
      </realms>
  </Plugin::Authentication>
 
-Or in your myapp.yml if you're using L<YAML> instead.
+Or in your myapp.yml if you're using L<YAML> instead-
 
  Plugin::Authentication:
    default_realm: openid
@@ -170,7 +171,7 @@ Or in your myapp.yml if you're using L<YAML> instead.
          class: OpenID
        ua_class: LWPx::ParanoidAgent
 
-In a controller, perhaps C<Root::openid>.
+In a controller, perhaps C<Root::openid>-
 
  sub openid : Local {
       my($self, $c) = @_;
@@ -186,7 +187,7 @@ In a controller, perhaps C<Root::openid>.
       }
  }
 
-And a L<Template> to match in C<openid.tt>.
+And a L<Template> to match in C<openid.tt>-
 
  <form action="[% c.uri_for('/openid') %]" method="GET" name="openid">
  <input type="text" name="openid_identifier" class="openid" />
@@ -196,10 +197,10 @@ And a L<Template> to match in C<openid.tt>.
 =head1 DESCRIPTION
 
 This is the B<third> OpenID related authentication piece for
-L<Catalyst>. The first -- L<Catalyst::Plugin::Authentication::OpenID>
-by Benjamin Trott -- was deprecated by the second --
+L<Catalyst>. The first E<mdash> L<Catalyst::Plugin::Authentication::OpenID>
+by Benjamin Trott E<mdash> was deprecated by the second E<mdash>
 L<Catalyst::Plugin::Authentication::Credential::OpenID> by Tatsuhiko
-Miyagawa -- and this is an attempt to deprecate both by conforming to
+Miyagawa E<mdash> and this is an attempt to deprecate both by conforming to
 the newish, at the time of this module's inception, realm-based
 authentication in L<Catalyst::Plugin::Authentication>.
 
@@ -221,7 +222,7 @@ This module functions quite differently internally from the others.
 See L<Catalyst::Plugin::Authentication::Internals> for more about this
 implementation.
 
-=head1 METHOD
+=head1 METHODS
 
 =over 4
 
@@ -324,10 +325,17 @@ clear text passwords and one called "openid" which uses... uh, OpenID.
                           class => "OpenID",
                       },
                   },
+                  extension_args => [
+                      'http://openid.net/extensions/sreg/1.1',
+                      {
+                       required => 'email',
+                       optional => 'fullname,nickname,timezone',
+                      },
+                  ],
               },
           },
-      },
-      );
+      }
+    );
 
 This is the same configuration in the default L<Catalyst> configuration format from L<Config::General>.
 
@@ -363,6 +371,11 @@ This is the same configuration in the default L<Catalyst> configuration format f
                  </store>
                  class   OpenID
              </credential>
+             <extension_args>
+                 http://openid.net/extensions/sreg/1.1
+                 required   email
+                 optional   fullname,nickname,timezone
+             </extension_args>
          </openid>
      </realms>
  </Plugin::Authentication>
@@ -394,8 +407,16 @@ And now, the same configuration in L<YAML>. B<NB>: L<YAML> is whitespace sensiti
          whitelisted_hosts:
            - 127.0.0.1
            - localhost
+       extension_args:
+           - http://openid.net/extensions/sreg/1.1
+           - required: email
+             optional: fullname,nickname,timezone
+
+B<NB>: There is no OpenID store yet.
 
-B<NB>: There is no OpenID store yet. Trying for next release.
+=head2 EXTENSIONS TO OPENID
+
+The L<Simple Registration|http://openid.net/extensions/sreg/1.1> (SREG) extension to OpenID is supported in the L<Net::OpenID> family now. Experimental support for it is included here as of v0.12. SREG is the only supported extension in OpenID 1.1. It's experimental in the sense it's a new interface and barely tested. Support for OpenID extensions is here to stay.
 
 =head2 MORE ON CONFIGURATION
 
@@ -405,7 +426,7 @@ These are set in your realm. See above.
 
 =item ua_args and ua_class
 
-L<LWPx::ParanoidAgent> is the default agent -- C<ua_class>. You don't
+L<LWPx::ParanoidAgent> is the default agent E<mdash> C<ua_class>. You don't
 have to set it. I recommend that you do B<not> override it. You can
 with any well behaved L<LWP::UserAgent>. You probably should not.
 L<LWPx::ParanoidAgent> buys you many defenses and extra security
@@ -426,6 +447,8 @@ longer). This should generally be superior to any fixed string.
 
 =head1 TODO
 
+Support more of the new methods in the L<Net::OpenID> kit.
+
 There are some interesting implications with this sort of setup. Does
 a user aggregate realms or can a user be signed in under more than one
 realm? The documents could contain a recipe of the self-answering
@@ -438,13 +461,17 @@ Better diagnostics in errors. Debug info at all consumer calls.
 
 Roles from provider domains? Mapped? Direct? A generic "openid" auto_role?
 
+=head1 THANKS
+
+To Benjamin Trott (L<Catalyst::Plugin::Authentication::OpenID>), Tatsuhiko Miyagawa (L<Catalyst::Plugin::Authentication::Credential::OpenID>), Brad Fitzpatrick for the great OpenID stuff, Martin Atkins for picking up the code to handle OpenID 2.0, and Jay Kuri and everyone else who has made Catalyst such a wonderful framework.
+
+L<Menno Blom|http://search.cpan.org/~blom/> provided a bug fix and the hook to use OpenID extensions.
+
 =head1 LICENSE AND COPYRIGHT
 
-Copyright (c) 2008, Ashley Pond V C<< <ashley@cpan.org> >>. Some of
-Tatsuhiko Miyagawa's work is reused here.
+Copyright (c) 2008, Ashley Pond V C<< <ashley@cpan.org> >>. Some of Tatsuhiko Miyagawa's work is reused here.
 
-This module is free software; you can redistribute it and modify it
-under the same terms as Perl itself. See L<perlartistic>.
+This module is free software; you can redistribute it and modify it under the same terms as Perl itself. See L<perlartistic>.
 
 =head1 DISCLAIMER OF WARRANTY
 
@@ -469,37 +496,26 @@ failure of the software to operate with any other software), even if
 such holder or other party has been advised of the possibility of
 such damages.
 
-=head1 THANKS
-
-To Benjamin Trott, Tatsuhiko Miyagawa, and Brad Fitzpatrick for the
-great OpenID stuff and to Jay Kuri and everyone else who has made
-Catalyst such a wonderful framework.
-
 =head1 SEE ALSO
 
 =over 4
 
 =item OpenID
 
-L<Net::OpenID::Server>, L<Net::OpenID::VerifiedIdentity>,
-L<Net::OpenID::Consumer>, and L<LWPx::ParanoidAgent>.
-
-L<http://openid.net/>, and L<http://openid.net/developers/specs/>.
+L<Net::OpenID::Server>, L<Net::OpenID::VerifiedIdentity>, L<Net::OpenID::Consumer>, L<http://openid.net/>, L<http://openid.net/developers/specs/>, and L<http://openid.net/extensions/sreg/1.1>.
 
 =item Catalyst Authentication
 
 L<Catalyst>, L<Catalyst::Plugin::Authentication>, L<Catalyst::Manual::Tutorial::Authorization>, and L<Catalyst::Manual::Tutorial::Authentication>.
 
-=item Catalyst Configuraiton
+=item Catalyst Configuration
 
 L<Catalyst::Plugin::ConfigLoader>, L<Config::General>, and L<YAML>.
 
 =item Miscellaneous
 
-L<Catalyst::Manual::Tutorial::CatalystBasics>, L<Template>, L<LWPx::ParanoidAgent>.
+L<Catalyst::Manual::Tutorial>, L<Template>, L<LWPx::ParanoidAgent>.
 
 =back
 
-L<Catalyst::Plugin::Authentication::OpenID> (Benjamin Trott) and L<Catalyst::Plugin::Authentication::Credential::OpenID> (Tatsuhiko Miyagawa).
-
 =cut