Beefy Boxes and Bandwidth Generously Provided by pair Networks
go ahead... be a heretic
 
PerlMonks  

Perl Catalyst

by akuk (Sexton)
on Oct 10, 2018 at 13:50 UTC ( #1223799=perlquestion: print w/replies, xml ) Need Help??
akuk has asked for the wisdom of the Perl Monks concerning the following question:

Hi Folks,

I am working on a Project to migrate the Legacy App in Perl to Catalyst Framework. Legacy app has its own authentication mechanism. And it uses Crypt::PBKDF2 to store the password in the database.

I want to use Catalyst::Plugin::Authentication instead of custom login mechanism for catalyst but I didn't find a way to authenticate password using Authentication Plugin

Legacy:

$pbk_crypt = Crypt::PBKDF2->new( hash_class => 'HMACSHA2', hash_args => { sha_size => 512, }, iterations => 10000, salt_len => 10, ); $pass = $pbk_crypt->generate('password');

Catalyst

__PACKAGE__->config( 'Plugin::Authentication' => { default => { class => 'SimpleDB', user_model => 'DB::User', password_type => 'self_check', }, )
And in the User table following code is added:
__PACKAGE__->add_columns( 'password' => { passphrase => 'rfc2307', passphrase_class => 'SaltedDigest', passphrase_args => { algorithm => 'SHA-512', salt_random => 10, iterations => 10000, }, passphrase_check_method => 'check_password', }, );

And in Controller :

if ($username and $password) { if ($c->authenticate({ username => $username, password => $password } )) { $c->response->redirect($c->uri_for_action('/profile')); return; } else { # Set an error message $c->stash(error_msg => "Bad username or password."); } }
but it's not working. I am not sure what I am doing wrong here.

Replies are listed 'Best First'.
Re: Perl Catalyst
by Your Mother (Bishop) on Oct 10, 2018 at 17:37 UTC

    You seem to be configuring the DB column wrongly, at least, for DBIC. Try following this doc and ensuring you have the module installed: DBIx::Class::EncodedColumn::Crypt::PBKDF2. If that doesn't work, let us know and I'll try to dig deeper. Snippet from it–

    __PACKAGE__->add_columns( 'password' => { data_type => 'text', encode_column => 1, encode_class => 'Crypt::PBKDF2', encode_args => { hash_class => 'HMACSHA1', iterations => 1000 }, encode_check_method => 'check_password', } )

      Thanks for this information.

      App File, Authentication settings

      'Plugin::Authentication' => { default_realm => 'members', members => { credential => { class => 'Password', password_field => 'password', password_type => 'self_check' }, store => { class => 'DBIx::Class', user_model => 'DB::User', } } },

      modified add_columns in the User

      __PACKAGE__->add_columns( 'password' => { data_type => 'varchar', encode_column => 1, encode_class => 'Crypt::PBKDF2', encode_args => { hash_class => 'HMACSHA2', hash_args => { sha_size => 512, }, iterations => 10000, salt_len => 10, }, encode_check_method => 'check_password', } );

      data type of password field is varchar type, hence the varchar is used in the above code.

      To my surprise, when I changed the password of the user through a script, it is not encrypting the password field

      .
      #!/usr/bin/perl use strict; use warnings; use MyApp::Schema; my $schema = MyApp::Schema->connect('dbi:mysql:database', 'root', ''); my @users = $schema->resultset('User')->all; # Just traversing the User foreach my $user (@users) { if ($user->email eq 'xyz') { $user->password('password'); $user->update; } }

      when I checked the database, it stores the password in the clear text whereas it should save it in the encrypted format.

        Finally, I figured it out, how to authenticate using Crypt::PBKDF2

        Just in case anyone else stuck in this loop. Here is the way

        # In App.pm 'Plugin::Authentication' => { default_realm => 'members', members => { credential => { class => 'Password', password_field => 'password', password_type => 'self_check' }, store => { class => 'DBIx::Class', user_model => 'DB::User', } } },

        And now the DB::User file

        __PACKAGE__->load_components("InflateColumn::DateTime", "TimeStam +p", "EncodedColumn"); # Pay special attention to EncodedColumn, I was using passphrase colum +n there. That my silly mistake and it cost me hours # and now add_columns __PACKAGE__->add_columns( 'password' => { data_type => 'text', encode_column => 1, encode_class => 'Crypt::PBKDF2', encode_args => { hash_class => 'HMACSHA2', hash_args => { sha_size => 512, }, iterations => 10000, salt_len => 10, }, encode_check_method => 'check_password', } );

        And this works for me. Thanks for the assistance "@Your Mother"

Re: Perl Catalyst
by Corion (Pope) on Oct 10, 2018 at 13:58 UTC

    How is it not working?

    Does the new code calculate a different password hash than the legacy code?

    Do the versions calculate the same password hash but the new code doesn't update the session?

      The password validation goes wrong. It's generating the wrong password than the legacy. But I am not sure why.

      Legacy Password is generated by:

      $pbk_crypt = Crypt::PBKDF2->new( hash_class => 'HMACSHA2', hash_args => { sha_size => 512, }, iterations => 10000, salt_len => 10, ); $pass = $pbk_crypt->generate('password');

Log In?
Username:
Password:

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

How do I use this? | Other CB clients
Other Users?
Others about the Monastery: (4)
As of 2018-12-10 01:38 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?
    How many stories does it take before you've heard them all?







    Results (47 votes). Check out past polls.

    Notices?
    • (Sep 10, 2018 at 22:53 UTC) Welcome new users!