From 946120eeeeeff8ff28d83d0ad0dd2b3e64c9d23d Mon Sep 17 00:00:00 2001 From: Sara Arjona Date: Tue, 16 Mar 2021 12:32:20 +0100 Subject: [PATCH 1/3] MDL-71119 core_badges: Initialise scopes param in backpack-connect.php The scopes parameter should be passed when creating the OAuth2 badges client. As it is an optional parameter, when it's empty, it will be initilised with the supported scopes for the backpack issuer. It will happen, for instance, when a call is done to oauth2callback.php because, as defined in RFC6749, OAuth2 authorization response only supports code and state. --- badges/backpack-connect.php | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/badges/backpack-connect.php b/badges/backpack-connect.php index cece8081605..1bcbd117e10 100644 --- a/badges/backpack-connect.php +++ b/badges/backpack-connect.php @@ -42,6 +42,10 @@ if ($persistedissuer) { $returnurl = new moodle_url('/badges/backpack-connect.php', ['action' => 'authorization', 'sesskey' => sesskey()]); + // If scope is not passed as parameter, use the issuer supported scopes. + if (empty($scope)) { + $scope = $issuer->get('scopessupported'); + } $client = new core_badges\oauth2\client($issuer, $returnurl, $scope, $externalbackpack); if ($client) { if (!$client->is_logged_in()) { From dc4a36c3b1c9adc32fb6de69d6a29d12c0e9e963 Mon Sep 17 00:00:00 2001 From: Sara Arjona Date: Tue, 16 Mar 2021 12:43:39 +0100 Subject: [PATCH 2/3] MDL-71119 core_badges: Use basicauth and remove urlencode Basic authorization header is required to get token. Besides, client id and secret shouldn't call urlencode. --- badges/classes/oauth2/client.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/badges/classes/oauth2/client.php b/badges/classes/oauth2/client.php index 575985b796d..e7bc270e481 100644 --- a/badges/classes/oauth2/client.php +++ b/badges/classes/oauth2/client.php @@ -222,6 +222,7 @@ class client extends \core\oauth2\client { $callbackurl = self::callback_url(); if ($granttype == 'authorization_code') { + $this->basicauth = true; $params = array('code' => $code, 'grant_type' => $granttype, 'redirect_uri' => $callbackurl->out(false), @@ -236,7 +237,7 @@ class client extends \core\oauth2\client { ); } if ($this->basicauth) { - $idsecret = urlencode($this->clientid) . ':' . urlencode($this->clientsecret); + $idsecret = $this->clientid . ':' . $this->clientsecret; $this->setHeader('Authorization: Basic ' . base64_encode($idsecret)); } else { $params['client_id'] = $this->clientid; From 81da134c2cd7efa9b0aa744f2e6621141e0938bc Mon Sep 17 00:00:00 2001 From: Sara Arjona Date: Wed, 14 Apr 2021 10:52:34 +0200 Subject: [PATCH 3/3] MDL-71119 core_badges: Add more information to errors Some errors raised when calling external services were ignored. Displaying this information helps to debug and find the real reasons why some action, like connecting to an external backpack, can't be done. --- badges/classes/oauth2/client.php | 6 ++++-- lang/en/error.php | 1 + 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/badges/classes/oauth2/client.php b/badges/classes/oauth2/client.php index e7bc270e481..8e635bcec03 100644 --- a/badges/classes/oauth2/client.php +++ b/badges/classes/oauth2/client.php @@ -245,11 +245,13 @@ class client extends \core\oauth2\client { } // Requests can either use http GET or POST. $response = $this->post($this->token_url(), $this->build_post_data($params)); - $r = json_decode($response); if ($this->info['http_code'] !== 200) { - throw new moodle_exception('Could not upgrade oauth token'); + $debuginfo = !empty($this->error) ? $this->error : $response; + throw new moodle_exception('oauth2refreshtokenerror', 'core_error', '', $this->info['http_code'], $debuginfo); } + $r = json_decode($response); + if (is_null($r)) { throw new moodle_exception("Could not decode JSON token response"); } diff --git a/lang/en/error.php b/lang/en/error.php index d80be302266..f0ba2c304ee 100644 --- a/lang/en/error.php +++ b/lang/en/error.php @@ -468,6 +468,7 @@ $string['notownerofkey'] = 'You are not owner of this key'; $string['nousers'] = 'No such user!'; $string['oauth1accesstoken'] = 'OAuth 1.0 error: We did not obtain the access token.'; $string['oauth1requesttoken'] = 'OAuth 1.0 error: We did not obtain the request token - the service provider may be temporarily down.'; +$string['oauth2refreshtokenerror'] = 'Could not refresh OAuth 2 token. HTTP status for remote endpoint: {$a}'; $string['onlyadmins'] = 'Only administrators can do that'; $string['onlyeditingteachers'] = 'Only editing teachers can do that'; $string['onlyeditown'] = 'You can only edit your own information';