[ Index ]

PHP Cross Reference of phpBB-3.2.8-deutsch

title

Body

[close]

/phpbb/auth/provider/oauth/ -> oauth.php (source)

   1  <?php
   2  /**
   3  *
   4  * This file is part of the phpBB Forum Software package.
   5  *
   6  * @copyright (c) phpBB Limited <https://www.phpbb.com>
   7  * @license GNU General Public License, version 2 (GPL-2.0)
   8  *
   9  * For full copyright and license information, please see
  10  * the docs/CREDITS.txt file.
  11  *
  12  */
  13  
  14  namespace phpbb\auth\provider\oauth;
  15  
  16  use OAuth\Common\Consumer\Credentials;
  17  
  18  /**
  19  * OAuth authentication provider for phpBB3
  20  */
  21  class oauth extends \phpbb\auth\provider\base
  22  {
  23      /**
  24      * Database driver
  25      *
  26      * @var \phpbb\db\driver\driver_interface
  27      */
  28      protected $db;
  29  
  30      /**
  31      * phpBB config
  32      *
  33      * @var \phpbb\config\config
  34      */
  35      protected $config;
  36  
  37      /**
  38      * phpBB passwords manager
  39      *
  40      * @var \phpbb\passwords\manager
  41      */
  42      protected $passwords_manager;
  43  
  44      /**
  45      * phpBB request object
  46      *
  47      * @var \phpbb\request\request_interface
  48      */
  49      protected $request;
  50  
  51      /**
  52      * phpBB user
  53      *
  54      * @var \phpbb\user
  55      */
  56      protected $user;
  57  
  58      /**
  59      * OAuth token table
  60      *
  61      * @var string
  62      */
  63      protected $auth_provider_oauth_token_storage_table;
  64  
  65      /**
  66      * OAuth state table
  67      *
  68      * @var string
  69      */
  70      protected $auth_provider_oauth_state_table;
  71  
  72      /**
  73      * OAuth account association table
  74      *
  75      * @var string
  76      */
  77      protected $auth_provider_oauth_token_account_assoc;
  78  
  79      /**
  80      * All OAuth service providers
  81      *
  82      * @var \phpbb\di\service_collection Contains \phpbb\auth\provider\oauth\service_interface
  83      */
  84      protected $service_providers;
  85  
  86      /**
  87      * Users table
  88      *
  89      * @var string
  90      */
  91      protected $users_table;
  92  
  93      /**
  94      * Cached current uri object
  95      *
  96      * @var \OAuth\Common\Http\Uri\UriInterface|null
  97      */
  98      protected $current_uri;
  99  
 100      /**
 101      * DI container
 102      *
 103      * @var \Symfony\Component\DependencyInjection\ContainerInterface
 104      */
 105      protected $phpbb_container;
 106  
 107      /**
 108      * phpBB event dispatcher
 109      *
 110      * @var \phpbb\event\dispatcher_interface
 111      */
 112      protected $dispatcher;
 113  
 114      /**
 115      * phpBB root path
 116      *
 117      * @var string
 118      */
 119      protected $phpbb_root_path;
 120  
 121      /**
 122      * PHP file extension
 123      *
 124      * @var string
 125      */
 126      protected $php_ext;
 127  
 128      /**
 129      * OAuth Authentication Constructor
 130      *
 131      * @param    \phpbb\db\driver\driver_interface    $db
 132      * @param    \phpbb\config\config    $config
 133      * @param    \phpbb\passwords\manager    $passwords_manager
 134      * @param    \phpbb\request\request_interface    $request
 135      * @param    \phpbb\user        $user
 136      * @param    string            $auth_provider_oauth_token_storage_table
 137      * @param    string            $auth_provider_oauth_state_table
 138      * @param    string            $auth_provider_oauth_token_account_assoc
 139      * @param    \phpbb\di\service_collection    $service_providers Contains \phpbb\auth\provider\oauth\service_interface
 140      * @param    string            $users_table
 141      * @param    \Symfony\Component\DependencyInjection\ContainerInterface $phpbb_container DI container
 142      * @param    \phpbb\event\dispatcher_interface $dispatcher phpBB event dispatcher
 143      * @param    string            $phpbb_root_path
 144      * @param    string            $php_ext
 145      */
 146  	public function __construct(\phpbb\db\driver\driver_interface $db, \phpbb\config\config $config, \phpbb\passwords\manager $passwords_manager, \phpbb\request\request_interface $request, \phpbb\user $user, $auth_provider_oauth_token_storage_table, $auth_provider_oauth_state_table, $auth_provider_oauth_token_account_assoc, \phpbb\di\service_collection $service_providers, $users_table, \Symfony\Component\DependencyInjection\ContainerInterface $phpbb_container, \phpbb\event\dispatcher_interface $dispatcher, $phpbb_root_path, $php_ext)
 147      {
 148          $this->db = $db;
 149          $this->config = $config;
 150          $this->passwords_manager = $passwords_manager;
 151          $this->request = $request;
 152          $this->user = $user;
 153          $this->auth_provider_oauth_token_storage_table = $auth_provider_oauth_token_storage_table;
 154          $this->auth_provider_oauth_state_table = $auth_provider_oauth_state_table;
 155          $this->auth_provider_oauth_token_account_assoc = $auth_provider_oauth_token_account_assoc;
 156          $this->service_providers = $service_providers;
 157          $this->users_table = $users_table;
 158          $this->phpbb_container = $phpbb_container;
 159          $this->dispatcher = $dispatcher;
 160          $this->phpbb_root_path = $phpbb_root_path;
 161          $this->php_ext = $php_ext;
 162      }
 163  
 164      /**
 165      * {@inheritdoc}
 166      */
 167  	public function init()
 168      {
 169          // This does not test whether or not the key and secret provided are valid.
 170          foreach ($this->service_providers as $service_provider)
 171          {
 172              $credentials = $service_provider->get_service_credentials();
 173  
 174              if (($credentials['key'] && !$credentials['secret']) || (!$credentials['key'] && $credentials['secret']))
 175              {
 176                  return $this->user->lang['AUTH_PROVIDER_OAUTH_ERROR_ELEMENT_MISSING'];
 177              }
 178          }
 179          return false;
 180      }
 181  
 182      /**
 183      * {@inheritdoc}
 184      */
 185  	public function login($username, $password)
 186      {
 187          // Temporary workaround for only having one authentication provider available
 188          if (!$this->request->is_set('oauth_service'))
 189          {
 190              $provider = new \phpbb\auth\provider\db($this->db, $this->config, $this->passwords_manager, $this->request, $this->user, $this->phpbb_container, $this->phpbb_root_path, $this->php_ext);
 191              return $provider->login($username, $password);
 192          }
 193  
 194          // Request the name of the OAuth service
 195          $service_name_original = $this->request->variable('oauth_service', '', false);
 196          $service_name = 'auth.provider.oauth.service.' . strtolower($service_name_original);
 197          if ($service_name_original === '' || !array_key_exists($service_name, $this->service_providers))
 198          {
 199              return array(
 200                  'status'        => LOGIN_ERROR_EXTERNAL_AUTH,
 201                  'error_msg'        => 'LOGIN_ERROR_OAUTH_SERVICE_DOES_NOT_EXIST',
 202                  'user_row'        => array('user_id' => ANONYMOUS),
 203              );
 204          }
 205  
 206          // Get the service credentials for the given service
 207          $service_credentials = $this->service_providers[$service_name]->get_service_credentials();
 208  
 209          $storage = new \phpbb\auth\provider\oauth\token_storage($this->db, $this->user, $this->auth_provider_oauth_token_storage_table, $this->auth_provider_oauth_state_table);
 210          $query = 'mode=login&login=external&oauth_service=' . $service_name_original;
 211          $service = $this->get_service($service_name_original, $storage, $service_credentials, $query, $this->service_providers[$service_name]->get_auth_scope());
 212  
 213          if (($service::OAUTH_VERSION === 2 && $this->request->is_set('code', \phpbb\request\request_interface::GET))
 214              || ($service::OAUTH_VERSION === 1 && $this->request->is_set('oauth_token', \phpbb\request\request_interface::GET)))
 215          {
 216              $this->service_providers[$service_name]->set_external_service_provider($service);
 217              $unique_id = $this->service_providers[$service_name]->perform_auth_login();
 218  
 219              // Check to see if this provider is already assosciated with an account
 220              $data = array(
 221                  'provider'    => $service_name_original,
 222                  'oauth_provider_id'    => $unique_id
 223              );
 224  
 225              $sql = 'SELECT user_id FROM ' . $this->auth_provider_oauth_token_account_assoc . '
 226                  WHERE ' . $this->db->sql_build_array('SELECT', $data);
 227              $result = $this->db->sql_query($sql);
 228              $row = $this->db->sql_fetchrow($result);
 229              $this->db->sql_freeresult($result);
 230  
 231              $redirect_data = array(
 232                  'auth_provider'                => 'oauth',
 233                  'login_link_oauth_service'    => $service_name_original,
 234              );
 235  
 236              /**
 237              * Event is triggered before check if provider is already associated with an account
 238              *
 239              * @event core.oauth_login_after_check_if_provider_id_has_match
 240              * @var    array                                    row                User row
 241              * @var    array                                    data            Provider data
 242              * @var    array                                    redirect_data    Data to be appended to the redirect url
 243              * @var    \OAuth\Common\Service\ServiceInterface    service            OAuth service
 244              * @since 3.2.3-RC1
 245              * @changed 3.2.6-RC1 Added redirect_data
 246              */
 247              $vars = array(
 248                  'row',
 249                  'data',
 250                  'redirect_data',
 251                  'service',
 252              );
 253              extract($this->dispatcher->trigger_event('core.oauth_login_after_check_if_provider_id_has_match', compact($vars)));
 254  
 255              if (!$row)
 256              {
 257                  // The user does not yet exist, ask to link or create profile
 258                  return array(
 259                      'status'        => LOGIN_SUCCESS_LINK_PROFILE,
 260                      'error_msg'        => 'LOGIN_OAUTH_ACCOUNT_NOT_LINKED',
 261                      'user_row'        => array(),
 262                      'redirect_data'    => $redirect_data,
 263                  );
 264              }
 265  
 266              // Retrieve the user's account
 267              $sql = 'SELECT user_id, username, user_password, user_passchg, user_email, user_ip, user_type, user_login_attempts
 268                  FROM ' . $this->users_table . '
 269                      WHERE user_id = ' . (int) $row['user_id'];
 270              $result = $this->db->sql_query($sql);
 271              $row = $this->db->sql_fetchrow($result);
 272              $this->db->sql_freeresult($result);
 273  
 274              if (!$row)
 275              {
 276                  throw new \Exception('AUTH_PROVIDER_OAUTH_ERROR_INVALID_ENTRY');
 277              }
 278  
 279              /**
 280               * Check if the user is banned.
 281               * The fourth parameter, return, has to be true,
 282               * otherwise the OAuth login is still called and
 283               * an uncaught exception is thrown as there is no
 284               * token stored in the database.
 285               */
 286              $ban = $this->user->check_ban($row['user_id'], $row['user_ip'], $row['user_email'], true);
 287              if (!empty($ban))
 288              {
 289                  $till_date = !empty($ban['ban_end']) ? $this->user->format_date($ban['ban_end']) : '';
 290                  $message = !empty($ban['ban_end']) ? 'BOARD_BAN_TIME' : 'BOARD_BAN_PERM';
 291  
 292                  $contact_link = phpbb_get_board_contact_link($this->config, $this->phpbb_root_path, $this->php_ext);
 293                  $message = $this->user->lang($message, $till_date, '<a href="' . $contact_link . '">', '</a>');
 294                  $message .= !empty($ban['ban_give_reason']) ? '<br /><br />' . $this->user->lang('BOARD_BAN_REASON', $ban['ban_give_reason']) : '';
 295                  $message .= !empty($ban['ban_triggered_by']) ? '<br /><br /><em>' . $this->user->lang('BAN_TRIGGERED_BY_' . strtoupper($ban['ban_triggered_by'])) . '</em>' : '';
 296  
 297                  return array(
 298                      'status'    => LOGIN_BREAK,
 299                      'error_msg'    => $message,
 300                      'user_row'    => $row,
 301                  );
 302              }
 303  
 304              // Update token storage to store the user_id
 305              $storage->set_user_id($row['user_id']);
 306  
 307              /**
 308              * Event is triggered after user is successfully logged in via OAuth.
 309              *
 310              * @event core.auth_oauth_login_after
 311              * @var    array    row    User row
 312              * @since 3.1.11-RC1
 313              */
 314              $vars = array(
 315                  'row',
 316              );
 317              extract($this->dispatcher->trigger_event('core.auth_oauth_login_after', compact($vars)));
 318  
 319              // The user is now authenticated and can be logged in
 320              return array(
 321                  'status'        => LOGIN_SUCCESS,
 322                  'error_msg'        => false,
 323                  'user_row'        => $row,
 324              );
 325          }
 326          else
 327          {
 328              if ($service::OAUTH_VERSION === 1)
 329              {
 330                  $token = $service->requestRequestToken();
 331                  $url = $service->getAuthorizationUri(array('oauth_token' => $token->getRequestToken()));
 332              }
 333              else
 334              {
 335                  $url = $service->getAuthorizationUri();
 336              }
 337              header('Location: ' . $url);
 338          }
 339      }
 340  
 341      /**
 342      * Returns the cached current_uri object or creates and caches it if it is
 343      * not already created. In each case the query string is updated based on
 344      * the $query parameter.
 345      *
 346      * @param    string    $service_name    The name of the service
 347      * @param    string    $query            The query string of the current_uri
 348      *                                    used in redirects
 349      * @return    \OAuth\Common\Http\Uri\UriInterface
 350      */
 351  	protected function get_current_uri($service_name, $query)
 352      {
 353          if ($this->current_uri)
 354          {
 355              $this->current_uri->setQuery($query);
 356              return $this->current_uri;
 357          }
 358  
 359          $uri_factory = new \OAuth\Common\Http\Uri\UriFactory();
 360          $super_globals = $this->request->get_super_global(\phpbb\request\request_interface::SERVER);
 361          if (!empty($super_globals['HTTP_X_FORWARDED_PROTO']) && $super_globals['HTTP_X_FORWARDED_PROTO'] === 'https')
 362          {
 363              $super_globals['HTTPS'] = 'on';
 364              $super_globals['SERVER_PORT'] = 443;
 365          }
 366          $current_uri = $uri_factory->createFromSuperGlobalArray($super_globals);
 367          $current_uri->setQuery($query);
 368  
 369          $this->current_uri = $current_uri;
 370          return $current_uri;
 371      }
 372  
 373      /**
 374      * Returns a new service object
 375      *
 376      * @param    string    $service_name            The name of the service
 377      * @param    \phpbb\auth\provider\oauth\token_storage $storage
 378      * @param    array    $service_credentials    {@see \phpbb\auth\provider\oauth\oauth::get_service_credentials}
 379      * @param    string    $query                    The query string of the
 380      *                                            current_uri used in redirection
 381      * @param    array    $scopes                    The scope of the request against
 382      *                                            the api.
 383      * @return    \OAuth\Common\Service\ServiceInterface
 384      * @throws    \Exception
 385      */
 386  	protected function get_service($service_name, \phpbb\auth\provider\oauth\token_storage $storage, array $service_credentials, $query, array $scopes = array())
 387      {
 388          $current_uri = $this->get_current_uri($service_name, $query);
 389  
 390          // Setup the credentials for the requests
 391          $credentials = new Credentials(
 392              $service_credentials['key'],
 393              $service_credentials['secret'],
 394              $current_uri->getAbsoluteUri()
 395          );
 396  
 397          $service_factory = new \OAuth\ServiceFactory();
 398          $service = $service_factory->createService($service_name, $credentials, $storage, $scopes);
 399  
 400          if (!$service)
 401          {
 402              throw new \Exception('AUTH_PROVIDER_OAUTH_ERROR_SERVICE_NOT_CREATED');
 403          }
 404  
 405          return $service;
 406      }
 407  
 408      /**
 409      * {@inheritdoc}
 410      */
 411  	public function get_login_data()
 412      {
 413          $login_data = array(
 414              'TEMPLATE_FILE'        => 'login_body_oauth.html',
 415              'BLOCK_VAR_NAME'    => 'oauth',
 416              'BLOCK_VARS'        => array(),
 417          );
 418  
 419          foreach ($this->service_providers as $service_name => $service_provider)
 420          {
 421              // Only include data if the credentials are set
 422              $credentials = $service_provider->get_service_credentials();
 423              if ($credentials['key'] && $credentials['secret'])
 424              {
 425                  $actual_name = str_replace('auth.provider.oauth.service.', '', $service_name);
 426                  $redirect_url = generate_board_url() . '/ucp.' . $this->php_ext . '?mode=login&login=external&oauth_service=' . $actual_name;
 427                  $login_data['BLOCK_VARS'][$service_name] = array(
 428                      'REDIRECT_URL'    => redirect($redirect_url, true),
 429                      'SERVICE_NAME'    => $this->user->lang['AUTH_PROVIDER_OAUTH_SERVICE_' . strtoupper($actual_name)],
 430                  );
 431              }
 432          }
 433  
 434          return $login_data;
 435      }
 436  
 437      /**
 438      * {@inheritdoc}
 439      */
 440  	public function acp()
 441      {
 442          $ret = array();
 443  
 444          foreach ($this->service_providers as $service_name => $service_provider)
 445          {
 446              $actual_name = str_replace('auth.provider.oauth.service.', '', $service_name);
 447              $ret[] = 'auth_oauth_' . $actual_name . '_key';
 448              $ret[] = 'auth_oauth_' . $actual_name . '_secret';
 449          }
 450  
 451          return $ret;
 452      }
 453  
 454      /**
 455      * {@inheritdoc}
 456      */
 457  	public function get_acp_template($new_config)
 458      {
 459          $ret = array(
 460              'BLOCK_VAR_NAME'    => 'oauth_services',
 461              'BLOCK_VARS'        => array(),
 462              'TEMPLATE_FILE'        => 'auth_provider_oauth.html',
 463              'TEMPLATE_VARS'        => array(),
 464          );
 465  
 466          foreach ($this->service_providers as $service_name => $service_provider)
 467          {
 468              $actual_name = str_replace('auth.provider.oauth.service.', '', $service_name);
 469              $ret['BLOCK_VARS'][$actual_name] = array(
 470                  'ACTUAL_NAME'    => $this->user->lang['AUTH_PROVIDER_OAUTH_SERVICE_' . strtoupper($actual_name)],
 471                  'KEY'            => $new_config['auth_oauth_' . $actual_name . '_key'],
 472                  'NAME'            => $actual_name,
 473                  'SECRET'        => $new_config['auth_oauth_' . $actual_name . '_secret'],
 474              );
 475          }
 476  
 477          return $ret;
 478      }
 479  
 480      /**
 481      * {@inheritdoc}
 482      */
 483  	public function login_link_has_necessary_data($login_link_data)
 484      {
 485          if (empty($login_link_data))
 486          {
 487              return 'LOGIN_LINK_NO_DATA_PROVIDED';
 488          }
 489  
 490          if (!array_key_exists('oauth_service', $login_link_data) || !$login_link_data['oauth_service'] ||
 491              !array_key_exists('link_method', $login_link_data) || !$login_link_data['link_method'])
 492          {
 493              return 'LOGIN_LINK_MISSING_DATA';
 494          }
 495  
 496          return null;
 497      }
 498  
 499      /**
 500      * {@inheritdoc}
 501      */
 502  	public function link_account(array $link_data)
 503      {
 504          // Check for a valid link method (auth_link or login_link)
 505          if (!array_key_exists('link_method', $link_data) ||
 506              !in_array($link_data['link_method'], array(
 507                  'auth_link',
 508                  'login_link',
 509              )))
 510          {
 511              return 'LOGIN_LINK_MISSING_DATA';
 512          }
 513  
 514          // We must have an oauth_service listed, check for it two ways
 515          if (!array_key_exists('oauth_service', $link_data) || !$link_data['oauth_service'])
 516          {
 517              $link_data['oauth_service'] = $this->request->variable('oauth_service', '');
 518  
 519              if (!$link_data['oauth_service'])
 520              {
 521                  return 'LOGIN_LINK_MISSING_DATA';
 522              }
 523          }
 524  
 525          $service_name = 'auth.provider.oauth.service.' . strtolower($link_data['oauth_service']);
 526          if (!array_key_exists($service_name, $this->service_providers))
 527          {
 528              return 'LOGIN_ERROR_OAUTH_SERVICE_DOES_NOT_EXIST';
 529          }
 530  
 531          switch ($link_data['link_method'])
 532          {
 533              case 'auth_link':
 534                  return $this->link_account_auth_link($link_data, $service_name);
 535              case 'login_link':
 536                  return $this->link_account_login_link($link_data, $service_name);
 537          }
 538      }
 539  
 540      /**
 541      * Performs the account linking for login_link
 542      *
 543      * @param    array    $link_data        The same variable given to {@see \phpbb\auth\provider\provider_interface::link_account}
 544      * @param    string    $service_name    The name of the service being used in
 545      *                                    linking.
 546      * @return    string|null    Returns a language constant (string) if an error is
 547      *                        encountered, or null on success.
 548      */
 549  	protected function link_account_login_link(array $link_data, $service_name)
 550      {
 551          $storage = new \phpbb\auth\provider\oauth\token_storage($this->db, $this->user, $this->auth_provider_oauth_token_storage_table, $this->auth_provider_oauth_state_table);
 552  
 553          // Check for an access token, they should have one
 554          if (!$storage->has_access_token_by_session($service_name))
 555          {
 556              return 'LOGIN_LINK_ERROR_OAUTH_NO_ACCESS_TOKEN';
 557          }
 558  
 559          // Prepare the query string
 560          $query = 'mode=login_link&login_link_oauth_service=' . strtolower($link_data['oauth_service']);
 561  
 562          // Prepare for an authentication request
 563          $service_credentials = $this->service_providers[$service_name]->get_service_credentials();
 564          $scopes = $this->service_providers[$service_name]->get_auth_scope();
 565          $service = $this->get_service(strtolower($link_data['oauth_service']), $storage, $service_credentials, $query, $scopes);
 566          $this->service_providers[$service_name]->set_external_service_provider($service);
 567  
 568          // The user has already authenticated successfully, request to authenticate again
 569          $unique_id = $this->service_providers[$service_name]->perform_token_auth();
 570  
 571          // Insert into table, they will be able to log in after this
 572          $data = array(
 573              'user_id'            => $link_data['user_id'],
 574              'provider'            => strtolower($link_data['oauth_service']),
 575              'oauth_provider_id'    => $unique_id,
 576          );
 577  
 578          $this->link_account_perform_link($data);
 579          // Update token storage to store the user_id
 580          $storage->set_user_id($link_data['user_id']);
 581      }
 582  
 583      /**
 584      * Performs the account linking for auth_link
 585      *
 586      * @param    array    $link_data        The same variable given to {@see \phpbb\auth\provider\provider_interface::link_account}
 587      * @param    string    $service_name    The name of the service being used in
 588      *                                    linking.
 589      * @return    string|null    Returns a language constant (string) if an error is
 590      *                        encountered, or null on success.
 591      */
 592  	protected function link_account_auth_link(array $link_data, $service_name)
 593      {
 594          $storage = new \phpbb\auth\provider\oauth\token_storage($this->db, $this->user, $this->auth_provider_oauth_token_storage_table, $this->auth_provider_oauth_state_table);
 595          $query = 'i=ucp_auth_link&mode=auth_link&link=1&oauth_service=' . strtolower($link_data['oauth_service']);
 596          $service_credentials = $this->service_providers[$service_name]->get_service_credentials();
 597          $scopes = $this->service_providers[$service_name]->get_auth_scope();
 598          $service = $this->get_service(strtolower($link_data['oauth_service']), $storage, $service_credentials, $query, $scopes);
 599  
 600          if (($service::OAUTH_VERSION === 2 && $this->request->is_set('code', \phpbb\request\request_interface::GET))
 601              || ($service::OAUTH_VERSION === 1 && $this->request->is_set('oauth_token', \phpbb\request\request_interface::GET)))
 602          {
 603              $this->service_providers[$service_name]->set_external_service_provider($service);
 604              $unique_id = $this->service_providers[$service_name]->perform_auth_login();
 605  
 606              // Insert into table, they will be able to log in after this
 607              $data = array(
 608                  'user_id'            => $this->user->data['user_id'],
 609                  'provider'            => strtolower($link_data['oauth_service']),
 610                  'oauth_provider_id'    => $unique_id,
 611              );
 612  
 613              $this->link_account_perform_link($data);
 614          }
 615          else
 616          {
 617              if ($service::OAUTH_VERSION === 1)
 618              {
 619                  $token = $service->requestRequestToken();
 620                  $url = $service->getAuthorizationUri(array('oauth_token' => $token->getRequestToken()));
 621              }
 622              else
 623              {
 624                  $url = $service->getAuthorizationUri();
 625              }
 626              header('Location: ' . $url);
 627          }
 628      }
 629  
 630      /**
 631      * Performs the query that inserts an account link
 632      *
 633      * @param    array    $data    This array is passed to db->sql_build_array
 634      */
 635  	protected function link_account_perform_link(array $data)
 636      {
 637          // Check if the external account is already associated with other user
 638          $sql = 'SELECT user_id
 639              FROM ' . $this->auth_provider_oauth_token_account_assoc . "
 640              WHERE provider = '" . $this->db->sql_escape($data['provider']) . "'
 641                  AND oauth_provider_id = '" . $this->db->sql_escape($data['oauth_provider_id']) . "'";
 642          $result = $this->db->sql_query($sql);
 643          $row = $this->db->sql_fetchrow($result);
 644          $this->db->sql_freeresult($result);
 645  
 646          if ($row)
 647          {
 648              trigger_error('AUTH_PROVIDER_OAUTH_ERROR_ALREADY_LINKED');
 649          }
 650  
 651          // Link account
 652          $sql = 'INSERT INTO ' . $this->auth_provider_oauth_token_account_assoc . '
 653              ' . $this->db->sql_build_array('INSERT', $data);
 654          $this->db->sql_query($sql);
 655  
 656          /**
 657           * Event is triggered after user links account.
 658           *
 659           * @event core.auth_oauth_link_after
 660           * @var    array    data    User row
 661           * @since 3.1.11-RC1
 662           */
 663          $vars = array(
 664              'data',
 665          );
 666          extract($this->dispatcher->trigger_event('core.auth_oauth_link_after', compact($vars)));
 667      }
 668  
 669      /**
 670      * {@inheritdoc}
 671      */
 672  	public function logout($data, $new_session)
 673      {
 674          // Clear all tokens belonging to the user
 675          $storage = new \phpbb\auth\provider\oauth\token_storage($this->db, $this->user, $this->auth_provider_oauth_token_storage_table, $this->auth_provider_oauth_state_table);
 676          $storage->clearAllTokens();
 677  
 678          return;
 679      }
 680  
 681      /**
 682      * {@inheritdoc}
 683      */
 684  	public function get_auth_link_data($user_id = 0)
 685      {
 686          $block_vars = array();
 687  
 688          // Get all external accounts tied to the current user
 689          $data = array(
 690              'user_id' => ($user_id <= 0) ? (int) $this->user->data['user_id'] : (int) $user_id,
 691          );
 692          $sql = 'SELECT oauth_provider_id, provider FROM ' . $this->auth_provider_oauth_token_account_assoc . '
 693              WHERE ' . $this->db->sql_build_array('SELECT', $data);
 694          $result = $this->db->sql_query($sql);
 695          $rows = $this->db->sql_fetchrowset($result);
 696          $this->db->sql_freeresult($result);
 697  
 698          $oauth_user_ids = array();
 699  
 700          if ($rows !== false && count($rows))
 701          {
 702              foreach ($rows as $row)
 703              {
 704                  $oauth_user_ids[$row['provider']] = $row['oauth_provider_id'];
 705              }
 706          }
 707          unset($rows);
 708  
 709          foreach ($this->service_providers as $service_name => $service_provider)
 710          {
 711              // Only include data if the credentials are set
 712              $credentials = $service_provider->get_service_credentials();
 713              if ($credentials['key'] && $credentials['secret'])
 714              {
 715                  $actual_name = str_replace('auth.provider.oauth.service.', '', $service_name);
 716  
 717                  $block_vars[$service_name] = array(
 718                      'HIDDEN_FIELDS'    => array(
 719                          'link'            => (!isset($oauth_user_ids[$actual_name])),
 720                          'oauth_service' => $actual_name,
 721                      ),
 722  
 723                      'SERVICE_ID'    => $actual_name,
 724                      'SERVICE_NAME'    => $this->user->lang['AUTH_PROVIDER_OAUTH_SERVICE_' . strtoupper($actual_name)],
 725                      'UNIQUE_ID'        => (isset($oauth_user_ids[$actual_name])) ? $oauth_user_ids[$actual_name] : null,
 726                  );
 727              }
 728          }
 729  
 730          return array(
 731              'BLOCK_VAR_NAME'    => 'oauth',
 732              'BLOCK_VARS'        => $block_vars,
 733  
 734              'TEMPLATE_FILE'    => 'ucp_auth_link_oauth.html',
 735          );
 736      }
 737  
 738      /**
 739      * {@inheritdoc}
 740      */
 741  	public function unlink_account(array $link_data)
 742      {
 743          if (!array_key_exists('oauth_service', $link_data) || !$link_data['oauth_service'])
 744          {
 745              return 'LOGIN_LINK_MISSING_DATA';
 746          }
 747  
 748          // Remove user specified in $link_data if possible
 749          $user_id = isset($link_data['user_id']) ? $link_data['user_id'] : $this->user->data['user_id'];
 750  
 751          // Remove the link
 752          $sql = 'DELETE FROM ' . $this->auth_provider_oauth_token_account_assoc . "
 753              WHERE provider = '" . $this->db->sql_escape($link_data['oauth_service']) . "'
 754                  AND user_id = " . (int) $user_id;
 755          $this->db->sql_query($sql);
 756  
 757          // Clear all tokens belonging to the user on this service
 758          $service_name = 'auth.provider.oauth.service.' . strtolower($link_data['oauth_service']);
 759          $storage = new \phpbb\auth\provider\oauth\token_storage($this->db, $this->user, $this->auth_provider_oauth_token_storage_table, $this->auth_provider_oauth_state_table);
 760          $storage->clearToken($service_name);
 761      }
 762  }


Generated: Tue Apr 7 19:42:26 2020 Cross-referenced by PHPXref 0.7.1