Skip to content

Commit

Permalink
Merge pull request #13641 from owncloud/cache-storage-status
Browse files Browse the repository at this point in the history
Store storage availability in database
  • Loading branch information
Vincent Petry committed Aug 7, 2015
2 parents 404b5a2 + 75a5e6e commit b3a1aef
Show file tree
Hide file tree
Showing 11 changed files with 763 additions and 13 deletions.
12 changes: 10 additions & 2 deletions apps/files_external/lib/config.php
Original file line number Diff line number Diff line change
Expand Up @@ -496,8 +496,16 @@ public static function getBackendStatus($class, $options, $isPersonal) {
if (class_exists($class)) {
try {
$storage = new $class($options);
if ($storage->test($isPersonal)) {
return self::STATUS_SUCCESS;

try {
$result = $storage->test($isPersonal);
$storage->setAvailability($result);
if ($result) {
return self::STATUS_SUCCESS;
}
} catch (\Exception $e) {
$storage->setAvailability(false);
throw $e;
}
} catch (Exception $exception) {
\OCP\Util::logException('files_external', $exception);
Expand Down
12 changes: 12 additions & 0 deletions db_structure.xml
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,18 @@
<length>4</length>
</field>

<field>
<name>available</name>
<type>boolean</type>
<default>true</default>
<notnull>true</notnull>
</field>

<field>
<name>last_checked</name>
<type>integer</type>
</field>

<index>
<name>storages_id_index</name>
<unique>true</unique>
Expand Down
48 changes: 38 additions & 10 deletions lib/private/files/cache/storage.php
Original file line number Diff line number Diff line change
Expand Up @@ -43,27 +43,25 @@ class Storage {

/**
* @param \OC\Files\Storage\Storage|string $storage
* @param bool $isAvailable
* @throws \RuntimeException
*/
public function __construct($storage) {
public function __construct($storage, $isAvailable = true) {
if ($storage instanceof \OC\Files\Storage\Storage) {
$this->storageId = $storage->getId();
} else {
$this->storageId = $storage;
}
$this->storageId = self::adjustStorageId($this->storageId);

$sql = 'SELECT `numeric_id` FROM `*PREFIX*storages` WHERE `id` = ?';
$result = \OC_DB::executeAudited($sql, array($this->storageId));
if ($row = $result->fetchRow()) {
if ($row = self::getStorageById($this->storageId)) {
$this->numericId = $row['numeric_id'];
} else {
$connection = \OC_DB::getConnection();
if ($connection->insertIfNotExist('*PREFIX*storages', ['id' => $this->storageId])) {
if ($connection->insertIfNotExist('*PREFIX*storages', ['id' => $this->storageId, 'available' => $isAvailable])) {
$this->numericId = \OC_DB::insertid('*PREFIX*storages');
} else {
$result = \OC_DB::executeAudited($sql, array($this->storageId));
if ($row = $result->fetchRow()) {
if ($row = self::getStorageById($this->storageId)) {
$this->numericId = $row['numeric_id'];
} else {
throw new \RuntimeException('Storage could neither be inserted nor be selected from the database');
Expand All @@ -72,6 +70,16 @@ public function __construct($storage) {
}
}

/**
* @param string $storageId
* @return array|null
*/
public static function getStorageById($storageId) {
$sql = 'SELECT * FROM `*PREFIX*storages` WHERE `id` = ?';
$result = \OC_DB::executeAudited($sql, array($storageId));
return $result->fetchRow();
}

/**
* Adjusts the storage id to use md5 if too long
* @param string $storageId storage id
Expand Down Expand Up @@ -120,15 +128,35 @@ public static function getStorageId($numericId) {
public static function getNumericStorageId($storageId) {
$storageId = self::adjustStorageId($storageId);

$sql = 'SELECT `numeric_id` FROM `*PREFIX*storages` WHERE `id` = ?';
$result = \OC_DB::executeAudited($sql, array($storageId));
if ($row = $result->fetchRow()) {
if ($row = self::getStorageById($storageId)) {
return $row['numeric_id'];
} else {
return null;
}
}

/**
* @return array|null [ available, last_checked ]
*/
public function getAvailability() {
if ($row = self::getStorageById($this->storageId)) {
return [
'available' => $row['available'],
'last_checked' => $row['last_checked']
];
} else {
return null;
}
}

/**
* @param bool $isAvailable
*/
public function setAvailability($isAvailable) {
$sql = 'UPDATE `*PREFIX*storages` SET `available` = ?, `last_checked` = ? WHERE `id` = ?';
\OC_DB::executeAudited($sql, array($isAvailable, time(), $this->storageId));
}

/**
* Check if a string storage id is known
*
Expand Down
7 changes: 6 additions & 1 deletion lib/private/files/mount/mountpoint.php
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
use \OC\Files\Filesystem;
use OC\Files\Storage\StorageFactory;
use OC\Files\Storage\Storage;
use OC\Files\Storage\Wrapper\Wrapper;
use OCP\Files\Mount\IMountPoint;

class MountPoint implements IMountPoint {
Expand Down Expand Up @@ -92,7 +93,11 @@ public function __construct($storage, $mountpoint, $arguments = null, $loader =
$this->mountPoint = $mountpoint;
if ($storage instanceof Storage) {
$this->class = get_class($storage);
$this->storage = $this->loader->wrap($this, $storage);
$this->storage = $storage;
// only wrap if not already wrapped
if (!($this->storage instanceof Wrapper)) {
$this->storage = $this->loader->wrap($this, $this->storage);
}
} else {
// Update old classes to new namespace
if (strpos($storage, 'OC_Filestorage_') !== false) {
Expand Down
19 changes: 19 additions & 0 deletions lib/private/files/storage/common.php
Original file line number Diff line number Diff line change
Expand Up @@ -404,6 +404,11 @@ public function cleanPath($path) {
return implode('/', $output);
}

/**
* Test a storage for availability
*
* @return bool
*/
public function test() {
if ($this->stat('')) {
return true;
Expand Down Expand Up @@ -650,4 +655,18 @@ public function releaseLock($path, $type, ILockingProvider $provider) {
public function changeLock($path, $type, ILockingProvider $provider) {
$provider->changeLock('files/' . md5($this->getId() . '::' . trim($path, '/')), $type);
}

/**
* @return array [ available, last_checked ]
*/
public function getAvailability() {
return $this->getStorageCache()->getAvailability();
}

/**
* @param bool $isAvailable
*/
public function setAvailability($isAvailable) {
$this->getStorageCache()->setAvailability($isAvailable);
}
}
Loading

0 comments on commit b3a1aef

Please sign in to comment.