Lots of logic implementation fixes

This commit is contained in:
Alex Bilbie 2014-01-10 12:30:13 +00:00
parent 0250d8d4d1
commit ac2beb08d6
16 changed files with 168 additions and 111 deletions

View File

@ -476,18 +476,18 @@ class Authorization
public function getStorage($obj) public function getStorage($obj)
{ {
if (!isset($this->storages[$obj])) { if (!isset($this->storages[$obj])) {
throw new ServerException('The `'.$obj.'` storage interface has not been registered with the authorization throw new ServerException(
server'); 'The `'.$obj.'` storage interface has not been registered with the authorization server'
);
} }
return $this->storages[$obj]; return $this->storages[$obj];
} }
/** /**
* Issue an access token * Issue an access token
* @param array $inputParams Optional array of parsed $_POST keys
* @return array Authorise request parameters * @return array Authorise request parameters
*/ */
public function issueAccessToken($inputParams = []) public function issueAccessToken()
{ {
$grantType = $this->getRequest()->request->get('grant_type'); $grantType = $this->getRequest()->request->get('grant_type');
if (is_null($grantType)) { if (is_null($grantType)) {
@ -500,7 +500,7 @@ class Authorization
} }
// Complete the flow // Complete the flow
return $this->getGrantType($grantType)->completeFlow($inputParams); return $this->getGrantType($grantType)->completeFlow();
} }
/** /**

View File

@ -14,8 +14,8 @@ namespace League\OAuth2\Server\Entities;
use League\OAuth2\Server\Storage\SessionStorageInterface; use League\OAuth2\Server\Storage\SessionStorageInterface;
use League\OAuth2\Server\Util\SecureKey; use League\OAuth2\Server\Util\SecureKey;
use League\OAuth2\Server\Exception\ServerException; use League\OAuth2\Server\Exception\ServerException;
use \League\OAuth2\Server\Authorization; use League\OAuth2\Server\Authorization;
use \League\OAuth2\Server\Resource; use League\OAuth2\Server\Resource;
use Symfony\Component\HttpFoundation\ParameterBag; use Symfony\Component\HttpFoundation\ParameterBag;
/** /**
@ -29,12 +29,6 @@ abstract class AbstractToken
*/ */
protected $token; protected $token;
/**
* Session ID
* @var string
*/
protected $sessionId;
/** /**
* Associated session * Associated session
* @var \League\OAuth2\Server\Session * @var \League\OAuth2\Server\Session
@ -71,7 +65,6 @@ abstract class AbstractToken
} }
$this->server = $server; $this->server = $server;
$this->scopes = new ParameterBag();
return $this; return $this;
} }
@ -96,11 +89,8 @@ abstract class AbstractToken
return $this->session; return $this->session;
} }
if ($this->sessionId !== null) { $this->session = $this->server->getStorage('session')->getByAccessToken($this->token);
$session = $this->server->getStorage('session')->getSession($this->sessionId); return $this->session;
}
throw new ServerException('No session ID set for this token');
} }
/** /**
@ -148,10 +138,10 @@ abstract class AbstractToken
* @param \League\OAuth2\Server\Entities\Scope $scope * @param \League\OAuth2\Server\Entities\Scope $scope
* @return self * @return self
*/ */
public function associateScope($scope) public function associateScope(Scope $scope)
{ {
if (!$this->scopes->has($scope->getId())) { if (!isset($this->scopes[$scope->getId()])) {
$this->scopes->set($scope->getId(), $scope); $this->scopes[$scope->getId()] = $scope;
} }
return $this; return $this;
@ -164,18 +154,44 @@ abstract class AbstractToken
*/ */
public function hasScope($scope) public function hasScope($scope)
{ {
return $this->scopes->has($scope); if ($this->scopes === null) {
$this->getScopes();
}
return isset($this->scopes[$scope]);
} }
/** /**
* Return all associated scopes * Return all scopes associated with the session
* @return ParameterBag * @return array Array of \League\OAuth2\Server\Entities\Scope
*/ */
public function getScopes() public function getScopes()
{ {
if ($this->scopes === null) {
$this->scopes = $this->formatScopes(
$this->server->getStorage('access_token')->getScopes($this->getToken())
);
}
return $this->scopes; return $this->scopes;
} }
/**
* Format the local scopes array
* @param array $unformated Array of Array of \League\OAuth2\Server\Entities\Scope
* @return array
*/
private function formatScopes($unformated = [])
{
$scopes = [];
foreach ($unformated as $scope) {
if ($scope instanceof Scope) {
$scopes[$scope->getId()] = $scope;
}
}
return $scopes;
}
/** /**
* Expire the token * Expire the token
* @return void * @return void

View File

@ -27,7 +27,7 @@ class AccessToken extends AbstractToken
*/ */
public function save() public function save()
{ {
$this->server->getStorage('access_token')->createAccessToken( $this->server->getStorage('access_token')->create(
$this->getToken(), $this->getToken(),
$this->getExpireTime(), $this->getExpireTime(),
$this->getSession()->getId() $this->getSession()->getId()
@ -40,4 +40,12 @@ class AccessToken extends AbstractToken
return $this; return $this;
} }
/**
* {@inheritdoc}
*/
public function expire()
{
$this->server->getStorage('access_token')->delete($this->getToken());
}
} }

View File

@ -45,6 +45,9 @@ class RefreshToken extends AbstractToken
*/ */
public function getAccessToken() public function getAccessToken()
{ {
if (! $this->accessToken instanceof AccessToken) {
$this->accessToken = $this->server->getStorage('access_token')->getByRefreshToken($this->getToken());
}
return $this->accessToken; return $this->accessToken;
} }
@ -53,7 +56,7 @@ class RefreshToken extends AbstractToken
*/ */
public function save() public function save()
{ {
$this->server->getStorage('refresh_token')->createAccessToken( $this->server->getStorage('refresh_token')->create(
$this->getToken(), $this->getToken(),
$this->getExpireTime(), $this->getExpireTime(),
$this->getAccessToken()->getToken() $this->getAccessToken()->getToken()
@ -64,4 +67,12 @@ class RefreshToken extends AbstractToken
$this->server->getStorage('refresh_token')->associateScope($this->getToken(), $scope->getId()); $this->server->getStorage('refresh_token')->associateScope($this->getToken(), $scope->getId());
} }
} }
/**
* {@inheritdoc}
*/
public function expire()
{
$this->server->getStorage('refresh_token')->delete($this->getToken());
}
} }

View File

@ -11,6 +11,10 @@
namespace League\OAuth2\Server\Entities; namespace League\OAuth2\Server\Entities;
use League\OAuth2\Server\Exception\ServerException;
use League\OAuth2\Server\Authorization;
use League\OAuth2\Server\Resource;
/** /**
* Scope entity class * Scope entity class
*/ */

View File

@ -88,7 +88,7 @@ class Session
throw new ServerException('No instance of Authorization or Resource server injected'); throw new ServerException('No instance of Authorization or Resource server injected');
} }
$this->scopes = new ParameterBag(); $this->server = $server;
return $this; return $this;
} }
@ -117,10 +117,10 @@ class Session
* @param \League\OAuth2\Server\Entities\Scope $scope * @param \League\OAuth2\Server\Entities\Scope $scope
* @return self * @return self
*/ */
public function associateScope($scope) public function associateScope(Scope $scope)
{ {
if (!$this->scopes->has($scope->getId())) { if (!isset($this->scopes[$scope->getId()])) {
$this->scopes->set($scope->getId(), $scope); $this->scopes[$scope->getId()] = $scope;
} }
return $this; return $this;
@ -133,7 +133,11 @@ class Session
*/ */
public function hasScope($scope) public function hasScope($scope)
{ {
return $this->scopes->has($scope); if ($this->scopes === null) {
$this->getScopes();
}
return isset($this->scopes[$scope]);
} }
/** /**
@ -142,7 +146,27 @@ class Session
*/ */
public function getScopes() public function getScopes()
{ {
return $this->scopes->all(); if ($this->scopes === null) {
$this->scopes = $this->formatScopes($this->server->getStorage('session')->getScopes($this->getId()));
}
return $this->scopes;
}
/**
* Format the local scopes array
* @param array $unformated Array of Array of \League\OAuth2\Server\Entities\Scope
* @return array
*/
private function formatScopes($unformated = [])
{
$scopes = [];
foreach ($unformated as $scope) {
if ($scope instanceof Scope) {
$scopes[$scope->getId()] = $scope;
}
}
return $scopes;
} }
/** /**
@ -237,7 +261,7 @@ class Session
public function save() public function save()
{ {
// Save the session and get an identifier // Save the session and get an identifier
$id = $this->server->getStorage('session')->createSession( $id = $this->server->getStorage('session')->create(
$this->getOwnerType(), $this->getOwnerType(),
$this->getOwnerId(), $this->getOwnerId(),
$this->getClient()->getId(), $this->getClient()->getId(),

View File

@ -29,25 +29,25 @@ abstract class AbstractGrant implements GrantTypeInterface
* Response type * Response type
* @var string * @var string
*/ */
protected $responseType = null; protected $responseType;
/** /**
* Callback to authenticate a user's name and password * Callback to authenticate a user's name and password
* @var function * @var function
*/ */
protected $callback = null; protected $callback;
/** /**
* AuthServer instance * AuthServer instance
* @var AuthServer * @var AuthServer
*/ */
protected $server = null; protected $server;
/** /**
* Access token expires in override * Access token expires in override
* @var int * @var int
*/ */
protected $accessTokenTTL = null; protected $accessTokenTTL;
/** /**
* Return the identifier * Return the identifier
@ -132,7 +132,7 @@ abstract class AbstractGrant implements GrantTypeInterface
$scopes = []; $scopes = [];
foreach ($scopesList as $scopeItem) { foreach ($scopesList as $scopeItem) {
$scope = $this->server->getStorage('scope')->getScope( $scope = $this->server->getStorage('scope')->get(
$scopeItem, $scopeItem,
$this->getIdentifier() $this->getIdentifier()
); );
@ -141,12 +141,28 @@ abstract class AbstractGrant implements GrantTypeInterface
throw new ClientException(sprintf($this->server->getExceptionMessage('invalid_scope'), $scopeItem), 4); throw new ClientException(sprintf($this->server->getExceptionMessage('invalid_scope'), $scopeItem), 4);
} }
$scopes[] = $scope; $scopes[$scope->getId()] = $scope;
} }
return $scopes; return $scopes;
} }
/**
* Format the local scopes array
* @param array $unformated Array of Array of \League\OAuth2\Server\Entities\Scope
* @return array
*/
protected function formatScopes($unformated = [])
{
$scopes = [];
foreach ($unformated as $scope) {
if ($scope instanceof Scope) {
$scopes[$scope->getId()] = $scope;
}
}
return $scopes;
}
/** /**
* Complete the grant flow * Complete the grant flow
* *

View File

@ -76,7 +76,7 @@ class ClientCredentials extends AbstractGrant
} }
// Validate client ID and client secret // Validate client ID and client secret
$client = $this->server->getStorage('client')->getClient( $client = $this->server->getStorage('client')->get(
$clientId, $clientId,
$clientSecret, $clientSecret,
null, null,
@ -92,12 +92,12 @@ class ClientCredentials extends AbstractGrant
$scopes = $this->validateScopes($scopeParam); $scopes = $this->validateScopes($scopeParam);
// Create a new session // Create a new session
$session = new Session(); $session = new Session($this->server);
$session->setOwner('client', $client->getId()); $session->setOwner('client', $client->getId());
$session->associateClient($client); $session->associateClient($client);
// Generate an access token // Generate an access token
$accessToken = new AccessToken(); $accessToken = new AccessToken($this->server);
$accessToken->setToken(SecureKey::make()); $accessToken->setToken(SecureKey::make());
$accessToken->setExpireTime($this->server->getAccessTokenTTL() + time()); $accessToken->setExpireTime($this->server->getAccessTokenTTL() + time());

View File

@ -39,25 +39,19 @@ class Password extends AbstractGrant
* Response type * Response type
* @var string * @var string
*/ */
protected $responseType = null; protected $responseType;
/** /**
* Callback to authenticate a user's name and password * Callback to authenticate a user's name and password
* @var function * @var function
*/ */
protected $callback = null; protected $callback;
/**
* AuthServer instance
* @var AuthServer
*/
protected $authServer = null;
/** /**
* Access token expires in override * Access token expires in override
* @var int * @var int
*/ */
protected $accessTokenTTL = null; protected $accessTokenTTL;
/** /**
* Set the callback to verify a user's username and password * Set the callback to verify a user's username and password
@ -107,7 +101,7 @@ class Password extends AbstractGrant
} }
// Validate client ID and client secret // Validate client ID and client secret
$client = $this->server->getStorage('client')->getClient( $client = $this->server->getStorage('client')->get(
$clientId, $clientId,
$clientSecret, $clientSecret,
null, null,
@ -177,13 +171,13 @@ class Password extends AbstractGrant
} }
// Save everything // Save everything
$session->save($this->server->getStorage('session')); $session->save();
$accessToken->setSession($session); $accessToken->setSession($session);
$accessToken->save($this->server->getStorage('access_token')); $accessToken->save();
if ($this->server->hasGrantType('refresh_token')) { if ($this->server->hasGrantType('refresh_token')) {
$refreshToken->setAccessToken($accessToken); $refreshToken->setAccessToken($accessToken);
$refreshToken->save($this->server->getStorage('refresh_token')); $refreshToken->save();
} }
return $response; return $response;

View File

@ -80,7 +80,7 @@ class RefreshToken extends AbstractGrant
} }
// Validate client ID and client secret // Validate client ID and client secret
$client = $this->server->getStorage('client')->getClient( $client = $this->server->getStorage('client')->get(
$clientId, $clientId,
$clientSecret, $clientSecret,
null, null,
@ -100,7 +100,7 @@ class RefreshToken extends AbstractGrant
} }
// Validate refresh token // Validate refresh token
$oldRefreshToken = $this->server->getStorage('refresh_token')->getToken($oldRefreshTokenParam); $oldRefreshToken = $this->server->getStorage('refresh_token')->get($oldRefreshTokenParam);
if (($oldRefreshToken instanceof RT) === false) { if (($oldRefreshToken instanceof RT) === false) {
throw new Exception\ClientException($this->server->getExceptionMessage('invalid_refresh'), 0); throw new Exception\ClientException($this->server->getExceptionMessage('invalid_refresh'), 0);
@ -110,7 +110,7 @@ class RefreshToken extends AbstractGrant
// Get the scopes for the original session // Get the scopes for the original session
$session = $oldAccessToken->getSession(); $session = $oldAccessToken->getSession();
$scopes = $session->getScopes(); $scopes = $this->formatScopes($session->getScopes());
// Get and validate any requested scopes // Get and validate any requested scopes
$requestedScopesString = $this->server->getRequest()->request->get('scope', ''); $requestedScopesString = $this->server->getRequest()->request->get('scope', '');
@ -124,14 +124,19 @@ class RefreshToken extends AbstractGrant
// the request doesn't include any new scopes // the request doesn't include any new scopes
foreach ($requestedScopes as $requestedScope) { foreach ($requestedScopes as $requestedScope) {
// if () if (!isset($scopes[$requestedScope->getId()])) {
throw new Exception\ClientException(
sprintf($this->server->getExceptionMessage('invalid_scope'), $requestedScope->getId()),
0
);
}
} }
$newScopes = $requestedScopes; $newScopes = $requestedScopes;
} }
// Generate a new access token and assign it the correct sessions // Generate a new access token and assign it the correct sessions
$newAccessToken = new AccessToken(); $newAccessToken = new AccessToken($this->server);
$newAccessToken->setToken(SecureKey::make()); $newAccessToken->setToken(SecureKey::make());
$newAccessToken->setExpireTime($this->server->getAccessTokenTTL() + time()); $newAccessToken->setExpireTime($this->server->getAccessTokenTTL() + time());
$newAccessToken->setSession($session); $newAccessToken->setSession($session);
@ -155,7 +160,7 @@ class RefreshToken extends AbstractGrant
$oldRefreshToken->expire($this->server->getStorage('refresh_token')); $oldRefreshToken->expire($this->server->getStorage('refresh_token'));
// Generate a new refresh token // Generate a new refresh token
$newRefreshToken = new RT(); $newRefreshToken = new RT($this->server);
$newRefreshToken->setToken(SecureKey::make()); $newRefreshToken->setToken(SecureKey::make());
$newRefreshToken->setExpireTime($this->getRefreshTokenTTL() + time()); $newRefreshToken->setExpireTime($this->getRefreshTokenTTL() + time());
$newRefreshToken->setAccessToken($newAccessToken); $newRefreshToken->setAccessToken($newAccessToken);

View File

@ -21,14 +21,16 @@ interface AccessTokenInterface
* @param string $token The access token * @param string $token The access token
* @return \League\OAuth2\Server\Entities\AccessToken * @return \League\OAuth2\Server\Entities\AccessToken
*/ */
public function getToken($token); public function get($token);
public function getByRefreshToken($refreshToken);
/** /**
* Get the scopes for an access token * Get the scopes for an access token
* @param string $token The access token * @param string $token The access token
* @return array Array of \League\OAuth2\Server\Entities\Scope * @return array Array of \League\OAuth2\Server\Entities\Scope
*/ */
public function getTokenScopes($token); public function getScopes($token);
/** /**
* Creates a new access token * Creates a new access token
@ -37,7 +39,7 @@ interface AccessTokenInterface
* @param string|integer $sessionId The session ID * @param string|integer $sessionId The session ID
* @return \League\OAuth2\Server\Entities\AccessToken * @return \League\OAuth2\Server\Entities\AccessToken
*/ */
public function createAccessToken($token, $expireTime, $sessionId); public function create($token, $expireTime, $sessionId);
/** /**
* Associate a scope with an acess token * Associate a scope with an acess token

View File

@ -21,5 +21,5 @@ interface AuthCodeInterface
* @param string $code * @param string $code
* @return \League\OAuth2\Server\Entities\AuthCode * @return \League\OAuth2\Server\Entities\AuthCode
*/ */
public function getCode($code); public function get($code);
} }

View File

@ -18,34 +18,11 @@ interface ClientInterface
{ {
/** /**
* Validate a client * Validate a client
*
* Example SQL query:
*
* <code>
* # Client ID + redirect URI
* SELECT oauth_clients.id, oauth_clients.secret, oauth_endpoints.redirect_uri, oauth_clients.name
* FROM oauth_clients
* LEFT JOIN oauth_client_endpoints ON oauth_client_endpoints.client_id = oauth_clients.id
* WHERE oauth_clients.id = :clientId AND oauth_client_endpoints.redirect_uri = :redirectUri
*
* # Client ID + client secret
* SELECT oauth_clients.id, oauth_clients.secret, oauth_clients.name
* FROM oauth_clients
* WHERE oauth_clients.id = :clientId AND oauth_clients.secret = :clientSecret
*
* # Client ID + client secret + redirect URI
* SELECT oauth_clients.id, oauth_clients.secret, oauth_client_endpoints.redirect_uri, oauth_clients.name
* FROM oauth_clients LEFT JOIN oauth_client_endpoints
* ON oauth_client_endpoints.client_id = oauth_clients.id
* WHERE oauth_clients.id = :clientId AND oauth_clients.secret = :clientSecret AND
* oauth_client_endpoints.redirect_uri = :redirectUri
* </code>
*
* @param string $clientId The client's ID * @param string $clientId The client's ID
* @param string $clientSecret The client's secret (default = "null") * @param string $clientSecret The client's secret (default = "null")
* @param string $redirectUri The client's redirect URI (default = "null") * @param string $redirectUri The client's redirect URI (default = "null")
* @param string $grantType The grant type used in the request (default = "null") * @param string $grantType The grant type used in the request (default = "null")
* @return League\OAuth2\Server\Entities\Client|null * @return League\OAuth2\Server\Entities\Client|null
*/ */
public function getClient($clientId, $clientSecret = null, $redirectUri = null, $grantType = null); public function get($clientId, $clientSecret = null, $redirectUri = null, $grantType = null);
} }

View File

@ -21,7 +21,7 @@ interface RefreshTokenInterface
* @param string $token * @param string $token
* @return \League\OAuth2\Server\Entities\RefreshToken * @return \League\OAuth2\Server\Entities\RefreshToken
*/ */
public function getToken($token); public function get($token);
/** /**
* Create a new refresh token_name * Create a new refresh token_name
@ -30,7 +30,7 @@ interface RefreshTokenInterface
* @param string $accessToken * @param string $accessToken
* @return \League\OAuth2\Server\Entities\RefreshToken * @return \League\OAuth2\Server\Entities\RefreshToken
*/ */
public function createRefreshToken($token, $expireTime, $accessToken); public function create($token, $expireTime, $accessToken);
/** /**
* Delete the refresh token * Delete the refresh token

View File

@ -29,5 +29,5 @@ interface ScopeInterface
* @param string $grantType The grant type used in the request (default = "null") * @param string $grantType The grant type used in the request (default = "null")
* @return bool|array If the scope doesn't exist return false * @return bool|array If the scope doesn't exist return false
*/ */
public function getScope($scope, $grantType = null); public function get($scope, $grantType = null);
} }

View File

@ -17,25 +17,25 @@ namespace League\OAuth2\Server\Storage;
interface SessionInterface interface SessionInterface
{ {
/** /**
* Get a session * Get a session from it's identifier
* * @param string $sessionId
* @param int $sessionId * @return \League\OAuth2\Server\Entities\Session
* @return array (As described above)
*/ */
public function getSession($sessionId); public function get($sessionId);
/**
* Get a session from an access token
* @param string $accessToken The access token
* @return \League\OAuth2\Server\Entities\Session
*/
public function getByAccessToken($accessToken);
/** /**
* Get a session's scopes * Get a session's scopes
* * @param integer $sessionId
* Response: * @return array Array of \League\OAuth2\Server\Entities\Scope
* <code>
*
* </code>
*
* @param int $sessionId
* @return array (As described aboce)
*/ */
public function getSessionScopes($sessionId); public function getScopes($sessionId);
/** /**
* Create a new session * Create a new session
@ -43,14 +43,14 @@ interface SessionInterface
* @param string $ownerId Session owner's ID * @param string $ownerId Session owner's ID
* @param string $clientId Client ID * @param string $clientId Client ID
* @param string $clientRedirectUri Client redirect URI (default = null) * @param string $clientRedirectUri Client redirect URI (default = null)
* @return int Session ID * @return integer The session's ID
*/ */
public function createSession($ownerType, $ownerId, $clientId, $clientRedirectUri = null); public function create($ownerType, $ownerId, $clientId, $clientRedirectUri = null);
/** /**
* Associate a scope with a session * Associate a scope with a session
* @param int $sessionId * @param integer $sessionId
* @param int|string $scopeId The scopes ID might be an integer or string * @param string $scopeId The scopes ID might be an integer or string
* @return void * @return void
*/ */
public function associateScope($sessionId, $scopeId); public function associateScope($sessionId, $scopeId);