Compare commits
7 commits
Author | SHA1 | Date | |
---|---|---|---|
|
15a4b807d5 | ||
|
1e8e9efd95 | ||
|
80a36aee99 | ||
|
de2e4b997b | ||
|
6ff0061992 | ||
|
4bd4625dd3 | ||
|
1f3650b98a |
15 changed files with 122 additions and 710 deletions
|
@ -23,7 +23,7 @@
|
|||
},
|
||||
"require": {
|
||||
"php": ">=5.4",
|
||||
"league/oauth2-server": "4.0.x-dev"
|
||||
"bshaffer/oauth2-server-php": "v1.5"
|
||||
},
|
||||
"suggest": {
|
||||
"mongodb/mongo-php-driver": "Required to use the Mongo storage engine",
|
||||
|
|
174
composer.lock
generated
174
composer.lock
generated
|
@ -4,160 +4,35 @@
|
|||
"Read more about it at http://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file",
|
||||
"This file is @generated automatically"
|
||||
],
|
||||
"hash": "65e330b4eb2873d61093fc36aa624d0f",
|
||||
"hash": "f90250145c5046194b1c3187fc90513a",
|
||||
"packages": [
|
||||
{
|
||||
"name": "league/event",
|
||||
"version": "1.0.0",
|
||||
"name": "bshaffer/oauth2-server-php",
|
||||
"version": "v1.5",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/thephpleague/event.git",
|
||||
"reference": "06adb7ce55b93346be43a3ba677ac613bbf288a2"
|
||||
"url": "https://github.com/bshaffer/oauth2-server-php.git",
|
||||
"reference": "74fcc75e47614c1417c750e907a44567d9ceee1f"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/thephpleague/event/zipball/06adb7ce55b93346be43a3ba677ac613bbf288a2",
|
||||
"reference": "06adb7ce55b93346be43a3ba677ac613bbf288a2",
|
||||
"url": "https://api.github.com/repos/bshaffer/oauth2-server-php/zipball/74fcc75e47614c1417c750e907a44567d9ceee1f",
|
||||
"reference": "74fcc75e47614c1417c750e907a44567d9ceee1f",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.4.0"
|
||||
"php": ">=5.3.9"
|
||||
},
|
||||
"require-dev": {
|
||||
"henrikbjorn/phpspec-code-coverage": "1.0.*@dev",
|
||||
"phpspec/phpspec": "2.0.*@dev"
|
||||
"suggest": {
|
||||
"aws/aws-sdk-php": "Required to use the DynamoDB storage engine",
|
||||
"predis/predis": "Required to use the Redis storage engine",
|
||||
"thobbs/phpcassa": "Required to use the Cassandra storage engine"
|
||||
},
|
||||
"type": "library",
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"League\\Event\\": "src/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Frank de Jonge",
|
||||
"email": "info@frenky.net"
|
||||
}
|
||||
],
|
||||
"description": "Event package",
|
||||
"keywords": [
|
||||
"emitter",
|
||||
"event",
|
||||
"listener"
|
||||
],
|
||||
"time": "2014-09-09 14:40:43"
|
||||
},
|
||||
{
|
||||
"name": "league/oauth2-server",
|
||||
"version": "dev-develop",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/thephpleague/oauth2-server.git",
|
||||
"reference": "6333a975f8fb51111b447a7e85806e4519fb52b9"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/thephpleague/oauth2-server/zipball/6333a975f8fb51111b447a7e85806e4519fb52b9",
|
||||
"reference": "6333a975f8fb51111b447a7e85806e4519fb52b9",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"league/event": "1.0.*",
|
||||
"php": ">=5.4.0",
|
||||
"symfony/http-foundation": "~2.1"
|
||||
},
|
||||
"replace": {
|
||||
"league/oauth2server": "*",
|
||||
"lncd/oauth2": "*"
|
||||
},
|
||||
"require-dev": {
|
||||
"alexbilbie/fizzfuzz": "dev-develop",
|
||||
"codeception/codeception": "2.0.*",
|
||||
"league/phpunit-coverage-listener": "~1.0",
|
||||
"mockery/mockery": "~0.9",
|
||||
"phpunit/phpunit": "~4.0",
|
||||
"squizlabs/php_codesniffer": "~1.5"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-develop": "4.0.x-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"League\\OAuth2\\Server\\": "src/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Alex Bilbie",
|
||||
"email": "hello@alexbilbie.com",
|
||||
"homepage": "http://www.alexbilbie.com",
|
||||
"role": "Developer"
|
||||
}
|
||||
],
|
||||
"description": "A lightweight and powerful OAuth 2.0 authorization and resource server library with support for all the core specification grants. This library will allow you to secure your API with OAuth and allow your applications users to approve apps that want to access their data from your API.",
|
||||
"homepage": "http://oauth2.thephpleague.com/",
|
||||
"keywords": [
|
||||
"Authentication",
|
||||
"api",
|
||||
"auth",
|
||||
"authorisation",
|
||||
"authorization",
|
||||
"oauth",
|
||||
"oauth 2",
|
||||
"oauth 2.0",
|
||||
"oauth2",
|
||||
"protect",
|
||||
"resource",
|
||||
"secure",
|
||||
"server"
|
||||
],
|
||||
"time": "2014-10-03 13:42:01"
|
||||
},
|
||||
{
|
||||
"name": "symfony/http-foundation",
|
||||
"version": "dev-master",
|
||||
"target-dir": "Symfony/Component/HttpFoundation",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/HttpFoundation.git",
|
||||
"reference": "c24942a7ec2d8409d1f60d02c4460ca8317e885a"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/HttpFoundation/zipball/c24942a7ec2d8409d1f60d02c4460ca8317e885a",
|
||||
"reference": "c24942a7ec2d8409d1f60d02c4460ca8317e885a",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=5.3.3"
|
||||
},
|
||||
"require-dev": {
|
||||
"symfony/expression-language": "~2.4"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-master": "2.6-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"psr-0": {
|
||||
"Symfony\\Component\\HttpFoundation\\": ""
|
||||
},
|
||||
"classmap": [
|
||||
"Symfony/Component/HttpFoundation/Resources/stubs"
|
||||
]
|
||||
"OAuth2": "src/"
|
||||
}
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
|
@ -165,17 +40,19 @@
|
|||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Symfony Community",
|
||||
"homepage": "http://symfony.com/contributors"
|
||||
},
|
||||
{
|
||||
"name": "Fabien Potencier",
|
||||
"email": "fabien@symfony.com"
|
||||
"name": "Brent Shaffer",
|
||||
"email": "bshafs@gmail.com",
|
||||
"homepage": "http://brentertainment.com"
|
||||
}
|
||||
],
|
||||
"description": "Symfony HttpFoundation Component",
|
||||
"homepage": "http://symfony.com",
|
||||
"time": "2014-10-07 14:06:18"
|
||||
"description": "OAuth2 Server for PHP",
|
||||
"homepage": "http://github.com/bshaffer/oauth2-server-php",
|
||||
"keywords": [
|
||||
"auth",
|
||||
"oauth",
|
||||
"oauth2"
|
||||
],
|
||||
"time": "2014-08-28 02:13:42"
|
||||
}
|
||||
],
|
||||
"packages-dev": [
|
||||
|
@ -1434,7 +1311,6 @@
|
|||
"aliases": [],
|
||||
"minimum-stability": "dev",
|
||||
"stability-flags": {
|
||||
"league/oauth2-server": 20,
|
||||
"phpunit/phpunit": 20,
|
||||
"satooshi/php-coveralls": 20
|
||||
},
|
||||
|
|
129
sql/oauth2.sql
129
sql/oauth2.sql
|
@ -1,129 +0,0 @@
|
|||
CREATE TABLE `oauth_clients` (
|
||||
`id` CHAR(40) NOT NULL,
|
||||
`secret` CHAR(40) NOT NULL,
|
||||
`name` VARCHAR(255) NOT NULL,
|
||||
`auto_approve` TINYINT(1) NOT NULL DEFAULT '0',
|
||||
PRIMARY KEY (`id`),
|
||||
UNIQUE KEY `u_oacl_clse_clid` (`secret`,`id`)
|
||||
) ENGINE=INNODB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_endpoints` (
|
||||
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
|
||||
`client_id` char(40) NOT NULL,
|
||||
`redirect_uri` varchar(255) NOT NULL,
|
||||
PRIMARY KEY (`id`),
|
||||
KEY `i_oaclen_clid` (`client_id`),
|
||||
CONSTRAINT `f_oaclen_clid`
|
||||
FOREIGN KEY (`client_id`)
|
||||
REFERENCES `oauth_clients` (`id`)
|
||||
ON DELETE CASCADE ON UPDATE CASCADE
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_sessions` (
|
||||
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
|
||||
`client_id` char(40) NOT NULL,
|
||||
`owner_type` enum('user','client') NOT NULL DEFAULT 'user',
|
||||
`owner_id` varchar(255) NOT NULL,
|
||||
PRIMARY KEY (`id`),
|
||||
KEY `i_uase_clid_owty_owid` (`client_id`,`owner_type`,`owner_id`),
|
||||
CONSTRAINT `f_oase_clid`
|
||||
FOREIGN KEY (`client_id`)
|
||||
REFERENCES `oauth_clients` (`id`)
|
||||
ON DELETE CASCADE ON UPDATE CASCADE
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_access_tokens` (
|
||||
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
|
||||
`session_id` int(10) unsigned NOT NULL,
|
||||
`access_token` char(40) NOT NULL,
|
||||
`expires_at` int(10) unsigned NOT NULL,
|
||||
PRIMARY KEY (`id`),
|
||||
UNIQUE KEY `u_oaseacto_acto_seid` (`access_token`,`session_id`),
|
||||
KEY `f_oaseto_seid` (`session_id`),
|
||||
CONSTRAINT `f_oaseto_seid`
|
||||
FOREIGN KEY (`session_id`)
|
||||
REFERENCES `oauth_sessions` (`id`)
|
||||
ON DELETE CASCADE ON UPDATE NO ACTION
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_authorization_codes` (
|
||||
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
|
||||
`session_id` int(10) unsigned NOT NULL,
|
||||
`authorization_code` char(40) NOT NULL,
|
||||
`expires_at` int(10) unsigned NOT NULL,
|
||||
PRIMARY KEY (`id`),
|
||||
KEY `session_id` (`session_id`),
|
||||
CONSTRAINT `oauth_authorization_codes_ibfk_1`
|
||||
FOREIGN KEY (`session_id`)
|
||||
REFERENCES `oauth_sessions` (`id`)
|
||||
ON DELETE CASCADE
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_redirect_uris` (
|
||||
`session_id` int(10) unsigned NOT NULL,
|
||||
`redirect_uri` varchar(255) NOT NULL,
|
||||
PRIMARY KEY (`session_id`),
|
||||
CONSTRAINT `f_oasere_seid`
|
||||
FOREIGN KEY (`session_id`)
|
||||
REFERENCES `oauth_sessions` (`id`)
|
||||
ON DELETE CASCADE ON UPDATE NO ACTION
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_refresh_tokens` (
|
||||
`access_token_id` int(10) unsigned NOT NULL,
|
||||
`refresh_token` char(40) NOT NULL,
|
||||
`expires_at` int(10) unsigned NOT NULL,
|
||||
`client_id` char(40) NOT NULL,
|
||||
PRIMARY KEY (`access_token_id`),
|
||||
KEY `client_id` (`client_id`),
|
||||
CONSTRAINT `oauth_refresh_tokens_ibfk_1`
|
||||
FOREIGN KEY (`client_id`)
|
||||
REFERENCES `oauth_clients` (`id`)
|
||||
ON DELETE CASCADE,
|
||||
CONSTRAINT `f_oasetore_setoid`
|
||||
FOREIGN KEY (`access_token_id`)
|
||||
REFERENCES `oauth_access_tokens` (`id`)
|
||||
ON DELETE CASCADE ON UPDATE NO ACTION
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_scopes` (
|
||||
`id` smallint(5) unsigned NOT NULL AUTO_INCREMENT,
|
||||
`scope` varchar(255) NOT NULL,
|
||||
`name` varchar(255) NOT NULL,
|
||||
`description` varchar(255) DEFAULT NULL,
|
||||
PRIMARY KEY (`id`),
|
||||
UNIQUE KEY `u_oasc_sc` (`scope`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_access_token_scopes` (
|
||||
`id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,
|
||||
`access_token_id` int(10) unsigned DEFAULT NULL,
|
||||
`scope_id` smallint(5) unsigned NOT NULL,
|
||||
PRIMARY KEY (`id`),
|
||||
UNIQUE KEY `u_setosc_setoid_scid` (`access_token_id`,`scope_id`),
|
||||
KEY `f_oasetosc_scid` (`scope_id`),
|
||||
CONSTRAINT `f_oasetosc_scid`
|
||||
FOREIGN KEY (`scope_id`)
|
||||
REFERENCES `oauth_scopes` (`id`)
|
||||
ON DELETE CASCADE ON UPDATE NO ACTION,
|
||||
CONSTRAINT `f_oasetosc_setoid`
|
||||
FOREIGN KEY (`access_token_id`)
|
||||
REFERENCES `oauth_access_tokens` (`id`)
|
||||
ON DELETE CASCADE ON UPDATE NO ACTION
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
||||
CREATE TABLE `oauth_authorization_code_scopes` (
|
||||
`authorization_code_id` int(10) unsigned NOT NULL,
|
||||
`scope_id` smallint(5) unsigned NOT NULL,
|
||||
KEY `authorization_code_id` (`authorization_code_id`),
|
||||
KEY `scope_id` (`scope_id`),
|
||||
CONSTRAINT `oauth_authorization_code_scopes_ibfk_2`
|
||||
FOREIGN KEY (`scope_id`)
|
||||
REFERENCES `oauth_scopes` (`id`)
|
||||
ON DELETE CASCADE,
|
||||
CONSTRAINT `oauth_authorization_code_scopes_ibfk_1`
|
||||
FOREIGN KEY (`authorization_code_id`)
|
||||
REFERENCES `oauth_authorization_codes` (`id`)
|
||||
ON DELETE CASCADE
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE utf8_unicode_ci;
|
||||
|
|
@ -37,7 +37,7 @@ class Mongo extends Object
|
|||
|
||||
// Instantiates our Mongo client
|
||||
$instance = new \MongoClient($mongo['server']);
|
||||
$instance->selectDB($mongo['database']);
|
||||
$instance = $instance->$mongo['database'];
|
||||
|
||||
// Caches the instance for possible reuse later
|
||||
self::$instances['Mongo'] = $instance;
|
||||
|
|
|
@ -1,84 +0,0 @@
|
|||
<?php
|
||||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \League\OAuth2\Server\Entity\AbstractTokenEntity;
|
||||
use \League\OAuth2\Server\Entity\AccessTokenEntity;
|
||||
use \League\OAuth2\Server\Entity\ScopeEntity;
|
||||
use \League\OAuth2\Server\Storage\AccessTokenInterface;
|
||||
|
||||
class AccessTokenStorage extends StorageAdapter implements AccessTokenInterface
|
||||
{
|
||||
public function get($token)
|
||||
{
|
||||
$sql = 'SELECT oauth_access_tokens.*'
|
||||
. ' FROM oauth_access_tokens'
|
||||
. ' WHERE access_token = ?'
|
||||
. ' AND expires_at >= ?;';
|
||||
|
||||
$results = $this->db->fetch($sql, [$token, time()]);
|
||||
|
||||
if (count($results) === 1)
|
||||
{
|
||||
return (new AccessTokenEntity($this->server))
|
||||
->setId($results[0]['access_token'])
|
||||
->setExpireTime($results[0]['expires_at']);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public function getScopes(AbstractTokenEntity $token)
|
||||
{
|
||||
$sql = 'SELECT oauth_scopes.id, oauth_scopes.description'
|
||||
. ' FROM oauth_access_token_scopes'
|
||||
. ' INNER JOIN oauth_scopes'
|
||||
. ' ON oauth_access_token_scopes.scope_id = oauth_scopes.id'
|
||||
. ' WHERE oauth_access_token_scopes.access_token_id = ?;';
|
||||
|
||||
$results = $this->db->fetch($sql, [$token->getId()]);
|
||||
$response = [];
|
||||
|
||||
if (count($results) > 0)
|
||||
{
|
||||
foreach ($results as $row)
|
||||
{
|
||||
$response[] = (new ScopeEntity($this->server))->hydrate([
|
||||
'id' => $row['id'],
|
||||
'description' => $row['description']
|
||||
]);
|
||||
}
|
||||
}
|
||||
|
||||
return $response;
|
||||
}
|
||||
|
||||
public function create($token, $expiration, $session_id)
|
||||
{
|
||||
$sql = 'INSERT INTO oauth_access_tokens'
|
||||
. ' (access_token, session_id, expires_at)'
|
||||
. ' VALUES'
|
||||
. ' (?, ?, ?);';
|
||||
|
||||
$this->db->execute($sql, [$token, $session_id, $expiration]);
|
||||
}
|
||||
|
||||
public function associateScope(AbstractTokenEntity $token, ScopeEntity $scope)
|
||||
{
|
||||
$sql = 'INSERT INTO oauth_access_token_scopes'
|
||||
. ' (access_token, scope)'
|
||||
. ' VALUES'
|
||||
. ' (?, ?);';
|
||||
|
||||
$this->db->execute($sql, [$token->getId(), $scope->getId()]);
|
||||
}
|
||||
|
||||
public function delete(AbstractTokenEntity $token)
|
||||
{
|
||||
$sql = 'DELETE FROM oauth_access_token_scopes'
|
||||
. ' WHERE access_token = ?;';
|
||||
|
||||
$this->db->execute($sql, [$token->getId()]);
|
||||
}
|
||||
}
|
||||
|
|
@ -1,81 +0,0 @@
|
|||
<?php
|
||||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \League\OAuth2\Server\Entity\ClientEntity;
|
||||
use \League\OAuth2\Server\Entity\SessionEntity;
|
||||
use \League\OAuth2\Server\Storage\Adapter;
|
||||
use \League\OAuth2\Server\Storage\ClientInterface;
|
||||
|
||||
class ClientStorage extends StorageAdapter implements ClientInterface
|
||||
{
|
||||
public function get($client_id, $client_secret = null, $redirect_uri = null, $grant_type = null)
|
||||
{
|
||||
$sql = 'SELECT oauth_clients.*';
|
||||
|
||||
if ($redirect_uri)
|
||||
{
|
||||
$sql .= ', oauth_client_redirect_uris.*'
|
||||
. ' INNER JOIN oauth_redirect_uris'
|
||||
. ' ON oauth_clients.id = oauth_redirect_uris.client_id';
|
||||
}
|
||||
|
||||
$sql .= ' FROM oauth_clients WHERE oauth_clients.id = ?';
|
||||
|
||||
$parameters = [$client_id];
|
||||
|
||||
if ($client_secret)
|
||||
{
|
||||
$sql .= ' AND oauth_clients.secret = ?';
|
||||
$parameters[] = $client_secret;
|
||||
}
|
||||
|
||||
if ($redirect_uri)
|
||||
{
|
||||
$sql .= 'AND oauth_redirect_uris.redirect_uri = ?';
|
||||
$parameters[] = $redirect_uri;
|
||||
}
|
||||
|
||||
$results = $this->db->fetch($sql, $parameters);
|
||||
|
||||
if (count($results) === 1)
|
||||
{
|
||||
$client = new ClientEntity($this->server);
|
||||
|
||||
$client->hydrate([
|
||||
'id' => $results[0]['id'],
|
||||
'name' => $results[0]['name']
|
||||
]);
|
||||
|
||||
return $client;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public function getBySession(SessionEntity $session)
|
||||
{
|
||||
$sql = 'SELECT oauth_clients.id, oauth_clients.name'
|
||||
. ' FROM oauth_clients'
|
||||
. ' INNER JOIN oauth_sessions'
|
||||
. ' ON oauth_clients.id = oauth_sessions.client_id'
|
||||
. ' WHERE oauth_sessions.id = ?';
|
||||
|
||||
$results = $this->db->fetch($sql, [$session->getId()]);
|
||||
|
||||
if (count($results) === 1)
|
||||
{
|
||||
$client = new ClientEntity($this->server);
|
||||
|
||||
$client->hydrate([
|
||||
'id' => $results[0]['id'],
|
||||
'name' => $results[0]['name']
|
||||
]);
|
||||
|
||||
return $client;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,56 +0,0 @@
|
|||
<?php
|
||||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \League\OAuth2\Server\Entity\RefreshTokenEntity;
|
||||
use \League\OAuth2\Server\Storage\RefreshTokenInterface;
|
||||
|
||||
class RefreshTokenStorage extends StorageAdapter implements RefreshTokenInterface
|
||||
{
|
||||
public function get($token)
|
||||
{
|
||||
$sql = 'SELECT oauth_refresh_tokens.*'
|
||||
. ' FROM oauth_refresh_tokens'
|
||||
. ' WHERE refresh_token = ?'
|
||||
. ' AND expires_at >= ?;';
|
||||
|
||||
$results = $this->db->fetch($sql, [$token, time()]);
|
||||
|
||||
if (count($results) === 1)
|
||||
{
|
||||
return (new RefreshTokenEntity($this->server))
|
||||
->setId($results[0]['refresh_token'])
|
||||
->setExpireTime($results[0]['expires_at'])
|
||||
->setAccessTokenId($results[0]['access_token_id']);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public function create($token, $expiration, $access_token)
|
||||
{
|
||||
$sql = 'SELECT id FROM oauth_access_tokens WHERE access_token = ?;';
|
||||
$results = $this->db->fetch($sql, [$access_token]);
|
||||
$token_id = $results[0]['id'];
|
||||
|
||||
$sql = 'INSERT INTO oauth_refresh_tokens'
|
||||
. ' (refresh_token, access_token_id, expires_at, client_id)'
|
||||
. ' VALUES'
|
||||
. ' (?, ?, ?, ?);';
|
||||
|
||||
$this->db->execute($sql, [
|
||||
$token,
|
||||
$token_id,
|
||||
$expiration,
|
||||
$this->server->getRequest()->request->get('client_id', null),
|
||||
]);
|
||||
}
|
||||
|
||||
public function delete(RefreshTokenEntity $token)
|
||||
{
|
||||
$sql = 'DELETE FROM oauth_refresh_tokens WHERE refresh_token = ?;';
|
||||
|
||||
$this->db->execute($sql, [$token->getId()]);
|
||||
}
|
||||
}
|
||||
|
|
@ -2,11 +2,10 @@
|
|||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \League\OAuth2\Exception\OAuthException;
|
||||
use \League\OAuth2\Server\AuthorizationServer;
|
||||
use \League\OAuth2\Server\Grant\PasswordGrant;
|
||||
use \League\OAuth2\Server\Grant\RefreshTokenGrant;
|
||||
use \Pickles\App\Models\User;
|
||||
use \OAuth2\GrantType\UserCredentials;
|
||||
use \OAuth2\Request;
|
||||
use \OAuth2\Response;
|
||||
use \OAuth2\Server;
|
||||
use \Pickles\Config;
|
||||
|
||||
class Resource extends \Pickles\Resource
|
||||
|
@ -26,17 +25,9 @@ class Resource extends \Pickles\Resource
|
|||
|
||||
switch (substr($_REQUEST['request'], strlen($_SERVER['__version']) + 2))
|
||||
{
|
||||
case 'oauth/access_token':
|
||||
case 'oauth2/token':
|
||||
try
|
||||
{
|
||||
$server = new AuthorizationServer;
|
||||
|
||||
$server->setSessionStorage(new SessionStorage);
|
||||
$server->setAccessTokenStorage(new AccessTokenStorage);
|
||||
$server->setClientStorage(new ClientStorage);
|
||||
$server->setScopeStorage(new ScopeStorage);
|
||||
$server->setRefreshTokenStorage(new RefreshTokenStorage);
|
||||
|
||||
$grant_type = $_REQUEST['grant_type'];
|
||||
$grants = ['password'];
|
||||
|
||||
|
@ -50,7 +41,7 @@ class Resource extends \Pickles\Resource
|
|||
throw new \Exception('Unsupported grant type.', 403);
|
||||
}
|
||||
|
||||
// Defaults TTLs to 1 day and 1 week respectively
|
||||
// @todo Defaults TTLs to 1 day and 1 week respectively
|
||||
$token_ttl = 3600;
|
||||
$refresh_ttl = 604800;
|
||||
|
||||
|
@ -74,51 +65,34 @@ class Resource extends \Pickles\Resource
|
|||
break;
|
||||
|
||||
case 'password':
|
||||
$grant = new PasswordGrant;
|
||||
$grant->setAccessTokenTTL($token_ttl);
|
||||
$storage = new Storage($this->mongo, ['user_table' => 'user']);
|
||||
$server = new Server($storage);
|
||||
|
||||
$grant->setVerifyCredentialsCallback(function ($username, $password)
|
||||
$server->addGrantType(new UserCredentials($storage));
|
||||
|
||||
$request = Request::createFromGlobals();
|
||||
$response = new Response;
|
||||
$response = $server->handleTokenRequest($request, $response);
|
||||
$body = json_decode($response->getResponseBody(), true);
|
||||
|
||||
if (isset($body['error']))
|
||||
{
|
||||
$user = new User([
|
||||
'conditions' => [
|
||||
'email' => $username,
|
||||
],
|
||||
]);
|
||||
$parameters = $response->getParameters();
|
||||
|
||||
return $user->count()
|
||||
&& password_verify($password, $user->record['password']);
|
||||
});
|
||||
throw new \Exception(
|
||||
$parameters['error_description'],
|
||||
$response->getStatusCode()
|
||||
);
|
||||
}
|
||||
|
||||
$response = $body;
|
||||
break;
|
||||
|
||||
case 'refresh_token':
|
||||
throw new \Exception('Not Implemented', 501);
|
||||
|
||||
// @todo Need to work through this, appears lib is busted
|
||||
$grant = new RefreshTokenGrant;
|
||||
//$grant->setAccessTokenTTL($refresh_ttl);
|
||||
$server->addGrantType($grant);
|
||||
break;
|
||||
}
|
||||
|
||||
$server->addGrantType($grant);
|
||||
|
||||
// Adds the refresh token grant if enabled
|
||||
if ($grant_type != 'refresh_token'
|
||||
&& in_array('refresh_token', $grants))
|
||||
{
|
||||
if (isset($config['ttl']['refresh_token']))
|
||||
{
|
||||
$refresh_ttl = $config['ttl']['refresh_token'];
|
||||
}
|
||||
|
||||
$grant = new RefreshTokenGrant;
|
||||
$grant->setAccessTokenTTL($refresh_ttl);
|
||||
$server->addGrantType($grant);
|
||||
}
|
||||
|
||||
$response = $server->issueAccessToken();
|
||||
|
||||
return $response;
|
||||
}
|
||||
catch (OAuthException $e)
|
||||
|
|
|
@ -1,26 +0,0 @@
|
|||
<?php
|
||||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \League\OAuth2\Server\Storage\Adapter;
|
||||
use \League\OAuth2\Server\Storage\ScopeInterface;
|
||||
|
||||
class ScopeStorage extends StorageAdapter implements ScopeInterface
|
||||
{
|
||||
public function get($scope, $grant_type = null, $client_id = null)
|
||||
{
|
||||
$sql = 'SELECT * FROM oauth_scopes WHERE id = ?;';
|
||||
$results = $this->db->fetch($sql, [$scope]);
|
||||
|
||||
if (count($results) === 0)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return (new ScopeEntity($this->server))->hydrate([
|
||||
'id' => $result[0]['id'],
|
||||
'description' => $result[0]['description'],
|
||||
]);
|
||||
}
|
||||
}
|
||||
|
|
@ -1,106 +0,0 @@
|
|||
<?php
|
||||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \League\OAuth2\Server\Entity\AccessTokenEntity;
|
||||
use \League\OAuth2\Server\Entity\AuthCodeEntity;
|
||||
use \League\OAuth2\Server\Entity\ScopeEntity;
|
||||
use \League\OAuth2\Server\Entity\SessionEntity;
|
||||
use \League\OAuth2\Server\Storage\Adapter;
|
||||
use \League\OAuth2\Server\Storage\SessionInterface;
|
||||
|
||||
class SessionStorage extends StorageAdapter implements SessionInterface
|
||||
{
|
||||
public function getByAccessToken(AccessTokenEntity $access_token)
|
||||
{
|
||||
$sql = 'SELECT oauth_sessions.id, oauth_sessions.owner_type,'
|
||||
. ' oauth_sessions.owner_id, oauth_sessions.client_id,'
|
||||
. ' oauth_sessions.client_redirect_uri'
|
||||
. ' FROM oauth_sessions'
|
||||
. ' INNER JOIN oauth_access_tokens'
|
||||
. ' ON oauth_access_tokens.session_id = oauth_sessions.id'
|
||||
. ' WHERE oauth_access_tokens.access_token = ?;';
|
||||
|
||||
$results = $this->db->fetch($sql, [$access_token->getId()]);
|
||||
|
||||
if (count($results) === 1)
|
||||
{
|
||||
$session = new SessionEntity($this->server);
|
||||
$session->setId($result[0]['id']);
|
||||
$session->setOwner($result[0]['owner_type'], $result[0]['owner_id']);
|
||||
|
||||
return $session;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public function getByAuthCode(AuthCodeEntity $auth_code)
|
||||
{
|
||||
$sql = 'SELECT oauth_sessions.id, oauth_sessions.owner_type,'
|
||||
. ' oauth_sessions.owner_id, oauth_sessions.client_id,'
|
||||
. ' oauth_sessions.client_redirect_uri'
|
||||
. ' FROM oauth_sessions'
|
||||
. ' INNER JOIN oauth_authorization_codes'
|
||||
. ' ON oauth_authorization_codes.session_id = oauth_sessions.id'
|
||||
. ' WHERE oauth_authorization_codes.authorization_code = ?;';
|
||||
|
||||
$results = $this->db->fetch($sql, [$auth_code->getId()]);
|
||||
|
||||
if (count($results) === 1)
|
||||
{
|
||||
$session = new SessionEntity($this->server);
|
||||
$session->setId($result[0]['id']);
|
||||
$session->setOwner($result[0]['owner_type'], $result[0]['owner_id']);
|
||||
|
||||
return $session;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public function getScopes(SessionEntity $session)
|
||||
{
|
||||
$sql = 'SELECT oauth_sessions.*'
|
||||
. ' FROM oauth_sessions'
|
||||
. ' INNER JOIN oauth_access_token_scopes'
|
||||
. ' ON oauth_sessions.id = oauth_access_token_scopes.access_token_id'
|
||||
. ' INNER JOIN oauth_scopes'
|
||||
. ' ON oauth_scopes.id = oauth_access_token_scopes.scope_id'
|
||||
. ' WHERE oauth_sessions.id = ?;';
|
||||
|
||||
$results = $this->db->fetch($sql, [$session->getId()]);
|
||||
$scopes = [];
|
||||
|
||||
foreach ($results as $scope)
|
||||
{
|
||||
$scopes[] = (new ScopeEntity($this->server))->hydrate([
|
||||
'id' => $scope['id'],
|
||||
'description' => $scope['description'],
|
||||
]);
|
||||
}
|
||||
|
||||
return $scopes;
|
||||
}
|
||||
|
||||
public function create($owner_type, $owner_id, $client_id, $client_redirect_uri = null)
|
||||
{
|
||||
$sql = 'INSERT INTO oauth_sessions'
|
||||
. ' (owner_type, owner_id, client_id)'
|
||||
. ' VALUES'
|
||||
. ' (?, ?, ?);';
|
||||
|
||||
return $this->db->execute($sql, [$owner_type, $owner_id, $client_id]);
|
||||
}
|
||||
|
||||
public function associateScope(SessionEntity $session, ScopeEntity $scope)
|
||||
{
|
||||
$sql = 'INSERT INTO oauth_access_token_scopes'
|
||||
. ' (access_token_id, scope_id)'
|
||||
. ' VALUES'
|
||||
. ' (?, ?);';
|
||||
|
||||
$this->db->execute($sql, [$session->getId(), $scope->getId()]);
|
||||
}
|
||||
}
|
||||
|
38
src/OAuth2/Storage.php
Normal file
38
src/OAuth2/Storage.php
Normal file
|
@ -0,0 +1,38 @@
|
|||
<?php
|
||||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \OAuth2\Storage\Mongo;
|
||||
|
||||
class Storage extends Mongo
|
||||
{
|
||||
private $mongo;
|
||||
|
||||
public function __construct($connection, $config = [])
|
||||
{
|
||||
parent::__construct($connection, $config);
|
||||
|
||||
$this->mongo = \Pickles\Mongo::getInstance();
|
||||
}
|
||||
|
||||
public function getUser($email)
|
||||
{
|
||||
return $this->mongo->user->findOne(['email' => $email]);
|
||||
}
|
||||
|
||||
public function getUserDetails($email)
|
||||
{
|
||||
if ($user = $this->getUser($email))
|
||||
{
|
||||
$user['user_id'] = $user['_id']->{'$id'};
|
||||
}
|
||||
|
||||
return $user;
|
||||
}
|
||||
|
||||
protected function checkPassword($user, $password)
|
||||
{
|
||||
return $user && password_verify($password, $user['password']);
|
||||
}
|
||||
}
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
<?php
|
||||
|
||||
namespace Pickles\OAuth2;
|
||||
|
||||
use \League\OAuth2\Server\Storage\Adapter;
|
||||
use \Pickles\Config;
|
||||
use \Pickles\Database;
|
||||
|
||||
class StorageAdapter extends Adapter
|
||||
{
|
||||
protected $config;
|
||||
protected $db;
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
$this->config = Config::getInstance();
|
||||
$this->db = Database::getInstance();
|
||||
}
|
||||
}
|
||||
|
0
src/Redis.php
Normal file
0
src/Redis.php
Normal file
|
@ -14,12 +14,6 @@
|
|||
|
||||
namespace Pickles;
|
||||
|
||||
use \League\OAuth2\Server\ResourceServer;
|
||||
use Pickles\OAuth2\AccessTokenStorage;
|
||||
use Pickles\OAuth2\ClientStorage;
|
||||
use Pickles\OAuth2\ScopeStorage;
|
||||
use Pickles\OAuth2\SessionStorage;
|
||||
|
||||
/**
|
||||
* Resource Class
|
||||
*
|
||||
|
@ -333,6 +327,37 @@ class Resource extends Object
|
|||
}
|
||||
}
|
||||
|
||||
// Create
|
||||
public function POST()
|
||||
{
|
||||
// @todo Whatever gets POSTed (aside from OAuth stuff) should be inserted to the collection
|
||||
}
|
||||
|
||||
// Read
|
||||
public function GET()
|
||||
{
|
||||
if (current($this->uids))
|
||||
{
|
||||
// @todo Pulls the record with this UID
|
||||
}
|
||||
else
|
||||
{
|
||||
// @todo Do we pull all or return an empty set?
|
||||
}
|
||||
}
|
||||
|
||||
// Update
|
||||
public function PUT()
|
||||
{
|
||||
// @todo If we have a UID, update the record with whatever is posted
|
||||
}
|
||||
|
||||
// Delete
|
||||
public function DELETE()
|
||||
{
|
||||
// @todo If we have a UID, delete it
|
||||
}
|
||||
|
||||
public function respond()
|
||||
{
|
||||
http_response_code($this->status);
|
||||
|
|
|
@ -54,7 +54,7 @@ class Router extends Object
|
|||
$_SERVER['__version'] = substr($version, 1);
|
||||
|
||||
// Checks if we're trying to rock some OAuth
|
||||
if ($components[0] == 'oauth')
|
||||
if ($components[0] == 'oauth2')
|
||||
{
|
||||
$class = 'Pickles\OAuth2\Resource';
|
||||
}
|
||||
|
@ -69,7 +69,8 @@ class Router extends Object
|
|||
}
|
||||
else
|
||||
{
|
||||
$nouns[] = $component;
|
||||
$nouns[] = $component;
|
||||
$uids[$component] = null;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue