From b0e87f29e7be1f348aa6077084cb48b76e6b0c58 Mon Sep 17 00:00:00 2001
From: Pascal Seeland <pascal.seeland@tik.uni-stuttgart.de>
Date: Tue, 29 Aug 2023 14:46:38 +0200
Subject: [PATCH] Fix OIDC logout and set flow to code mode

---
 .../class.ilAuthProviderOpenIdConnect.php     | 45 +++++++++----------
 1 file changed, 20 insertions(+), 25 deletions(-)

diff --git a/Services/OpenIdConnect/classes/class.ilAuthProviderOpenIdConnect.php b/Services/OpenIdConnect/classes/class.ilAuthProviderOpenIdConnect.php
index 296d81a416b0..eaf3f9063432 100644
--- a/Services/OpenIdConnect/classes/class.ilAuthProviderOpenIdConnect.php
+++ b/Services/OpenIdConnect/classes/class.ilAuthProviderOpenIdConnect.php
@@ -1,7 +1,5 @@
 <?php
 
-declare(strict_types=1);
-
 /**
  * This file is part of ILIAS, a powerful learning management system
  * published by ILIAS open source e-Learning e.V.
@@ -18,6 +16,8 @@
  *
  *********************************************************************/
 
+declare(strict_types=1);
+
 use Jumbojett\OpenIDConnectClient;
 
 /**
@@ -26,6 +26,7 @@
  */
 class ilAuthProviderOpenIdConnect extends ilAuthProvider
 {
+    private const OIDC_AUTH_IDTOKEN = "oidc_auth_idtoken";
     private ilOpenIdConnectSettings $settings;
     /** @var array $body */
     private $body;
@@ -50,16 +51,21 @@ public function handleLogout(): void
             return;
         }
 
-        $auth_token = ilSession::get('oidc_auth_token');
-        $this->logger->debug('Using token: ' . $auth_token);
+        $id_token = ilSession::get(self::OIDC_AUTH_IDTOKEN);
+        $this->logger->debug('Logging out with token: ' . $id_token);
 
-        if (isset($auth_token) && $auth_token !== '') {
-            ilSession::set('oidc_auth_token', '');
+        if (isset($id_token) && $id_token !== '') {
+            ilSession::set(self::OIDC_AUTH_IDTOKEN, '');
             $oidc = $this->initClient();
-            $oidc->signOut(
-                $auth_token,
-                ILIAS_HTTP_PATH . '/logout.php'
-            );
+            try {
+                $oidc->signOut(
+                    $id_token,
+                    ILIAS_HTTP_PATH . '/logout.php'
+                );
+            } catch (\Jumbojett\OpenIDConnectClientException $e) {
+                $this->logger->warning("Logging out of OIDC provider failed with: " . $e->getMessage());
+            }
+
         }
     }
 
@@ -84,36 +90,25 @@ public function doAuthentication(ilAuthStatus $status): bool
                 $oidc->getRedirectURL()
             );
 
-            $oidc->setResponseTypes(
-                [
-                    'id_token'
-                ]
-            );
-
-
             $oidc->addScope($this->settings->getAllScopes());
-            $oidc->addAuthParam(['response_mode' => 'form_post']);
             if ($this->settings->getLoginPromptType() === ilOpenIdConnectSettings::LOGIN_ENFORCE) {
                 $oidc->addAuthParam(['prompt' => 'login']);
             }
-            $oidc->setAllowImplicitFlow(true);
 
             $oidc->authenticate();
             // user is authenticated, otherwise redirected to authorization endpoint or exception
             $this->logger->dump($this->body, ilLogLevel::DEBUG);
 
-            $claims = $oidc->getVerifiedClaims(null);
+            $claims = $oidc->requestUserInfo();
             $this->logger->dump($claims, ilLogLevel::DEBUG);
             $status = $this->handleUpdate($status, $claims);
 
             // @todo : provide a general solution for all authentication methods
             //$_GET['target'] = $this->getCredentials()->getRedirectionTarget();// TODO PHP8-REVIEW Please eliminate this. Mutating the request is not allowed and will not work in ILIAS 8.
 
-            //TODO fix this. There is a PR and it is broken in 7 as well
-            //if ($this->settings->getLogoutScope() === ilOpenIdConnectSettings::LOGOUT_SCOPE_GLOBAL) {
-            //$token = $oidc->requestClientCredentialsToken();
-            //ilSession::set('oidc_auth_token', $token->access_token);
-            //}
+            if ($this->settings->getLogoutScope() === ilOpenIdConnectSettings::LOGOUT_SCOPE_GLOBAL) {
+                ilSession::set(self::OIDC_AUTH_IDTOKEN, $oidc->getIdToken());
+            }
             return true;
         } catch (Exception $e) {
             $this->logger->warning($e->getMessage());