Source for file client.php

Documentation is available at client.php

  1. <?php
  2. /**
  3.  * @package     Joomla.Platform
  4.  * @subpackage  OAuth2
  5.  *
  6.  * @copyright   Copyright (C) 2005 - 2013 Open Source Matters, Inc. All rights reserved
  7.  * @license     GNU General Public License version 2 or later; see LICENSE
  8.  */
  9.  
  10. defined('JPATH_PLATFORM'or die;
  11.  
  12. /**
  13.  * Joomla Platform class for interacting with an OAuth 2.0 server.
  14.  *
  15.  * @package     Joomla.Platform
  16.  * @subpackage  OAuth2
  17.  * @since       12.3
  18.  */
  19. {
  20.     /**
  21.      * @var    JRegistry  Options for the JOAuth2Client object.
  22.      * @since  12.3
  23.      */
  24.     protected $options;
  25.  
  26.     /**
  27.      * @var    JHttp  The HTTP client object to use in sending HTTP requests.
  28.      * @since  12.3
  29.      */
  30.     protected $http;
  31.  
  32.     /**
  33.      * @var    JInput  The input object to use in retrieving GET/POST data.
  34.      * @since  12.3
  35.      */
  36.     protected $input;
  37.  
  38.     /**
  39.      * @var    JApplicationWeb  The application object to send HTTP headers for redirects.
  40.      * @since  12.3
  41.      */
  42.     protected $application;
  43.  
  44.     /**
  45.      * Constructor.
  46.      *
  47.      * @param   JRegistry        $options      JOAuth2Client options object
  48.      * @param   JHttp            $http         The HTTP client object
  49.      * @param   JInput           $input        The input object
  50.      * @param   JApplicationWeb  $application  The application object
  51.      *
  52.      * @since   12.3
  53.      */
  54.     public function __construct(JRegistry $options nullJHttp $http nullJInput $input nullJApplicationWeb $application null)
  55.     {
  56.         $this->options = isset($options$options new JRegistry;
  57.         $this->http = isset($http$http new JHttp($this->options);
  58.         $this->input = isset($input$input JFactory::getApplication()->input;
  59.         $this->application = isset($application$application new JApplicationWeb;
  60.     }
  61.  
  62.     /**
  63.      * Get the access token or redict to the authentication URL.
  64.      *
  65.      * @return  string  The access token
  66.      *
  67.      * @since   12.3
  68.      * @throws  RuntimeException
  69.      */
  70.     public function authenticate()
  71.     {
  72.         if ($data['code'$this->input->get('code'false'raw'))
  73.         {
  74.             $data['grant_type''authorization_code';
  75.             $data['redirect_uri'$this->getOption('redirecturi');
  76.             $data['client_id'$this->getOption('clientid');
  77.             $data['client_secret'$this->getOption('clientsecret');
  78.             $response $this->http->post($this->getOption('tokenurl')$data);
  79.  
  80.             if ($response->code >= 200 && $response->code 400)
  81.             {
  82.  
  83.                 if ($response->headers['Content-Type'== 'application/json')
  84.                 {
  85.                     $token array_merge(json_decode($response->bodytrue)array('created' => time()));
  86.                 }
  87.                 else
  88.                 {
  89.                     parse_str($response->body$token);
  90.                     $token array_merge($tokenarray('created' => time()));
  91.                 }
  92.  
  93.                 $this->setToken($token);
  94.  
  95.                 return $token;
  96.             }
  97.             else
  98.             {
  99.                 throw new RuntimeException('Error code ' $response->code ' received requesting access token: ' $response->body '.');
  100.             }
  101.         }
  102.  
  103.         if ($this->getOption('sendheaders'))
  104.         {
  105.             $this->application->redirect($this->createUrl());
  106.         }
  107.         return false;
  108.     }
  109.  
  110.     /**
  111.      * Verify if the client has been authenticated
  112.      *
  113.      * @return  boolean  Is authenticated
  114.      *
  115.      * @since   12.3
  116.      */
  117.     public function isAuthenticated()
  118.     {
  119.         $token $this->getToken();
  120.  
  121.         if (!$token || !array_key_exists('access_token'$token))
  122.         {
  123.             return false;
  124.         }
  125.         elseif (array_key_exists('expires_in'$token&& $token['created'$token['expires_in'time(20)
  126.         {
  127.             return false;
  128.         }
  129.         else
  130.         {
  131.             return true;
  132.         }
  133.     }
  134.  
  135.     /**
  136.      * Create the URL for authentication.
  137.      *
  138.      * @return  JHttpResponse  The HTTP response
  139.      *
  140.      * @since   12.3
  141.      * @throws  InvalidArgumentException
  142.      */
  143.     public function createUrl()
  144.     {
  145.         if (!$this->getOption('authurl'|| !$this->getOption('clientid'))
  146.         {
  147.             throw new InvalidArgumentException('Authorization URL and client_id are required');
  148.         }
  149.  
  150.         $url $this->getOption('authurl');
  151.  
  152.         if (strpos($url'?'))
  153.         {
  154.             $url .= '&';
  155.         }
  156.         else
  157.         {
  158.             $url .= '?';
  159.         }
  160.  
  161.         $url .= 'response_type=code';
  162.         $url .= '&client_id=' urlencode($this->getOption('clientid'));
  163.  
  164.         if ($this->getOption('redirecturi'))
  165.         {
  166.             $url .= '&redirect_uri=' urlencode($this->getOption('redirecturi'));
  167.         }
  168.  
  169.         if ($this->getOption('scope'))
  170.         {
  171.             $scope is_array($this->getOption('scope')) implode(' '$this->getOption('scope')) $this->getOption('scope');
  172.             $url .= '&scope=' urlencode($scope);
  173.         }
  174.  
  175.         if ($this->getOption('state'))
  176.         {
  177.             $url .= '&state=' urlencode($this->getOption('state'));
  178.         }
  179.  
  180.         if (is_array($this->getOption('requestparams')))
  181.         {
  182.             foreach ($this->getOption('requestparams'as $key => $value)
  183.             {
  184.                 $url .= '&' $key '=' urlencode($value);
  185.             }
  186.         }
  187.  
  188.         return $url;
  189.     }
  190.  
  191.     /**
  192.      * Send a signed Oauth request.
  193.      *
  194.      * @param   string  $url      The URL forf the request.
  195.      * @param   mixed   $data     The data to include in the request
  196.      * @param   array   $headers  The headers to send with the request
  197.      * @param   string  $method   The method with which to send the request
  198.      * @param   int     $timeout  The timeout for the request
  199.      *
  200.      * @return  string  The URL.
  201.      *
  202.      * @since   12.3
  203.      * @throws  InvalidArgumentException
  204.      * @throws  RuntimeException
  205.      */
  206.     public function query($url$data null$headers array()$method 'get'$timeout null)
  207.     {
  208.         $token $this->getToken();
  209.  
  210.         if (array_key_exists('expires_in'$token&& $token['created'$token['expires_in'time(20)
  211.         {
  212.             if (!$this->getOption('userefresh'))
  213.             {
  214.                 return false;
  215.             }
  216.             $token $this->refreshToken($token['refresh_token']);
  217.         }
  218.  
  219.         if (!$this->getOption('authmethod'|| $this->getOption('authmethod'== 'bearer')
  220.         {
  221.             $headers['Authorization''Bearer ' $token['access_token'];
  222.         }
  223.         elseif ($this->getOption('authmethod'== 'get')
  224.         {
  225.             if (strpos($url'?'))
  226.             {
  227.                 $url .= '&';
  228.             }
  229.             else
  230.             {
  231.                 $url .= '?';
  232.             }
  233.             $url .= $this->getOption('getparam'$this->getOption('getparam''access_token';
  234.             $url .= '=' $token['access_token'];
  235.         }
  236.  
  237.         switch ($method)
  238.         {
  239.             case 'head':
  240.             case 'get':
  241.             case 'delete':
  242.             case 'trace':
  243.             $response $this->http->$method($url$headers$timeout);
  244.             break;
  245.             case 'post':
  246.             case 'put':
  247.             case 'patch':
  248.             $response $this->http->$method($url$data$headers$timeout);
  249.             break;
  250.             default:
  251.             throw new InvalidArgumentException('Unknown HTTP request method: ' $method '.');
  252.         }
  253.  
  254.         if ($response->code 200 || $response->code >= 400)
  255.         {
  256.             throw new RuntimeException('Error code ' $response->code ' received requesting data: ' $response->body '.');
  257.         }
  258.         return $response;
  259.     }
  260.  
  261.     /**
  262.      * Get an option from the JOAuth2Client instance.
  263.      *
  264.      * @param   string  $key  The name of the option to get
  265.      *
  266.      * @return  mixed  The option value
  267.      *
  268.      * @since   12.3
  269.      */
  270.     public function getOption($key)
  271.     {
  272.         return $this->options->get($key);
  273.     }
  274.  
  275.     /**
  276.      * Set an option for the JOAuth2Client instance.
  277.      *
  278.      * @param   string  $key    The name of the option to set
  279.      * @param   mixed   $value  The option value to set
  280.      *
  281.      * @return  JOAuth2Client  This object for method chaining
  282.      *
  283.      * @since   12.3
  284.      */
  285.     public function setOption($key$value)
  286.     {
  287.         $this->options->set($key$value);
  288.  
  289.         return $this;
  290.     }
  291.  
  292.     /**
  293.      * Get the access token from the JOAuth2Client instance.
  294.      *
  295.      * @return  array  The access token
  296.      *
  297.      * @since   12.3
  298.      */
  299.     public function getToken()
  300.     {
  301.         return $this->getOption('accesstoken');
  302.     }
  303.  
  304.     /**
  305.      * Set an option for the JOAuth2Client instance.
  306.      *
  307.      * @param   array  $value  The access token
  308.      *
  309.      * @return  JOAuth2Client  This object for method chaining
  310.      *
  311.      * @since   12.3
  312.      */
  313.     public function setToken($value)
  314.     {
  315.         if (is_array($value&& !array_key_exists('expires_in'$value&& array_key_exists('expires'$value))
  316.         {
  317.             $value['expires_in'$value['expires'];
  318.             unset($value['expires']);
  319.         }
  320.         $this->setOption('accesstoken'$value);
  321.  
  322.         return $this;
  323.     }
  324.  
  325.     /**
  326.      * Refresh the access token instance.
  327.      *
  328.      * @param   string  $token  The refresh token
  329.      *
  330.      * @return  array  The new access token
  331.      *
  332.      * @since   12.3
  333.      * @throws  Exception
  334.      * @throws  RuntimeException
  335.      */
  336.     public function refreshToken($token null)
  337.     {
  338.         if (!$this->getOption('userefresh'))
  339.         {
  340.             throw new RuntimeException('Refresh token is not supported for this OAuth instance.');
  341.         }
  342.  
  343.         if (!$token)
  344.         {
  345.             $token $this->getToken();
  346.  
  347.             if (!array_key_exists('refresh_token'$token))
  348.             {
  349.                 throw new RuntimeException('No refresh token is available.');
  350.             }
  351.             $token $token['refresh_token'];
  352.         }
  353.         $data['grant_type''refresh_token';
  354.         $data['refresh_token'$token;
  355.         $data['client_id'$this->getOption('clientid');
  356.         $data['client_secret'$this->getOption('clientsecret');
  357.         $response $this->http->post($this->getOption('tokenurl')$data);
  358.  
  359.         if ($response->code >= 200 || $response->code 400)
  360.         {
  361.             if ($response->headers['Content-Type'== 'application/json')
  362.             {
  363.                 $token array_merge(json_decode($response->bodytrue)array('created' => time()));
  364.             }
  365.             else
  366.             {
  367.                 parse_str($response->body$token);
  368.                 $token array_merge($tokenarray('created' => time()));
  369.             }
  370.  
  371.             $this->setToken($token);
  372.  
  373.             return $token;
  374.         }
  375.         else
  376.         {
  377.             throw new Exception('Error code ' $response->code ' received refreshing token: ' $response->body '.');
  378.         }
  379.     }
  380. }

Documentation generated on Tue, 19 Nov 2013 14:55:51 +0100 by phpDocumentor 1.4.3