2015-07-15 10:14:32 -04:00
|
|
|
<?php
|
2025-06-30 09:04:05 -04:00
|
|
|
|
2015-07-15 10:14:32 -04:00
|
|
|
/**
|
2024-05-10 09:09:14 -04:00
|
|
|
* SPDX-FileCopyrightText: 2016-2024 Nextcloud GmbH and Nextcloud contributors
|
|
|
|
|
* SPDX-FileCopyrightText: 2016 ownCloud, Inc.
|
|
|
|
|
* SPDX-License-Identifier: AGPL-3.0-only
|
2015-07-15 10:14:32 -04:00
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
namespace Test\Lock;
|
|
|
|
|
|
2025-06-12 12:31:58 -04:00
|
|
|
use OC\Lock\DBLockingProvider;
|
2016-09-12 15:35:24 -04:00
|
|
|
use OCP\AppFramework\Utility\ITimeFactory;
|
2025-06-12 12:31:58 -04:00
|
|
|
use OCP\IDBConnection;
|
2015-09-17 07:55:04 -04:00
|
|
|
use OCP\Lock\ILockingProvider;
|
2025-06-12 12:31:58 -04:00
|
|
|
use OCP\Server;
|
2015-09-17 07:55:04 -04:00
|
|
|
|
2015-11-02 19:52:41 -05:00
|
|
|
/**
|
|
|
|
|
* Class DBLockingProvider
|
|
|
|
|
*
|
|
|
|
|
*
|
|
|
|
|
* @package Test\Lock
|
|
|
|
|
*/
|
2025-10-20 19:52:40 -04:00
|
|
|
#[\PHPUnit\Framework\Attributes\Group('DB')]
|
2016-05-20 09:38:20 -04:00
|
|
|
class DBLockingProviderTest extends LockingProvider {
|
2015-09-17 07:55:04 -04:00
|
|
|
/**
|
|
|
|
|
* @var \OC\Lock\DBLockingProvider
|
|
|
|
|
*/
|
|
|
|
|
protected $instance;
|
2015-07-15 10:14:32 -04:00
|
|
|
|
|
|
|
|
/**
|
2025-06-30 10:56:59 -04:00
|
|
|
* @var IDBConnection
|
2015-07-15 10:14:32 -04:00
|
|
|
*/
|
2018-04-10 12:30:43 -04:00
|
|
|
protected $connection;
|
2015-07-15 10:14:32 -04:00
|
|
|
|
2015-09-17 07:55:04 -04:00
|
|
|
/**
|
2025-06-30 10:56:59 -04:00
|
|
|
* @var ITimeFactory
|
2015-09-17 07:55:04 -04:00
|
|
|
*/
|
2018-04-10 12:30:43 -04:00
|
|
|
protected $timeFactory;
|
2015-09-17 07:55:04 -04:00
|
|
|
|
2018-04-10 12:30:43 -04:00
|
|
|
protected $currentTime;
|
2015-09-17 07:55:04 -04:00
|
|
|
|
2019-11-27 09:27:18 -05:00
|
|
|
protected function setUp(): void {
|
2015-09-17 07:55:04 -04:00
|
|
|
$this->currentTime = time();
|
2016-09-12 15:35:24 -04:00
|
|
|
$this->timeFactory = $this->createMock(ITimeFactory::class);
|
2015-09-17 07:55:04 -04:00
|
|
|
$this->timeFactory->expects($this->any())
|
|
|
|
|
->method('getTime')
|
2020-03-25 17:21:27 -04:00
|
|
|
->willReturnCallback(function () {
|
2015-09-17 07:55:04 -04:00
|
|
|
return $this->currentTime;
|
2020-03-25 17:21:27 -04:00
|
|
|
});
|
2015-09-17 07:55:04 -04:00
|
|
|
parent::setUp();
|
|
|
|
|
}
|
|
|
|
|
|
2015-07-15 10:14:32 -04:00
|
|
|
/**
|
2025-06-30 10:56:59 -04:00
|
|
|
* @return ILockingProvider
|
2015-07-15 10:14:32 -04:00
|
|
|
*/
|
|
|
|
|
protected function getInstance() {
|
2025-06-12 12:31:58 -04:00
|
|
|
$this->connection = Server::get(IDBConnection::class);
|
|
|
|
|
return new DBLockingProvider($this->connection, $this->timeFactory, 3600);
|
2015-07-15 10:14:32 -04:00
|
|
|
}
|
|
|
|
|
|
2019-11-27 09:27:18 -05:00
|
|
|
protected function tearDown(): void {
|
2025-08-26 09:20:42 -04:00
|
|
|
$qb = $this->connection->getQueryBuilder();
|
|
|
|
|
$qb->delete('file_locks')->executeStatement();
|
2015-07-15 10:14:32 -04:00
|
|
|
parent::tearDown();
|
|
|
|
|
}
|
2015-09-17 07:55:04 -04:00
|
|
|
|
2024-09-15 16:32:31 -04:00
|
|
|
public function testCleanEmptyLocks(): void {
|
2015-09-17 07:55:04 -04:00
|
|
|
$this->currentTime = 100;
|
|
|
|
|
$this->instance->acquireLock('foo', ILockingProvider::LOCK_EXCLUSIVE);
|
|
|
|
|
$this->instance->acquireLock('asd', ILockingProvider::LOCK_EXCLUSIVE);
|
|
|
|
|
|
|
|
|
|
$this->currentTime = 200;
|
|
|
|
|
$this->instance->acquireLock('bar', ILockingProvider::LOCK_EXCLUSIVE);
|
|
|
|
|
$this->instance->changeLock('asd', ILockingProvider::LOCK_SHARED);
|
|
|
|
|
|
2016-03-24 09:07:43 -04:00
|
|
|
$this->currentTime = 150 + 3600;
|
2015-09-17 07:55:04 -04:00
|
|
|
|
|
|
|
|
$this->assertEquals(3, $this->getLockEntryCount());
|
|
|
|
|
|
2015-12-09 08:13:05 -05:00
|
|
|
$this->instance->cleanExpiredLocks();
|
2015-09-17 07:55:04 -04:00
|
|
|
|
|
|
|
|
$this->assertEquals(2, $this->getLockEntryCount());
|
|
|
|
|
}
|
|
|
|
|
|
2025-08-26 09:20:42 -04:00
|
|
|
private function getLockEntryCount(): int {
|
|
|
|
|
$qb = $this->connection->getQueryBuilder();
|
|
|
|
|
$result = $qb->select($qb->func()->count('*'))
|
|
|
|
|
->from('file_locks')
|
|
|
|
|
->executeQuery();
|
|
|
|
|
return (int)$result->fetchOne();
|
2015-09-17 07:55:04 -04:00
|
|
|
}
|
2018-04-10 12:30:43 -04:00
|
|
|
|
|
|
|
|
protected function getLockValue($key) {
|
|
|
|
|
$query = $this->connection->getQueryBuilder();
|
|
|
|
|
$query->select('lock')
|
|
|
|
|
->from('file_locks')
|
|
|
|
|
->where($query->expr()->eq('key', $query->createNamedParameter($key)));
|
2020-11-05 04:50:53 -05:00
|
|
|
|
2025-08-26 09:20:42 -04:00
|
|
|
$result = $query->executeQuery();
|
2021-01-03 09:28:31 -05:00
|
|
|
$rows = $result->fetchOne();
|
2020-11-05 04:50:53 -05:00
|
|
|
$result->closeCursor();
|
|
|
|
|
|
|
|
|
|
return $rows;
|
2018-04-10 12:30:43 -04:00
|
|
|
}
|
|
|
|
|
|
2024-09-15 16:32:31 -04:00
|
|
|
public function testDoubleShared(): void {
|
2018-04-10 12:30:43 -04:00
|
|
|
$this->instance->acquireLock('foo', ILockingProvider::LOCK_SHARED);
|
|
|
|
|
$this->instance->acquireLock('foo', ILockingProvider::LOCK_SHARED);
|
|
|
|
|
|
|
|
|
|
$this->assertEquals(1, $this->getLockValue('foo'));
|
|
|
|
|
|
|
|
|
|
$this->instance->releaseLock('foo', ILockingProvider::LOCK_SHARED);
|
|
|
|
|
|
|
|
|
|
$this->assertEquals(1, $this->getLockValue('foo'));
|
|
|
|
|
|
|
|
|
|
$this->instance->releaseLock('foo', ILockingProvider::LOCK_SHARED);
|
|
|
|
|
|
|
|
|
|
$this->assertEquals(1, $this->getLockValue('foo'));
|
|
|
|
|
|
|
|
|
|
$this->instance->releaseAll();
|
|
|
|
|
|
|
|
|
|
$this->assertEquals(0, $this->getLockValue('foo'));
|
|
|
|
|
}
|
2015-07-15 10:14:32 -04:00
|
|
|
}
|