summaryrefslogtreecommitdiffstats
path: root/lib/private/cache
diff options
context:
space:
mode:
authorVincent Petry <pvince81@owncloud.com>2015-02-11 16:26:03 +0100
committerThomas Müller <thomas.mueller@tmit.eu>2015-03-16 10:13:13 +0100
commitb495ca492408c3560e654e0137fcae35ff35a576 (patch)
treeee9136364c1dc8d6e3f3585954c06de2c5688e8e /lib/private/cache
parent1e0d8f1774747871c8cab03bccc03cd84ee96764 (diff)
downloadnextcloud-server-b495ca492408c3560e654e0137fcae35ff35a576.tar.gz
nextcloud-server-b495ca492408c3560e654e0137fcae35ff35a576.zip
Added part files for when writing chunks
Whenever a chunk is being written, it is now written to a part file first. This is to avoid a concurrent chunk upload to believe that the former chunk already exists, even though it's not fully written. This makes sure that the final file assembly is only done when all chunks were successfully written. Also added an extra unique id to chunk parts in case the same chunk is uploaded twice concurrently.
Diffstat (limited to 'lib/private/cache')
-rw-r--r--lib/private/cache/file.php15
1 files changed, 13 insertions, 2 deletions
diff --git a/lib/private/cache/file.php b/lib/private/cache/file.php
index 6fa7686ea96..8ec048ccba0 100644
--- a/lib/private/cache/file.php
+++ b/lib/private/cache/file.php
@@ -11,6 +11,7 @@ namespace OC\Cache;
use OC\Files\Filesystem;
use OC\Files\View;
+use OCP\Security\ISecureRandom;
class File {
protected $storage;
@@ -79,12 +80,22 @@ class File {
$storage = $this->getStorage();
$result = false;
$proxyStatus = \OC_FileProxy::$enabled;
+ // unique id to avoid chunk collision, just in case
+ $uniqueId = \OC::$server->getSecureRandom()->getLowStrengthGenerator()->generate(
+ 16,
+ ISecureRandom::CHAR_DIGITS . ISecureRandom::CHAR_LOWER . ISecureRandom::CHAR_UPPER
+ );
+
+ // use part file to prevent hasKey() to find the key
+ // while it is being written
+ $keyPart = $key . '.' . $uniqueId . '.part';
\OC_FileProxy::$enabled = false;
- if ($storage and $storage->file_put_contents($key, $value)) {
+ if ($storage and $storage->file_put_contents($keyPart, $value)) {
if ($ttl === 0) {
$ttl = 86400; // 60*60*24
}
- $result = $storage->touch($key, time() + $ttl);
+ $result = $storage->touch($keyPart, time() + $ttl);
+ $result &= $storage->rename($keyPart, $key);
}
\OC_FileProxy::$enabled = $proxyStatus;
return $result;