*/
class DatabaseLockDriver extends AbstractLockDriver
{
+ /**
+ * The current ID of the process
+ *
+ * @var int
+ */
+ private $pid;
+
+ /**
+ * @param null|int $pid The Id of the current process (null means determine automatically)
+ */
+ public function __construct($pid = null)
+ {
+ $this->pid = isset($pid) ? $pid : getmypid();
+ }
+
/**
* (@inheritdoc)
*/
if (DBA::isResult($lock)) {
if ($lock['locked']) {
// We want to lock something that was already locked by us? So we got the lock.
- if ($lock['pid'] == getmypid()) {
+ if ($lock['pid'] == $this->pid) {
$got_lock = true;
}
}
if (!$lock['locked']) {
- DBA::update('locks', ['locked' => true, 'pid' => getmypid(), 'expires' => DateTimeFormat::utc('now + ' . $ttl . 'seconds')], ['name' => $key]);
+ DBA::update('locks', ['locked' => true, 'pid' => $this->pid, 'expires' => DateTimeFormat::utc('now + ' . $ttl . 'seconds')], ['name' => $key]);
$got_lock = true;
}
} else {
- DBA::insert('locks', ['name' => $key, 'locked' => true, 'pid' => getmypid(), 'expires' => DateTimeFormat::utc('now + ' . $ttl . 'seconds')]);
+ DBA::insert('locks', ['name' => $key, 'locked' => true, 'pid' => $this->pid, 'expires' => DateTimeFormat::utc('now + ' . $ttl . 'seconds')]);
$got_lock = true;
$this->markAcquire($key);
}
*/
public function releaseLock($key)
{
- DBA::delete('locks', ['name' => $key, 'pid' => getmypid()]);
+ DBA::delete('locks', ['name' => $key, 'pid' => $this->pid]);
$this->markRelease($key);
*/
public function releaseAll()
{
- DBA::delete('locks', ['pid' => getmypid()]);
+ DBA::delete('locks', ['pid' => $this->pid]);
$this->acquiredLocks = [];
}
use Mockery\MockInterface;
+class DBAStub
+{
+ public static $connected = true;
+}
+
/**
* Trait to mock the DBA connection status
*/
*/
private $dbaMock;
+ private function checkMock()
+ {
+ if (!isset($this->dbaMock)) {
+ $this->dbaMock = \Mockery::namedMock('Friendica\Database\DBA', 'Friendica\Test\Util\DBAStub');
+ }
+ }
+
/**
* Mocking DBA::connect()
*
*/
public function mockConnect($return = true, $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
$this->dbaMock
->shouldReceive('connect')
*/
public function mockConnected($return = true, $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
$this->dbaMock
->shouldReceive('connected')
*/
public function mockFetchFirst($arg, $return = true, $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
$this->dbaMock
->shouldReceive('fetchFirst')
->andReturn($return);
}
+ /**
+ * Mocking each DBA::fetch() call of an statement
+ *
+ * @param array $stmt The result statement (array)
+ * @param null|int $times How often the method will get used
+ */
+ public function mockFetchLoop($stmt = [], $times = null)
+ {
+ $this->checkMock();
+
+ foreach ($stmt as $item) {
+ $this->dbaMock
+ ->shouldReceive('fetch')
+ ->times($times)
+ ->andReturn($item);
+ }
+
+ // The last mock call of a fetch (=> breaking the loop)
+ $this->dbaMock
+ ->shouldReceive('fetch')
+ ->times($times)
+ ->andReturn(false);
+ }
+
+ /**
+ * Mocking DBA::close()
+ *
+ * @param array $return The return per fetch
+ * @param null|int $times How often the method will get used
+ */
+ public function mockDbaClose($return = [], $times = null)
+ {
+ $this->checkMock();
+
+ $this->dbaMock
+ ->shouldReceive('close')
+ ->times($times)
+ ->andReturn($return);
+ }
/**
* Mocking DBA::select()
*/
public function mockSelect($tableName, $select = [], $where = [], $return = null, $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
$this->dbaMock
->shouldReceive('select')
}
/**
- * Mocking DBA::selectFirst()
+ * Mocking DBA::delete()
*
* @param string $tableName The name of the table
- * @param array $select The Select Array (Default is [])
* @param array $where The Where Array (Default is [])
+ * @param bool $return The array to return (Default is true)
+ * @param null|int $times How often the method will get used
+ */
+ public function mockDBADelete($tableName, $where = [], $return = true, $times = null)
+ {
+ $this->checkMock();
+
+ $this->dbaMock
+ ->shouldReceive('delete')
+ ->with($tableName, $where)
+ ->times($times)
+ ->andReturn($return);
+ }
+
+ /**
+ * Mocking DBA::update()
+ *
+ * @param string $expTableName The name of the table
+ * @param array $expFields The Fields Array
+ * @param array $expCondition The Condition Array
+ * @param array $expOld_fields The Old Fieldnames (Default is [])
+ * @param bool $return true if the update was successful
+ * @param null|int $times How often the method will get used
+ */
+ public function mockDBAUpdate($expTableName, $expFields, $expCondition, $expOld_fields = [], $return = true, $times = null)
+ {
+ $this->checkMock();
+
+ $closure = function ($tableName, $fields, $condition, $old_fields = []) use ($expTableName, $expFields, $expCondition, $expOld_fields) {
+ return
+ $tableName == $expTableName &&
+ $fields == $expFields &&
+ $condition == $expCondition &&
+ $old_fields == $expOld_fields;
+ };
+
+ $this->dbaMock
+ ->shouldReceive('update')
+ ->withArgs($closure)
+ ->times($times)
+ ->andReturn($return);
+ }
+
+ /**
+ * Mocking DBA::insert()
+ *
+ * @param string $expTableName The name of the table
+ * @param array $expParam The Parameters Array
+ * @param bool $expOnDuplUpdate Update on a duplicated entry
+ * @param bool $return True if the insert was successful
+ * @param null|int $times How often the method will get used
+ */
+ public function mockDBAInsert($expTableName, $expParam, $expOnDuplUpdate = false, $return = true, $times = null)
+ {
+ $this->checkMock();
+
+ $closure = function ($tableName, $param, $on_duplicate_update = false) use ($expTableName, $expParam, $expOnDuplUpdate) {
+ return $tableName == $expTableName
+ && $param == $expParam
+ && $on_duplicate_update == $expOnDuplUpdate;
+
+ };
+
+ $this->dbaMock
+ ->shouldReceive('insert')
+ ->withArgs($closure)
+ ->times($times)
+ ->andReturn($return);
+ }
+
+ /**
+ * Mocking DBA::selectFirst()
+ *
+ * @param string $expTableName The name of the table
+ * @param array $expSelect The Select Array (Default is [])
+ * @param array $expWhere The Where Array (Default is [])
* @param array $return The array to return (Default is [])
* @param null|int $times How often the method will get used
*/
- public function mockSelectFirst($tableName, $select = [], $where = [], $return = [], $times = null)
+ public function mockSelectFirst($expTableName, $expSelect = [], $expWhere = [], $return = [], $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
+
+ $closure = function ($tableName, $select = [], $where = []) use ($expTableName, $expSelect, $expWhere) {
+ return $tableName === $expTableName
+ && $select === $expSelect
+ && $where === $expWhere;
+ };
$this->dbaMock
->shouldReceive('selectFirst')
- ->with($tableName, $select, $where)
+ ->withArgs($closure)
->times($times)
->andReturn($return);
}
*/
public function mockIsResult($record, $return = true, $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
$this->dbaMock
->shouldReceive('isResult')
*/
public function mockToArray($record = null, $return = [], $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
$this->dbaMock
->shouldReceive('toArray')
->andReturn($return);
}
-
/**
* Mocking DBA::p()
*
*/
public function mockP($sql = null, $return = null, $times = null)
{
- if (!isset($this->dbaMock)) {
- $this->dbaMock = \Mockery::mock('alias:Friendica\Database\DBA');
- }
+ $this->checkMock();
if (!isset($sql)) {
$this->dbaMock
->andReturn($return);
}
}
+
+ /**
+ * Mocking DBA::lock()
+ *
+ * @param string $table The table to lock
+ * @param bool $return True, if the lock is set successful
+ * @param null|int $times How often the method will get used
+ */
+ public function mockDbaLock($table, $return = true, $times = null)
+ {
+ $this->checkMock();
+
+ $this->dbaMock
+ ->shouldReceive('lock')
+ ->with($table)
+ ->times($times)
+ ->andReturn($return);
+ }
+
+ /**
+ * Mocking DBA::unlock()
+ *
+ * @param bool $return True, if the lock is set successful
+ * @param null|int $times How often the method will get used
+ */
+ public function mockDbaUnlock( $return = true, $times = null)
+ {
+ $this->checkMock();
+
+ $this->dbaMock
+ ->shouldReceive('unlock')
+ ->times($times)
+ ->andReturn($return);
+ }
}
--- /dev/null
+<?php
+
+namespace Friendica\Test\Util;
+
+use Mockery\MockInterface;
+
+trait DateTimeFormatMockTrait
+{
+ /**
+ * @var MockInterface The mocking interface of Friendica\Database\DBA
+ */
+ private $dtfMock;
+
+ public function mockUtcNow($time, $times = null)
+ {
+ if (!isset($this->dtfMock)) {
+ $this->dtfMock = \Mockery::mock('alias:Friendica\Util\DateTimeFormat');
+ }
+
+ $this->dtfMock
+ ->shouldReceive('utcNow')
+ ->andReturn($time)
+ ->times($times);
+ }
+
+ public function mockUtc($input, $time, $times = null)
+ {
+ if (!isset($this->dtfMock)) {
+ $this->dtfMock = \Mockery::mock('alias:Friendica\Util\DateTimeFormat');
+ }
+
+ $this->dtfMock
+ ->shouldReceive('utc')
+ ->with($input)
+ ->andReturn($time)
+ ->times($times);
+ }
+}
--- /dev/null
+<?php
+
+namespace Friendica\Test\Util;
+
+trait DbaCacheMockTrait
+{
+ use DBAMockTrait;
+ use DateTimeFormatMockTrait;
+
+ protected function mockDelete($key, $return = true, $times = null)
+ {
+ $this->mockDBADelete('cache', ['k' => $key], $return, $times);
+ }
+
+ protected function mockGet($key, $return = null, $time = null, $times = null)
+ {
+ if ($time === null) {
+ $time = time();
+ }
+
+ $value = @serialize($return);
+
+ $this->mockSelectFirst('cache', ['v'], ['`k` = ? AND (`expires` >= ? OR `expires` = -1)', $key, $time], ['v' => $value], $times);
+ $this->mockIsResult(['v' => $value], isset($return), $times);
+ }
+
+ protected function mockSet($key, $value, $ttl = Cache::FIVE_MINUTES, $time = null, $return = true, $times = null)
+ {
+ if ($time === null) {
+ $time = time();
+ }
+
+ if ($ttl > 0) {
+ $this->mockUtc('now + ' . $ttl . 'seconds', $time + $ttl, $times);
+ $fields = [
+ 'v' => serialize($value),
+ 'expires' => $time + $ttl,
+ 'updated' => $time
+ ];
+ } else {
+ $fields = [
+ 'v' => serialize($value),
+ 'expires' => -1,
+ 'updated' => $time
+ ];
+ }
+
+ $this->mockDBAUpdate('cache', $fields, ['k' => $key], true, $return, $times);
+ }
+
+ protected function mockClear($outdated = true, $return = true, $times = null)
+ {
+ if ($outdated) {
+ $this->mockDBADelete('cache', ['`expires` < NOW()'], $return, $times);
+ } else {
+ $this->mockDBADelete('cache', ['`k` IS NOT NULL '], $return, $times);
+ }
+ }
+
+ protected function mockGetAllKeys($prefix = null, $return = [], $time = null, $times = null)
+ {
+ if ($time === null) {
+ $time = time();
+ }
+
+ if (empty($prefix)) {
+ $where = ['`expires` >= ?', $time];
+ } else {
+ $where = ['`expires` >= ? AND `k` LIKE CONCAT(?, \'%\')', $time, $prefix];
+ }
+
+ $this->mockSelect('cache', ['k'], $where, $return, $times);
+ $this->mockFetchLoop($return, $times);
+ $this->mockDbaClose(true, $times);
+ }
+}
--- /dev/null
+<?php
+
+namespace Friendica\Test\Util;
+
+use Friendica\Core\Cache;
+use Friendica\Core\Lock\DatabaseLockDriver;
+
+trait DbaLockMockTrait
+{
+ use DBAMockTrait;
+ use DateTimeFormatMockTrait;
+
+ /**
+ * Mocking acquireLock with DBA-backend
+ * @see DatabaseLockDriver::acquireLock()
+ *
+ * @param mixed $key The key to lock
+ * @param int $ttl The TimeToLive
+ *
+ * @param bool $locked Was the lock already set?
+ * @param null $pid The PID which was set
+ * @param bool $rowExists True, if a row already exists in the lock table
+ * @param null $time The current timestamp
+ * @param null|int $times How often the method will get used
+ */
+ public function mockAcquireLock($key, $ttl = Cache::FIVE_MINUTES, $locked = false, $pid = null, $rowExists = true, $time = null, $times = null)
+ {
+ if ($time === null) {
+ $time = time();
+ }
+
+ if ($pid === null) {
+ $pid = getmypid();
+ }
+
+ $this->mockDbaLock('locks', true, $times);
+
+ $this->mockUtcNow($time, $times);
+ $result = ['locked' => $locked, 'pid' => $pid];
+ $this->mockSelectFirst('locks', ['locked', 'pid'], ['`name` = ? AND `expires` >= ?', $key, $time], $result, $times);
+ $this->mockIsResult($result, $rowExists, $times);
+
+ if ($rowExists) {
+ if (!$locked ) {
+ $this->mockUtc('now + ' . $ttl . 'seconds', $time, $times);
+ $this->mockDBAUpdate('locks', ['locked' => true, 'pid' => $pid, 'expires' => $time], ['name' => $key], [], true, $times);
+ }
+ } else {
+ $this->mockUtc('now + ' . $ttl . 'seconds', $time, $times);
+ $this->mockDBAInsert('locks', ['name' => $key, 'locked' => true, 'pid' => $pid, 'expires' => $time], false, true, $times);
+ }
+
+ $this->mockDbaUnlock($times);
+ }
+
+ /**
+ * Mocking isLocked with DBA-backend
+ * @see DatabaseLockDriver::isLocked()
+ *
+ * @param mixed $key The key of the lock
+ * @param null|bool $return True, if the key is already locked
+ * @param null $time The current timestamp
+ * @param null|int $times How often the method will get used
+ */
+ public function mockIsLocked($key, $return = true, $time = null, $times = null)
+ {
+ if ($time === null) {
+ $time = time();
+ }
+
+ $this->mockUtcNow($time, $times);
+ $return = ((isset($return)) ? ['locked' => $return] : null);
+ $this->mockSelectFirst('locks', ['locked'], ['`name` = ? AND `expires` >= ?', $key, $time], $return, $times);
+ $this->mockIsResult($return, (isset($return) && $return), $times);
+ }
+
+ /**
+ * Mocking releaseAll with DBA-backend
+ * @see DatabaseLockDriver::releaseAll()
+ *
+ * @param null $pid The PID which was set
+ * @param null|int $times How often the method will get used
+ */
+ public function mockReleaseAll($pid = null, $times = null)
+ {
+ if ($pid === null) {
+ $pid = getmypid();
+ }
+
+ $this->mockDBADelete('locks', ['pid' => $pid], true, $times);
+ }
+
+ /**
+ * Mocking ReleaseLock with DBA-backend
+ * @see DatabaseLockDriver::releaseLock()
+ *
+ * @param mixed $key The key to release
+ * @param null|int $pid The PID which was set
+ * @param null|int $times How often the method will get used
+ */
+ public function mockReleaseLock($key, $pid = null, $times = null)
+ {
+ if ($pid === null) {
+ $pid = getmypid();
+ }
+
+ $this->mockDBADelete('locks', ['name' => $key, 'pid' => $pid], true, $times);
+ }
+}
use Friendica\App;
use Friendica\BaseObject;
-use Friendica\Util\LoggerFactory;
+use Friendica\Test\Util\AppMockTrait;
+use Friendica\Test\Util\VFSTrait;
use PHPUnit\Framework\TestCase;
/**
* Tests for the BaseObject class.
+ * @runTestsInSeparateProcesses
+ * @preserveGlobalState disabled
*/
class BaseObjectTest extends TestCase
{
+ use VFSTrait;
+ use AppMockTrait;
+
+ /**
+ * @var BaseObject
+ */
+ private $baseObject;
/**
* Create variables used in tests.
*/
protected function setUp()
{
+ $this->setUpVfsDir();
+ $this->mockApp($this->root);
+
$this->baseObject = new BaseObject();
}
*/
public function testSetApp()
{
- $logger = $logger = LoggerFactory::create('test');
- $app = new App(__DIR__ . '/../../', $logger);
- LoggerFactory::enableTest($logger);
- $this->assertNull($this->baseObject->setApp($app));
- $this->assertEquals($app, $this->baseObject->getApp());
+ $this->assertNull($this->baseObject->setApp($this->app));
+ $this->assertEquals($this->app, $this->baseObject->getApp());
}
}
namespace Friendica\Test\src\Core\Cache;
use Friendica\Core\Cache\MemcachedCacheDriver;
-use Friendica\Core\Config;
-use Friendica\Test\DatabaseTest;
-use Friendica\Util\DateTimeFormat;
+use Friendica\Test\MockedTest;
+use Friendica\Test\Util\AppMockTrait;
+use Friendica\Test\Util\DateTimeFormatMockTrait;
+use Friendica\Test\Util\VFSTrait;
+use Friendica\Util\PidFile;
-abstract class CacheTest extends DatabaseTest
+abstract class CacheTest extends MockedTest
{
+ use VFSTrait;
+ use AppMockTrait;
+ use DateTimeFormatMockTrait;
+
+ /**
+ * @var int Start time of the mock (used for time operations)
+ */
+ protected $startTime = 1417011228;
+
/**
* @var \Friendica\Core\Cache\ICacheDriver
*/
*/
protected $cache;
+ /**
+ * Dataset for test setting different types in the cache
+ * @return array
+ */
+ public function dataTypesInCache()
+ {
+ return [
+ 'string' => ['data' => 'foobar'],
+ 'integer' => ['data' => 1],
+ 'boolTrue' => ['data' => true],
+ 'boolFalse' => ['data' => false],
+ 'float' => ['data' => 4.6634234],
+ 'array' => ['data' => ['1', '2', '3', '4', '5']],
+ 'object' => ['data' => new PidFile()],
+ 'null' => ['data' => null],
+ ];
+ }
+
+ /**
+ * Dataset for simple value sets/gets
+ * @return array
+ */
+ public function dataSimple()
+ {
+ return [
+ 'string' => [
+ 'value1' => 'foobar',
+ 'value2' => 'ipsum lorum',
+ 'value3' => 'test',
+ 'value4' => 'lasttest',
+ ],
+ ];
+ }
abstract protected function getInstance();
protected function setUp()
{
+ $this->setUpVfsDir();
+ $this->mockApp($this->root);
+ $this->app
+ ->shouldReceive('getHostname')
+ ->andReturn('friendica.local');
+
+ $this->mockUtcNow($this->startTime);
+
parent::setUp();
- $this->instance = $this->getInstance();
- // Reusable App object
- $this->app = \Friendica\BaseObject::getApp();
+ $this->instance = $this->getInstance();
// Default config
- Config::set('config', 'hostname', 'localhost');
- Config::set('system', 'throttle_limit_day', 100);
- Config::set('system', 'throttle_limit_week', 100);
- Config::set('system', 'throttle_limit_month', 100);
- Config::set('system', 'theme', 'system_theme');
+ $this->mockConfigGet('config', 'hostname', 'localhost');
+ $this->mockConfigGet('system', 'throttle_limit_day', 100);
+ $this->mockConfigGet('system', 'throttle_limit_week', 100);
+ $this->mockConfigGet('system', 'throttle_limit_month', 100);
+ $this->mockConfigGet('system', 'theme', 'system_theme');
$this->instance->clear(false);
}
/**
* @small
+ * @dataProvider dataSimple
+ * @param mixed $value1 a first
+ * @param mixed $value2 a second
*/
- function testSimple() {
+ function testSimple($value1, $value2) {
$this->assertNull($this->instance->get('value1'));
- $value = 'foobar';
- $this->instance->set('value1', $value);
+ $this->instance->set('value1', $value1);
$received = $this->instance->get('value1');
- $this->assertEquals($value, $received, 'Value received from cache not equal to the original');
+ $this->assertEquals($value1, $received, 'Value received from cache not equal to the original');
- $value = 'ipsum lorum';
- $this->instance->set('value1', $value);
+ $this->instance->set('value1', $value2);
$received = $this->instance->get('value1');
- $this->assertEquals($value, $received, 'Value not overwritten by second set');
+ $this->assertEquals($value2, $received, 'Value not overwritten by second set');
- $value2 = 'foobar';
- $this->instance->set('value2', $value2);
+ $this->instance->set('value2', $value1);
$received2 = $this->instance->get('value2');
- $this->assertEquals($value, $received, 'Value changed while setting other variable');
- $this->assertEquals($value2, $received2, 'Second value not equal to original');
+ $this->assertEquals($value2, $received, 'Value changed while setting other variable');
+ $this->assertEquals($value1, $received2, 'Second value not equal to original');
$this->assertNull($this->instance->get('not_set'), 'Unset value not equal to null');
/**
* @small
+ * @dataProvider dataSimple
+ * @param mixed $value1 a first
+ * @param mixed $value2 a second
+ * @param mixed $value3 a third
+ * @param mixed $value4 a fourth
*/
- function testClear() {
+ function testClear($value1, $value2, $value3, $value4) {
$value = 'ipsum lorum';
- $this->instance->set('1_value1', $value . '1');
- $this->instance->set('1_value2', $value . '2');
- $this->instance->set('2_value1', $value . '3');
- $this->instance->set('3_value1', $value . '4');
+ $this->instance->set('1_value1', $value1);
+ $this->instance->set('1_value2', $value2);
+ $this->instance->set('2_value1', $value3);
+ $this->instance->set('3_value1', $value4);
$this->assertEquals([
- '1_value1' => 'ipsum lorum1',
- '1_value2' => 'ipsum lorum2',
- '2_value1' => 'ipsum lorum3',
- '3_value1' => 'ipsum lorum4',
+ '1_value1' => $value1,
+ '1_value2' => $value2,
+ '2_value1' => $value3,
+ '3_value1' => $value4,
], [
'1_value1' => $this->instance->get('1_value1'),
'1_value2' => $this->instance->get('1_value2'),
$this->assertTrue($this->instance->clear());
$this->assertEquals([
- '1_value1' => 'ipsum lorum1',
- '1_value2' => 'ipsum lorum2',
- '2_value1' => 'ipsum lorum3',
- '3_value1' => 'ipsum lorum4',
+ '1_value1' => $value1,
+ '1_value2' => $value2,
+ '2_value1' => $value3,
+ '3_value1' => $value4,
], [
'1_value1' => $this->instance->get('1_value1'),
'1_value2' => $this->instance->get('1_value2'),
/**
* @small
+ * @param $data mixed the data to store in the cache
+ * @dataProvider dataTypesInCache
*/
- function testDifferentTypesInCache() {
- // String test
- $value = "foobar";
- $this->instance->set('stringVal', $value);
- $received = $this->instance->get('stringVal');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
-
- // Integer test
- $value = 1;
- $this->instance->set('intVal', $value);
- $received = $this->instance->get('intVal');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
-
- // Boolean test
- $value = true;
- $this->instance->set('boolValTrue', $value);
- $received = $this->instance->get('boolValTrue');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
-
- $value = false;
- $this->instance->set('boolValFalse', $value);
- $received = $this->instance->get('boolValFalse');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
-
- // float
- $value = 4.6634234;
- $this->instance->set('decVal', $value);
- $received = $this->instance->get('decVal');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
-
- // array
- $value = array('1', '2', '3', '4', '5');
- $this->instance->set('arrayVal', $value);
- $received = $this->instance->get('arrayVal');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
-
- // object
- $value = new DateTimeFormat();
- $this->instance->set('objVal', $value);
- $received = $this->instance->get('objVal');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
-
- // null
- $value = null;
- $this->instance->set('objVal', $value);
- $received = $this->instance->get('objVal');
- $this->assertEquals($value, $received, 'Value type changed from ' . gettype($value) . ' to ' . gettype($received));
+ function testDifferentTypesInCache($data) {
+ $this->instance->set('val', $data);
+ $received = $this->instance->get('val');
+ $this->assertEquals($data, $received, 'Value type changed from ' . gettype($data) . ' to ' . gettype($received));
}
/**
* @small
+ * @param mixed $value1 a first
+ * @param mixed $value2 a second
+ * @param mixed $value3 a third
+ * @dataProvider dataSimple
*/
- public function testGetAllKeys() {
+ public function testGetAllKeys($value1, $value2, $value3) {
if ($this->cache instanceof MemcachedCacheDriver) {
$this->markTestSkipped('Memcached doesn\'t support getAllKeys anymore');
}
- $this->assertTrue($this->instance->set('value1', 'test'));
- $this->assertTrue($this->instance->set('value2', 'test'));
- $this->assertTrue($this->instance->set('test_value3', 'test'));
+ $this->assertTrue($this->instance->set('value1', $value1));
+ $this->assertTrue($this->instance->set('value2', $value2));
+ $this->assertTrue($this->instance->set('test_value3', $value3));
$list = $this->instance->getAllKeys();
namespace Friendica\Test\src\Core\Cache;
+use Friendica\Core\Cache;
use Friendica\Core\Cache\CacheDriverFactory;
+use Friendica\Test\Util\DbaCacheMockTrait;
/**
* @runTestsInSeparateProcesses
*/
class DatabaseCacheDriverTest extends CacheTest
{
+ use DbaCacheMockTrait;
+
+ public function setUp()
+ {
+ $this->mockConnected();
+ $this->mockConnect();
+
+ // The first "clear" at setup
+ $this->mockClear(false, true, 2);
+
+ parent::setUp();
+ }
+
protected function getInstance()
{
$this->cache = CacheDriverFactory::create('database');
$this->cache->clear(false);
parent::tearDown();
}
+
+ /**
+ * {@inheritdoc}
+ * @dataProvider dataSimple
+ */
+ public function testSimple($value1, $value2)
+ {
+ // assertNull
+ $this->mockGet('value1', null, $this->startTime, 1);
+
+ // assertEquals
+ $this->mockSet('value1', $value1, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockGet('value1', $value1, $this->startTime, 1);
+
+ // assertEquals
+ $this->mockSet('value1', $value2, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockGet('value1', $value2, $this->startTime, 1);
+
+ // assertEquals
+ $this->mockSet('value2', $value1, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockGet('value2', $value1, $this->startTime, 1);
+
+ // assertNull
+ $this->mockGet('not_set', null, $this->startTime, 1);
+
+ // assertNull
+ $this->mockDelete('value1', true, 1);
+ $this->mockGet('value1', null, $this->startTime, 1);
+
+ parent::testSimple($value1, $value2);
+ }
+
+ /**
+ * {@inheritdoc}
+ * @dataProvider dataSimple
+ */
+ public function testClear($value1, $value2, $value3, $value4)
+ {
+ // assert Equals
+ $this->mockSet('1_value1', $value1, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockSet('1_value2', $value2, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockSet('2_value1', $value3, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockSet('3_value1', $value4, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+
+ $this->mockGet('1_value1', $value1, $this->startTime, 2);
+ $this->mockGet('1_value2', $value2, $this->startTime, 2);
+ $this->mockGet('2_value1', $value3, $this->startTime, 2);
+ $this->mockGet('3_value1', $value4, $this->startTime, 2);
+
+ // assertTrue
+ $this->mockClear(true, true, 1);
+ $this->mockClear(false, true, 1);
+
+ // assertEquals
+ $this->mockGet('1_value1', null, $this->startTime, 1);
+ $this->mockGet('1_value2', null, $this->startTime, 1);
+ $this->mockGet('2_value3', null, $this->startTime, 1);
+ $this->mockGet('3_value4', null, $this->startTime, 1);
+
+ parent::testClear($value1, $value2, $value3, $value4);
+ }
+
+ /**
+ * {@inheritdoc}
+ * @dataProvider dataTypesInCache
+ */
+ public function testDifferentTypesInCache($data)
+ {
+ $this->mockSet('val', $data, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockGet('val', $data, $this->startTime, 1);
+
+ parent::testDifferentTypesInCache($data);
+ }
+
+ /**
+ * {@inheritdoc}
+ * @dataProvider dataSimple
+ */
+ public function testGetAllKeys($value1, $value2, $value3)
+ {
+ $this->mockSet('value1', $value1, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockSet('value2', $value2,Cache::FIVE_MINUTES, $this->startTime, true, 1);
+ $this->mockSet('test_value3', $value3, Cache::FIVE_MINUTES, $this->startTime, true, 1);
+
+ $result = [
+ ['k' => 'value1'],
+ ['k' => 'value2'],
+ ['k' => 'test_value3'],
+ ];
+
+ $this->mockGetAllKeys(null, $result, $this->startTime, 1);
+
+ $result = [
+ ['k' => 'test_value3'],
+ ];
+
+ $this->mockGetAllKeys('test', $result, $this->startTime, 1);
+
+ parent::testGetAllKeys($value1, $value2, $value3);
+ }
}
namespace Friendica\Test\src\Core\Cache;
-/**
- * @runTestsInSeparateProcesses
- * @preserveGlobalState disabled
- */
use Friendica\Core\Cache\CacheDriverFactory;
/**
+ * @runTestsInSeparateProcesses
+ * @preserveGlobalState disabled
* @requires extension memcache
*/
class MemcacheCacheDriverTest extends MemoryCacheTest
{
protected function getInstance()
{
+ $this->mockConfigGet('system', 'memcache_host', 'localhost', 1);
+ $this->mockConfigGet('system', 'memcache_port', 11211, 1);
+
$this->cache = CacheDriverFactory::create('memcache');
return $this->cache;
namespace Friendica\Test\src\Core\Cache;
-/**
- * @runTestsInSeparateProcesses
- * @preserveGlobalState disabled
- */
use Friendica\Core\Cache\CacheDriverFactory;
/**
+ * @runTestsInSeparateProcesses
+ * @preserveGlobalState disabled
* @requires extension memcached
*/
class MemcachedCacheDriverTest extends MemoryCacheTest
{
protected function getInstance()
{
+ $this->mockConfigGet('system', 'memcached_hosts', [0 => 'localhost, 11211']);
+
$this->cache = CacheDriverFactory::create('memcached');
return $this->cache;
}
/**
* @small
+ * @dataProvider dataSimple
*/
- function testCompareSet() {
+ function testCompareSet($value1, $value2) {
$this->assertNull($this->instance->get('value1'));
- $value = 'foobar';
- $this->instance->add('value1', $value);
+ $this->instance->add('value1', $value1);
$received = $this->instance->get('value1');
- $this->assertEquals($value, $received, 'Value received from cache not equal to the original');
+ $this->assertEquals($value1, $received, 'Value received from cache not equal to the original');
- $newValue = 'ipsum lorum';
- $this->instance->compareSet('value1', $value, $newValue);
+ $this->instance->compareSet('value1', $value1, $value2);
$received = $this->instance->get('value1');
- $this->assertEquals($newValue, $received, 'Value not overwritten by compareSet');
+ $this->assertEquals($value2, $received, 'Value not overwritten by compareSet');
}
/**
* @small
+ * @dataProvider dataSimple
*/
- function testNegativeCompareSet() {
+ function testNegativeCompareSet($value1, $value2) {
$this->assertNull($this->instance->get('value1'));
- $value = 'foobar';
- $this->instance->add('value1', $value);
+ $this->instance->add('value1', $value1);
$received = $this->instance->get('value1');
- $this->assertEquals($value, $received, 'Value received from cache not equal to the original');
+ $this->assertEquals($value1, $received, 'Value received from cache not equal to the original');
- $newValue = 'ipsum lorum';
- $this->instance->compareSet('value1', 'wrong', $newValue);
+ $this->instance->compareSet('value1', 'wrong', $value2);
$received = $this->instance->get('value1');
- $this->assertNotEquals($newValue, $received, 'Value was wrongly overwritten by compareSet');
- $this->assertEquals($value, $received, 'Value was wrongly overwritten by any other value');
+ $this->assertNotEquals($value2, $received, 'Value was wrongly overwritten by compareSet');
+ $this->assertEquals($value1, $received, 'Value was wrongly overwritten by any other value');
}
/**
* @small
+ * @dataProvider dataSimple
*/
- function testCompareDelete() {
+ function testCompareDelete($data) {
$this->assertNull($this->instance->get('value1'));
- $value = 'foobar';
- $this->instance->add('value1', $value);
+ $this->instance->add('value1', $data);
$received = $this->instance->get('value1');
- $this->assertEquals($value, $received, 'Value received from cache not equal to the original');
- $this->instance->compareDelete('value1', $value);
+ $this->assertEquals($data, $received, 'Value received from cache not equal to the original');
+ $this->instance->compareDelete('value1', $data);
$this->assertNull($this->instance->get('value1'), 'Value was not deleted by compareDelete');
}
/**
* @small
+ * @dataProvider dataSimple
*/
- function testNegativeCompareDelete() {
+ function testNegativeCompareDelete($data) {
$this->assertNull($this->instance->get('value1'));
- $value = 'foobar';
- $this->instance->add('value1', $value);
+ $this->instance->add('value1', $data);
$received = $this->instance->get('value1');
- $this->assertEquals($value, $received, 'Value received from cache not equal to the original');
+ $this->assertEquals($data, $received, 'Value received from cache not equal to the original');
$this->instance->compareDelete('value1', 'wrong');
$this->assertNotNull($this->instance->get('value1'), 'Value was wrongly compareDeleted');
- $this->instance->compareDelete('value1', $value);
+ $this->instance->compareDelete('value1', $data);
$this->assertNull($this->instance->get('value1'), 'Value was wrongly NOT deleted by compareDelete');
}
/**
* @small
+ * @dataProvider dataSimple
*/
- function testAdd() {
+ function testAdd($value1, $value2) {
$this->assertNull($this->instance->get('value1'));
- $value = 'foobar';
- $this->instance->add('value1', $value);
+ $this->instance->add('value1', $value1);
- $newValue = 'ipsum lorum';
- $this->instance->add('value1', $newValue);
+ $this->instance->add('value1', $value2);
$received = $this->instance->get('value1');
- $this->assertNotEquals($newValue, $received, 'Value was wrongly overwritten by add');
- $this->assertEquals($value, $received, 'Value was wrongly overwritten by any other value');
+ $this->assertNotEquals($value2, $received, 'Value was wrongly overwritten by add');
+ $this->assertEquals($value1, $received, 'Value was wrongly overwritten by any other value');
$this->instance->delete('value1');
- $this->instance->add('value1', $newValue);
+ $this->instance->add('value1', $value2);
$received = $this->instance->get('value1');
- $this->assertEquals($newValue, $received, 'Value was not overwritten by add');
- $this->assertNotEquals($value, $received, 'Value was not overwritten by any other value');
+ $this->assertEquals($value2, $received, 'Value was not overwritten by add');
+ $this->assertNotEquals($value1, $received, 'Value was not overwritten by any other value');
}
}
\ No newline at end of file
namespace Friendica\Test\src\Core\Cache;
-/**
- * @runTestsInSeparateProcesses
- * @preserveGlobalState disabled
- */
use Friendica\Core\Cache\CacheDriverFactory;
/**
+ * @runTestsInSeparateProcesses
+ * @preserveGlobalState disabled
* @requires extension redis
*/
class RedisCacheDriverTest extends MemoryCacheTest
{
protected function getInstance()
{
+ $this->mockConfigGet('system', 'redis_host', 'localhost', 1);
+ $this->mockConfigGet('system', 'redis_port', null, 1);
+
$this->cache = CacheDriverFactory::create('redis');
return $this->cache;
}
]
]);
- $mode = \Mockery::mock('alias:Friendica\App\Mode');
+ $mode = \Mockery::mock('Friendica\App\Mode');
$mode
->shouldReceive('has')
->andReturn(true);
*/
public function testCheckKeys()
{
+ $this->mockL10nT();
+
$this->setFunctions(['openssl_pkey_new' => false]);
$install = new Installer();
$this->assertFalse($install->checkKeys());
*/
public function testCheckLocalIni()
{
+ $this->mockL10nT();
+
$this->assertTrue($this->root->hasChild('config/local.config.php'));
$install = new Installer();
*/
public function testCheckHtAccessFail()
{
+ $this->mockL10nT();
+
// Mocking the CURL Response
$curlResult = \Mockery::mock('Friendica\Network\CurlResult');
$curlResult
*/
public function testCheckHtAccessWork()
{
+ $this->mockL10nT();
+
// Mocking the failed CURL Response
$curlResultF = \Mockery::mock('Friendica\Network\CurlResult');
$curlResultF
*/
public function testImagick()
{
+ $this->mockL10nT();
+
$imageMock = \Mockery::mock('alias:Friendica\Object\Image');
$imageMock
->shouldReceive('supportedTypes')
*/
public function testImagickNotFound()
{
+ $this->mockL10nT();
+
$imageMock = \Mockery::mock('alias:Friendica\Object\Image');
$imageMock
->shouldReceive('supportedTypes')
namespace Friendica\Test\src\Core\Lock;
+use Friendica\Core\Cache;
use Friendica\Core\Lock\DatabaseLockDriver;
-use Friendica\Database\DBA;
+use Friendica\Test\Util\DbaLockMockTrait;
/**
* @runTestsInSeparateProcesses
*/
class DatabaseLockDriverTest extends LockTest
{
+ use DbaLockMockTrait;
+
+ protected $pid = 123;
+
+ protected function setUp()
+ {
+ $this->mockConnected();
+ $this->mockConnect();
+
+ $this->mockReleaseAll($this->pid, 2);
+
+ parent::setUp();
+ }
+
protected function getInstance()
{
- return new DatabaseLockDriver();
+ return new DatabaseLockDriver($this->pid);
+ }
+
+ public function testLock()
+ {
+ $this->mockIsLocked('foo', false, $this->startTime, 1);
+ $this->mockAcquireLock('foo', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+ $this->mockIsLocked('foo', true, $this->startTime, 1);
+ $this->mockIsLocked('bar', false, $this->startTime, 1);
+
+ parent::testLock();
+ }
+
+ public function testDoubleLock()
+ {
+ $this->mockIsLocked('foo', false, $this->startTime, 1);
+ $this->mockAcquireLock('foo', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+ $this->mockIsLocked('foo', true, $this->startTime, 1);
+ $this->mockAcquireLock('foo', Cache::FIVE_MINUTES, true, $this->pid, true, $this->startTime, 1);
+
+ parent::testDoubleLock();
+ }
+
+ public function testReleaseLock()
+ {
+ $this->mockIsLocked('foo', false, $this->startTime, 1);
+ $this->mockAcquireLock('foo', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+ $this->mockIsLocked('foo', true, $this->startTime, 1);
+ $this->mockReleaseLock('foo', $this->pid, 1);
+ $this->mockIsLocked('foo', false, $this->startTime, 1);
+
+ parent::testReleaseLock();
+ }
+
+ public function testReleaseAll()
+ {
+ $this->mockAcquireLock('foo', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+ $this->mockAcquireLock('bar', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+ $this->mockAcquireLock('nice', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+
+ $this->mockIsLocked('foo', true, $this->startTime, 1);
+ $this->mockIsLocked('bar', true, $this->startTime, 1);
+ $this->mockIsLocked('nice', true, $this->startTime, 1);
+
+ $this->mockReleaseAll($this->pid, 1);
+
+ $this->mockIsLocked('foo', false, $this->startTime, 1);
+ $this->mockIsLocked('bar', false, $this->startTime, 1);
+ $this->mockIsLocked('nice', false, $this->startTime, 1);
+
+ parent::testReleaseAll();
}
- public function tearDown()
+ public function testReleaseAfterUnlock()
{
- DBA::delete('locks', [ 'id > 0']);
- parent::tearDown();
+ $this->mockIsLocked('foo', false, $this->startTime, 1);
+ $this->mockIsLocked('bar', false, $this->startTime, 1);
+ $this->mockIsLocked('nice', false, $this->startTime, 1);
+
+ $this->mockAcquireLock('foo', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+ $this->mockAcquireLock('bar', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+ $this->mockAcquireLock('nice', Cache::FIVE_MINUTES, false, $this->pid, false, $this->startTime, 1);
+
+ $this->mockReleaseLock('foo', $this->pid, 1);
+
+ $this->mockIsLocked('foo', false, $this->startTime, 1);
+ $this->mockIsLocked('bar', true, $this->startTime, 1);
+ $this->mockIsLocked('nice', true, $this->startTime, 1);
+
+ $this->mockReleaseAll($this->pid, 1);
+
+ $this->mockIsLocked('bar', false, $this->startTime, 1);
+ $this->mockIsLocked('nice', false, $this->startTime, 1);
+
+ parent::testReleaseAfterUnlock();
}
}
namespace Friendica\Test\src\Core\Lock;
-use Friendica\BaseObject;
-use Friendica\Core\Config;
-use Friendica\Test\DatabaseTest;
+use Friendica\Test\MockedTest;
+use Friendica\Test\Util\AppMockTrait;
+use Friendica\Test\Util\VFSTrait;
-abstract class LockTest extends DatabaseTest
+abstract class LockTest extends MockedTest
{
+ use VFSTrait;
+ use AppMockTrait;
+
+ /**
+ * @var int Start time of the mock (used for time operations)
+ */
+ protected $startTime = 1417011228;
+
/**
* @var \Friendica\Core\Lock\ILockDriver
*/
$this->instance->releaseAll();
// Reusable App object
- $this->app = BaseObject::getApp();
+ $this->setUpVfsDir();
+ $this->mockApp($this->root);
+ $this->app
+ ->shouldReceive('getHostname')
+ ->andReturn('friendica.local');
// Default config
- Config::set('config', 'hostname', 'localhost');
- Config::set('system', 'throttle_limit_day', 100);
- Config::set('system', 'throttle_limit_week', 100);
- Config::set('system', 'throttle_limit_month', 100);
- Config::set('system', 'theme', 'system_theme');
+ $this->mockConfigGet('config', 'hostname', 'localhost');
+ $this->mockConfigGet('system', 'throttle_limit_day', 100);
+ $this->mockConfigGet('system', 'throttle_limit_week', 100);
+ $this->mockConfigGet('system', 'throttle_limit_month', 100);
+ $this->mockConfigGet('system', 'theme', 'system_theme');
}
protected function tearDown()
{
- parent::tearDown();
$this->instance->releaseAll();
+ parent::tearDown();
}
/**
{
protected function getInstance()
{
+ $this->mockConfigGet('system', 'memcache_host', 'localhost', 1);
+ $this->mockConfigGet('system', 'memcache_port', 11211, 1);
+
return new CacheLockDriver(CacheDriverFactory::create('memcache'));
}
}
{
protected function getInstance()
{
+ $this->mockConfigGet('system', 'memcached_hosts', [0 => 'localhost, 11211']);
+
return new CacheLockDriver(CacheDriverFactory::create('memcached'));
}
}
{
protected function getInstance()
{
- return new CacheLockDriver(CacheDriverFactory::create('redis'));
+ $this->mockConfigGet('system', 'redis_host', 'localhost', 1);
+ $this->mockConfigGet('system', 'redis_port', null, 1);
+ return new CacheLockDriver(CacheDriverFactory::create('redis'));
}
}
*/
class SemaphoreLockDriverTest extends LockTest
{
+ public function setUp()
+ {
+ parent::setUp();
+
+ $this->app->shouldReceive('getHostname')->andReturn('friendica.local');
+ $this->mockConfigGet('system', 'temppath', '/tmp/');
+ }
+
protected function getInstance()
{
return new SemaphoreLockDriver();
/**
* @small
+ * @runInSeparateProcess
+ * @preserveGlobalState disabled
*/
public function testRedirect()
{
/**
* @small
+ * @runInSeparateProcess
+ * @preserveGlobalState disabled
*/
public function testRedirectHeader()
{