wiki:docs_oauth2

Background

The OAuth 2.0 authorization framework enables a third-party application (Google,Facebook etc.) to obtain limited access to an HTTP service, either on behalf of a resource owner by orchestrating an approval interaction between the resource owner and the HTTP service, or by allowing the third-party application to obtain access on its own behalf.

basic steps

Irrespective of the third-party application used, at a high level there are several steps:

  • Registering application to obtain OAuth2 credentials of the third-party, such as client ID and client secret.
  • Obtaining authorization to access third-party's API (OAuth2 server)
  • User authentication on OAuth2 server
  • Redirecting back to user application

Specific Examples

In this section we will provide some specific examples of authentication flow employing different third-party applications. We start with Google. More examples will be provided later.

Google's OAuth2 API

Detailed documentation is available at https://developers.google.com/identity/protocols/OAuth2

Below is a compete example of user authentication using Google's PHP API library and jQuery:

  • Obtain web application credentials for your project. Compete the following steps:
    • Go to Google API console. Create a project.
    • Create your OAuth 2.0 credentials by clicking 'Create new Client ID' under the 'OAuth Client ID' heading. Choose 'Web Application'.
    • For 'Authorized redirect URIs' put the path in your application that user will be redirected to after authentication via Google. For the example provided below, it should be a path to oath2.php file.
    • Download user credentials for you project by clicking 'Download JSON' in Google API console and save it to the place when oath2.php resides.
    • Rename a saved .json to 'client_secrets.json'.
composer require google/apiclient:^2.0
  • create the file oauth2.php with the following content

<?php
require_once __DIR__.'/vendor/autoload.php';    

session_start();

$client = new Google_Client();
$client->setAuthConfig('client_secrets.json');               // 'client_secrets.json' is downloaded from Google's API console for your project 

$client->addScope(Google_Service_Oauth2::USERINFO_PROFILE);
$client->addScope(Google_Service_Oauth2::USERINFO_EMAIL);

$service = new Google_Service_Oauth2($client);              // you can create different services to access user's information, look Google's documentation

if (! isset($_GET['code'])) {
$auth_url = $client->createAuthUrl();
//header('Location: ' . filter_var($auth_url, FILTER_SANITIZE_URL));

echo filter_var($auth_url, FILTER_SANITIZE_URL);
		     
} 
else {
  	$client->authenticate($_GET['code']);
  	$_SESSION['access_token'] = $client->getAccessToken();
	   
	$user = $service->userinfo->get();

        $redirect_uri = 'http://' . $_SERVER['HTTP_HOST'] . "/?weloggedin=1&email=$user->email";   // Here we pass user's email to the redirect URL 
  	header('Location: ' . filter_var($redirect_uri, FILTER_SANITIZE_URL));

	exit;

      }


  • on the client side, add the following jQuery code:
     
    $( "#login_google" ).click( function()    // id of the button associated with login via Google
    {
       my_google_call();

     });   

     function my_google_call() {
      $.ajax({
       type: 'GET',
       datatype: "html",
       url:'oauth2.php',           // location of the above .php code
     })
      .done( function(data)
       {
	  window.location.href = data;
       })
       .fail ( function()
       {
	 messagebox( { icon: "toast.png",
                       text: "There was an error!",
                       buttons : [ { id : "ok", label : "OK" } ] });
	 return;
       });
     }

     // PARSE URL ARGUMENTS
     urlparams = function( sParam ) {
       var sURLVariables = window.location.search.substring(1).split('&');
       for (var i = 0; i < sURLVariables.length; i++) {
         var sParameterName = sURLVariables[i].split('=');
         if (sParameterName[0] == sParam) {
           return sParameterName[1];
         }
       }
     }
     
     if (urlparams("weloggedin")){
       messagebox( { icon: "toast.png",
                       text: ga.urlparams("email") ? ("We logged in, Email is: " + ga.urlparams("email")) : "We logged in, No Email",
                       buttons : [ { id : "ok", label : "OK" } ] });
     }


     window.history.replaceState({},"MyWebSite","/myweb/");   // clear URL from user's data [title and application are assumed to be 'MyWebSite' and 'myweb', respectively]

Globus's OAuth2 API

See documentaion at https://docs.globus.org/api/auth/developer-guide

  • To register application, compete the following steps:
    • Navigate to https://developers.globus.org, click 'Register your App with Globus'
    • Use your credentials to Log in [select organization from the drop down menu]
    • Add a project
  • Create a oauth2.php file with the following content:
<?php

session_start();
	
$client_id = 'XXXX';                        // from Globus's API console for your registered app
$client_secret = 'XXXXXXXXXX';              // from Globus's API console for your registered app
$redirect_uri = '/path/to/oauth2.php';      // the link your app will be redirected to after authorization (to this .php file)
$scope = 'openid+email+profile';            // scopes [to use https://auth.globus.org/v2/oauth2/userinfo endpoint]
$response_type = 'code';	 

 if (! isset($_GET['code'])) {
 $auth_url = "https://auth.globus.org/v2/oauth2/authorize?client_id=$client_id&redirect_uri=$redirect_uri&scope=$scope&response_type=$response_type";
 //header('Location: ' . filter_var($auth_url, FILTER_SANITIZE_URL));
 echo filter_var($auth_url, FILTER_SANITIZE_URL);
 }
 else 
 {
   $code = $_GET['code'];

  /// Authorization /////////////////////////////////////////////////////
   $url = 'https://auth.globus.org/v2/oauth2/token';

   $sPD = array('grant_type' => 'authorization_code', 'redirect_uri' => $redirect_uri, 'code' => $code, 'client_id' => $client_id);
 
   $options_post = array(
    'http' => array(
            'method'  => 'POST',
	    'header'  => array ('Content-type: application/x-www-form-urlencoded'
	    	      	        ,'Authorization: Basic '. base64_encode("$client_id:$client_secret")
				),   
	    'content' => http_build_query($sPD)
           )
    ); 

   $context  = stream_context_create($options_post);
   $result = file_get_contents($url, false, $context);
   $res_json = json_decode($result, true);
 
   //var_dump($result);
   //echo "<br><br>";
   //echo ($res_json['other_tokens']['0']['access_token']);     

 //////// Use access token to get Globus's user profile: v2/oauth2/userinfo endpoint /////////////////////////////////////////
  $url_token = 'https://auth.globus.org/v2/oauth2/userinfo';

  $options_use_token = array(
    'http' => array(
            'method'  => 'POST',
	    'header'  => array( 'Authorization: Bearer ' .  $res_json['access_token'] )	    
           )
  ); 

  $context_use_token  = stream_context_create($options_use_token);
  $result_use_token   = file_get_contents($url_token, false, $context_use_token);

  //echo "<br>";
  //echo "<br>";
  //var_dump ($result_use_token);

  $res_json_use_token = json_decode($result_use_token, true);

  $user_email = $res_json_use_token['email'];
  $user_name  = $res_json_use_token['name'];
  $sub_id     = $res_json_use_token['sub'];

 ///// Use access token to get user identities: v2/api/identities/<id> endpoint ////////////////////////////////////

  $url_token_id = "https://auth.globus.org/v2/api/identities/" . "$sub_id";

  $options_use_token_id = array(
    'http' => array(
            'method'  => 'GET',
	    'header'  => array( 'Authorization: Bearer ' .  $res_json['access_token'] )	    
           )
  ); 

  $context_use_token_id  = stream_context_create($options_use_token_id);
  $result_use_token_id   = file_get_contents($url_token_id, false, $context_use_token_id);

  //echo "<br>";
  //echo "<br>";
  //var_dump ($result_use_token_id);

  $res_json_use_token_id = json_decode($result_use_token_id, true);

  $user_username = $res_json_use_token_id['identity']['username'];
  $user_username_split = explode("@", $user_username);
  //echo ( $user_username_split[0] );

   
  $redirect_uri = 'http://localhost/mywebtraning'. "/?weloggedinglobus=1&email=$user_email&name=$user_name&username=$user_username_split[0]";
  //Pass user info into the redirect uri for further processing on the client side

  header('Location: ' . filter_var($redirect_uri, FILTER_SANITIZE_URL));

}

Use with Genapp applications

To enable Oauth2 authrization via Google and Globus API, the following sections have to be added to directives.json and appconfig.json files:

  • directives.json
       "usesplash" : "true"
       
       ,"register" : {
              "globuslogin"  : "true"   
             ,"googlelogin"  : "true"
        }
    
    
  • appconfig.json
          "oauth2" : { 
                       "globus" : {
    	                         "client_id"     : "XXXX" 
    	                        ,"client_secret" : "XXXXXXXX"  
                                  }
                      ,"google" : {
    	                         "client_id"     : "XXXXXXXX"
    	                        ,"client_secret" : "XXXXXXXXXXXX"
                                   }
                      }
    

where 'client_id' and 'client_secret' are credentials of the application registered with Globus or Google.

Disable Regular Login & Registration

When Oauth2 authorization via Google and Globus API is used, there may be a need to disable (hide) regular login/registration. To do so, just add the following line into appconfig.json or directives.json:

     "hideregularlogin" : "true"

Specify Globus sources to login/register with

in appconfig.json the "only" key word is responsible for this:

      "oauth2" : { 
                   "only"   : [xsede.org, ...], 
                   "globus" : {
	                         "client_id"     : "XXXX" 
	                        ,"client_secret" : "XXXXXXXX"  
                              }
                  ,"google" : {
	                         "client_id"     : "XXXXXXXX"
	                        ,"client_secret" : "XXXXXXXXXXXX"
                               }
                  }

Stripping the domain name from username

in appconfig.json use "stripdomain" key word:

      "oauth2" : { 
                   "stripdomain" : "true",  
                   "only"   : [xsede.org, ...], 
                   "globus" : {
	                         "client_id"     : "XXXX" 
	                        ,"client_secret" : "XXXXXXXX"  
                              }
                  ,"google" : {
	                         "client_id"     : "XXXXXXXX"
	                        ,"client_secret" : "XXXXXXXXXXXX"
                               }
                  }

Specifying https vs http in the web address

in appconfig.json, to specify https use "use_https" key word:

      "oauth2" : { 
                   "use_https"   : "true",
                   "stripdomain" : "true",  
                   "only"   : [xsede.org, ...], 
                   "globus" : {
	                         "client_id"     : "XXXX" 
	                        ,"client_secret" : "XXXXXXXX"  
                              }
                  ,"google" : {
	                         "client_id"     : "XXXXXXXX"
	                        ,"client_secret" : "XXXXXXXXXXXX"
                               }
                  }

Otherwise, for http pages do not use "use_https".

Last modified 17 months ago Last modified on Mar 9, 2017, 9:38:45 AM