payprop / net-oauth2-authorizationserver

Module to implement core functions of an OAuth2 authorization server
7 stars 10 forks source link

Client credentials issue #28

Closed danjboyd closed 3 years ago

danjboyd commented 4 years ago

I'm using the oauth2_server_db.pl file as a launching point for a production OAuth2 server. I am trying to get the client credentials grant type operational. The example code breaks in the store_access_token_sub because client_credentials doesn't have an auth_code. I patched the function like this. I'm not sure this was the best way to handle, though...

if ( ! defined( $auth_code ) && $old_refresh_token) {
...
# new code
} elsif( ! defined $auth_code ) {
    $user_id = $args{client_id};  #not sure what else to set the user_id to...? there is no user
# end new code
} else {
    $user_id = $c->db->get_collection( 'auth_codes' )->find_one({
        auth_code => $auth_code,
    })->{user_id};
}
leejo commented 4 years ago

The client credentials flow doesn't use an authorisation code that's only the authorisation code grant, which thestore_access_token_sub example is demonstrating here. You'll need to tweak it as necessary for the grant type you are using. Here's an example from our production app that uses both the authorisation code grant and the implicit grant, so it handles both. You'll need something similar to the final elsif case in the block below:

sub _store_access_token {

    ...

    if ( ! defined( $auth_code ) && $old_refresh_token ) {
        # must have generated an access token via a refresh token so revoke the
        # old access token and refresh token (also copy required data if missing)
        my $RefreshToken = Foo::Model::OAuth2::RefreshToken->new_from_token(
            $old_refresh_token
        );

        # access tokens can be revoked, whilst refresh tokens can remain so we
        # need to get the data from the refresh token as the access token may
        # no longer exist at the point that the refresh token is used
        $scope //= $RefreshToken->privileges;

        $application_user_id = $RefreshToken->application_user_id;

    } elsif ( $auth_code ) {
        # came in using the auth code grant
        my $AuthCode = Foo::Model::OAuth2::AuthCode->new_from_code( $auth_code );
        $application_user_id = $AuthCode->application_user_id;

    } elsif ( $access_token ) {
        # came in using the implicit grant
        $implicit_grant++;
        $application_user_id = _get_application_user( $c )->id;
    }

    ....

}
danjboyd commented 3 years ago

perfect -- thank you. Yes I am planning to use both auth code and client.