Commit d45afda6 authored by sampaioprimo's avatar sampaioprimo

allow token to be created with unlimited timeout and maximum hits

parent e7f5f871
......@@ -10,6 +10,7 @@ class AuthTokens
const SCHEME = 'MD5( CONCAT(tokenId, creation, timeout, entry, parameters, groups) )';
private $db;
private $table;
private $dt;
private $maxTimeout = 3600;
private $maxHits = 1;
public $ok = false;
......@@ -21,10 +22,16 @@ class AuthTokens
) );
}
function __construct( $db, $options = array() ) {
function __construct( $db, $options = array(), DateTime $dt = null ) {
$this->db = $db;
$this->table = $this->db->table('tiki_auth_tokens');
if (is_null($dt)) {
$this->dt = new DateTime;
} else {
$this->dt = $dt;
}
if( isset( $options['maxTimeout'] ) ) {
$this->maxTimeout = (int) $options['maxTimeout'];
}
......@@ -46,7 +53,7 @@ class AuthTokens
}
function getGroups( $token, $entry, $parameters ) {
$this->db->query( 'DELETE FROM tiki_auth_tokens WHERE UNIX_TIMESTAMP(creation) + timeout < UNIX_TIMESTAMP() OR `hits` <= 0' );
$this->db->query( 'DELETE FROM tiki_auth_tokens WHERE (timeout != -1 AND UNIX_TIMESTAMP(creation) + timeout < ?) OR `hits` = 0', $this->dt->getTimestamp() );
$data = $this->db->query( 'SELECT tokenId, entry, parameters, groups FROM tiki_auth_tokens WHERE token = ? AND token = ' . self::SCHEME, array( $token ) )
->fetchRow();
......@@ -60,7 +67,7 @@ class AuthTokens
return null;
}
$this->db->query( 'UPDATE `tiki_auth_tokens` SET `hits` = `hits` - 1 WHERE `tokenId` = ?', array( $data['tokenId'] ) );
$this->db->query( 'UPDATE `tiki_auth_tokens` SET `hits` = `hits` - 1 WHERE `tokenId` = ? AND hits != -1', array( $data['tokenId'] ) );
$this->ok = true;
return (array) json_decode( $data['groups'], true );
}
......@@ -94,7 +101,8 @@ class AuthTokens
$email = '';
}
$this->db->query( 'INSERT INTO tiki_auth_tokens ( timeout, maxhits, hits, entry, parameters, groups, email ) VALUES( ?, ?, ?, ?, ?, ?, ? )', array(
$this->db->query( 'INSERT INTO tiki_auth_tokens ( creation, timeout, maxhits, hits, entry, parameters, groups, email ) VALUES( ?, ?, ?, ?, ?, ?, ?, ? )', array(
$this->dt->format('Y-m-d H:i:s'),
(int) $timeout,
(int) $hits,
(int) $hits,
......
......@@ -11,29 +11,34 @@
require_once 'lib/auth/tokens.php';
class AuthTokensTest extends PHPUnit_Framework_TestCase
class AuthTokensTest extends TikiDatabaseTestCase
{
private $db;
private $dt;
private $table;
private $obj;
public function getDataSet()
{
return $this->createMySQLXMLDataSet(dirname(__FILE__) . '/fixtures/auth_tokens_dataset.xml');
}
function setUp()
{
$this->db = TikiDb::get();
$this->db->query('TRUNCATE tiki_auth_tokens');
$this->dt = new DateTime;
// 2012-02-03 13:25:07
$this->dt->setTimestamp('1328282707');
$this->table = $this->db->table('tiki_auth_tokens');
$this->obj = new AuthTokens($this->db);
}
function tearDown()
{
if ($this->db) {
$this->db->query('TRUNCATE tiki_auth_tokens');
}
$this->obj = new AuthTokens($this->db, array(), $this->dt);
parent::setUp();
}
function testNoTokensIsDenied()
......@@ -46,38 +51,43 @@ class AuthTokensTest extends PHPUnit_Framework_TestCase
function testCreateToken()
{
$data = array(
'tokenId' => 1,
'tokenId' => 4,
'timeout' => 5,
'entry' => 'tiki-index.php',
'parameters' => '{"page":"HomePage"}',
'groups' => '["Registered"]',
);
$expectedTable = $this->createMySQLXmlDataSet(dirname(__FILE__) . '/fixtures/auth_tokens_dataset_create.xml')
->getTable('tiki_auth_tokens');
$token = $this->obj->createToken('tiki-index.php', array('page' => 'HomePage'), array('Registered'), array('timeout' => 5));
$this->assertEquals($data, $this->db->query('SELECT tokenId, timeout, entry, parameters, groups FROM tiki_auth_tokens')->fetchRow());
$queryTable = $this->getConnection()->createQueryTable('tiki_auth_tokens', 'SELECT * FROM tiki_auth_tokens');
$this->assertEquals($data, $this->db->query('SELECT tokenId, timeout, entry, parameters, groups FROM tiki_auth_tokens ORDER BY tokenId desc LIMIT 1')->fetchRow());
$this->assertEquals(32, strlen($token['token']));
$this->assertTablesEqual($expectedTable, $queryTable);
}
function testTokenMatchesCompleteHash()
{
$token = $this->obj->createToken('tiki-index.php', array('page' => 'HomePage'), array('Registered'));
$row = $this->db->query('SELECT tokenId, creation, timeout, entry, parameters, groups FROM tiki_auth_tokens')->fetchRow();
$row = $this->db->query('SELECT tokenId, creation, timeout, entry, parameters, groups FROM tiki_auth_tokens ORDER BY creation desc')->fetchRow();
$this->assertEquals(md5(implode('', $row)), $token['token']);
}
function testRetrieveGroupsForToken()
{
$this->dt->setTimestamp(time());
$token = $this->obj->createToken('tiki-index.php', array('page' => 'HomePage'), array('Registered'));
$this->assertEquals(array('Registered'), $this->obj->getGroups($token['token'], 'tiki-index.php', array('page' => 'HomePage')));
}
function testAccessExpiredToken()
{
$this->db->query('INSERT INTO tiki_auth_tokens (tokenId, creation, timeout, entry, parameters, groups, token) VALUES(?, ?, ?, ?, ?, ?, ?)', array(1, '2009-11-05 11:45:16', 5, 'tiki-index.php', '{"page":"HomePage"}', '["Registered"]', "946fc2fa0a5e1cecd54440ce733b8fb4"));
$this->assertNull($this->obj->getGroups("946fc2fa0a5e1cecd54440ce733b8fb4", 'tiki-index.php', array('page' => 'HomePage')));
}
......@@ -114,6 +124,7 @@ class AuthTokensTest extends PHPUnit_Framework_TestCase
function testNoParamerers()
{
$this->dt->setTimestamp(time());
$token = $this->obj->createToken('tiki-index.php', array(), array('Registered'));
$this->assertEquals(array('Registered'), $this->obj->getGroups($token['token'], 'tiki-index.php', array()));
}
......@@ -125,7 +136,7 @@ class AuthTokensTest extends PHPUnit_Framework_TestCase
));
$token = $lib->createToken('tiki-index.php', array('page' => 'HomePage'), array('Registered'), array('timeout' => 3600));
$this->assertEquals(10, $this->db->getOne('SELECT timeout FROM tiki_auth_tokens WHERE tokenId = 1'));
$this->assertEquals(10, $this->db->getOne('SELECT timeout FROM tiki_auth_tokens ORDER BY creation desc'));
}
function testSameTokenTwice()
......@@ -186,22 +197,22 @@ class AuthTokensTest extends PHPUnit_Framework_TestCase
function testGetTokens_shouldReturnEmptyArrayIfNoToken()
{
$this->db->query('TRUNCATE tiki_auth_tokens');
$this->assertEquals(array(), $this->obj->getTokens());
}
function testGetTokens_shouldReturnAllTokens()
{
$url1 = 'tiki-index.php';
$url2 = 'tiki-user_send_reports.php';
$this->obj->createToken($url1, array('page' => 'HomePage'), array('Registered'));
$this->obj->createToken($url2, array(), array('Admin'));
$token1 = '823bde97a717c55b2cfbf9fbd6c81816';
$token2 = '91bba2f998b48fce0146016809886127';
$token3 = 'e2990f7983b7b6c46b3987536aa38d32';
$tokens = $this->obj->getTokens();
$this->assertEquals(2, count($tokens));
$this->assertEquals($url1, $tokens[0]['entry']);
$this->assertEquals($url2, $tokens[1]['entry']);
$this->assertEquals(3, count($tokens));
$this->assertEquals($token1, $tokens[0]['token']);
$this->assertEquals($token2, $tokens[1]['token']);
$this->assertEquals($token3, $tokens[2]['token']);
}
function testDeleteToken()
......@@ -212,5 +223,51 @@ class AuthTokensTest extends PHPUnit_Framework_TestCase
$this->assertEmpty($this->table->fetchRow(array('entry'), array('tokenId' => $token['tokenId'])));
}
function testGetGroups_shouldDeleteExpiredTokens()
{
$expectedTable = $this->createMySQLXmlDataSet(dirname(__FILE__) . '/fixtures/auth_tokens_dataset_delete_timeout.xml')
->getTable('tiki_auth_tokens');
$this->obj->getGroups('bcbcbf5a4fffa9cd734ec8aec6c66c2a', 'tiki-index.php', array());
$queryTable = $this->getConnection()->createQueryTable('tiki_auth_tokens', 'SELECT * FROM tiki_auth_tokens');
$this->assertTablesEqual($expectedTable, $queryTable);
}
function testGetGroups_shouldDeleteTokensWithoutHitsLeft()
{
// 2012-02-01 13:25:07
$this->dt->setTimestamp('1328109907');
$this->db->query('UPDATE tiki_auth_tokens set maxHits = -1, hits = -1 WHERE tokenId = 1');
$this->db->query('UPDATE tiki_auth_tokens set maxHits = 10, hits = 0 WHERE tokenId = 2');
$expectedTable = $this->createMySQLXmlDataSet(dirname(__FILE__) . '/fixtures/auth_tokens_dataset_delete_hits.xml')
->getTable('tiki_auth_tokens');
$this->obj->getGroups('91bba2f998b48fce0146016809886127', 'tiki-index.php', array());
$queryTable = $this->getConnection()->createQueryTable('tiki_auth_tokens', 'SELECT * FROM tiki_auth_tokens');
$this->assertTablesEqual($expectedTable, $queryTable);
}
function testGetGroups_shouldDecrementHits()
{
$this->obj->getGroups('91bba2f998b48fce0146016809886127', 'tiki-index.php', array());
$this->assertEquals('9', $this->db->getOne('SELECT hits FROM tiki_auth_tokens WHERE tokenId = 2'));
}
function testGetGroups_shouldDecrementIfUnlimitedHits()
{
$this->db->query('UPDATE tiki_auth_tokens set maxHits = -1, hits = -1 WHERE tokenId = 2');
$this->obj->getGroups('91bba2f998b48fce0146016809886127', 'tiki-index.php', array());
$this->assertEquals('-1', $this->db->getOne('SELECT hits FROM tiki_auth_tokens WHERE tokenId = 2'));
}
}
......@@ -41,19 +41,26 @@
{/tab}
{tab name="{tr}Add new token{/tr}"}
<h2>{tr}Add new token{/tr}</h2>
{if $tokenCreated}
{remarksbox type="note" title="{tr}Note{/tr}"}
{tr}Token successfully created.{/tr}
{/remarksbox}
{/if}
<form action="tiki-admin_tokens.php" method="post">
<input type="hidden" name="action" value="add" />
<table class="formcolor">
<tr>
<td><label for='entry'>{tr}URL{/tr}</label></td>
<td><label for='entry'>{tr}Full URL{/tr}</label></td>
<td><input type="text" id='entry' name='entry' /></td>
</tr>
<tr>
<td><label for='timeout'>{tr}Timeout (in seconds){/tr}</label></td>
<td><label for='timeout'>{tr}Timeout in seconds (-1 for unlimited){/tr}</label></td>
<td><input type="text" id='timeout' name='timeout' /></td>
</tr>
<tr>
<td><label for='maxhits'>{tr}Maximum number of hits{/tr}</label></td>
<td><label for='maxhits'>{tr}Maximum number of hits (-1 for unlimited){/tr}</label></td>
<td><input type="text" id='maxhits' name='maxhits' /></td>
</tr>
<tr>
......
......@@ -15,6 +15,7 @@ $tokenlib = AuthTokens::build($prefs);
$action = '';
$tokenId = 0;
$smarty->assign('tokenCreated', false);
if (isset($_REQUEST['action'])) {
$action = $_REQUEST['action'];
......@@ -30,6 +31,7 @@ if ($action == 'delete' && $tokenId > 0) {
if ($action == 'add') {
$entry = filter_input(INPUT_POST, 'entry', FILTER_SANITIZE_STRING);
$entry = parse_url($entry, PHP_URL_PATH);
$groups = filter_input(INPUT_POST, 'groups', FILTER_SANITIZE_STRING);
$groups = str_replace(' ', '', $groups);
......@@ -40,12 +42,21 @@ if ($action == 'add') {
$arguments['hits'] = filter_input(INPUT_POST, 'maxhits', FILTER_SANITIZE_NUMBER_INT);
if (!empty($entry) && !empty($groups)) {
$tokenlib->createToken($entry, array(), $groups, $arguments);
$token = $tokenlib->createToken($entry, array(), $groups, $arguments);
if (!empty($token)) {
$smarty->assign('tokenCreated', true);
}
}
}
$tokens = $tokenlib->getTokens();
foreach ($tokens as $key => $token) {
$tokens[$key]['groups'] = join(', ', json_decode($token['groups']));
$tokens[$key]['parameters'] = join(', ', json_decode($token['parameters']));
}
$smarty->assign('tokens', $tokens);
$smarty->assign('mid', 'tiki-admin_tokens.tpl');
$smarty->display('tiki.tpl');
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment