Skip to content

Commit

Permalink
Checksum calculating storage wrapper: Initial draft owncloud#26655
Browse files Browse the repository at this point in the history
  • Loading branch information
IljaN committed Jan 27, 2017
1 parent ba67184 commit 2eb954a
Show file tree
Hide file tree
Showing 3 changed files with 158 additions and 0 deletions.
82 changes: 82 additions & 0 deletions lib/private/Files/Storage/Wrapper/Checksum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
<?php
/**
* @author Ilja Neumann <ineumann@owncloud.com>
*
* @copyright Copyright (c) 2017, ownCloud GmbH.
* @license AGPL-3.0
*
* This code is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License, version 3,
* as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License, version 3,
* along with this program. If not, see <http://www.gnu.org/licenses/>
*
*/
namespace OC\Files\Storage\Wrapper;


class Checksum extends Wrapper {

const FILTER_NAME = 'sha1_checksum';

private $fileHashes = [];

/**
* @param array $parameters
*/
public function __construct($parameters) {
parent::__construct($parameters);
stream_filter_register(self::FILTER_NAME, '\OC\Files\Stream\Filter\Sha1');
}

/**
* @param string $path
* @param string $mode
* @return false|resource
*/
public function fopen($path, $mode) {
$stream = $this->getWrapperStorage()->fopen($path, $mode);

if (!self::requiresChecksum($path, $mode)) {
return $stream;
}

stream_filter_append(
$stream,
self::FILTER_NAME,
STREAM_FILTER_WRITE,
['path' => $path, 'callback' => [$this, 'addFileHash']]
);

return $stream;
}

/**
* Checksum is only required for everything under files/
* @param $path
* @param $mode
* @return bool
*/
private static function requiresChecksum($path, $mode) {
return substr($path, 0, 6) == 'files/' && $mode != 'r';
}

public function rename($path1, $path2) {
if (array_key_exists($path1, $this->fileHashes)) {
$checksum = $this->fileHashes[$path1];
// Update checksum in oc_filecache here?
}

return $this->getWrapperStorage()->rename($path1, $path2);
}

public function addFileHash($path, $hash) {
$this->fileHashes[$path] = $hash;
}
}
71 changes: 71 additions & 0 deletions lib/private/Files/Stream/Filter/Sha1.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
<?php
/**
* @author Ilja Neumann <ineumann@owncloud.com>
*
* @copyright Copyright (c) 2017, ownCloud GmbH.
* @license AGPL-3.0
*
* This code is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License, version 3,
* as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License, version 3,
* along with this program. If not, see <http://www.gnu.org/licenses/>
*
*/
namespace OC\Files\Stream\Filter;

class Sha1 extends \php_user_filter {

/** @var resource */
private $ctx;

/**
* @return bool
*/
function onCreate () {
$this->ctx = hash_init('sha1');
return true;
}

/**
* @return bool
*/
function onClose () {
$hash = hash_final($this->ctx);
// Debug
file_put_contents(
'/tmp/hashtest.txt', $this->params['path'] . ' --> ' . $hash . PHP_EOL,
FILE_APPEND
);

call_user_func_array(
$this->params['callback'],
[$this->params['path'], $hash]
);

return true;
}

/**
* @param resource $in
* @param resource $out
* @param int $consumed
* @param bool $closing
* @return int
*/
function filter ($in, $out, &$consumed, $closing) {
while ($bucket = stream_bucket_make_writeable($in)) {
hash_update($this->ctx, $bucket->data);
$consumed += $bucket->datalen;
stream_bucket_append($out, $bucket);
}

return PSFS_PASS_ON;
}
}
5 changes: 5 additions & 0 deletions lib/private/legacy/util.php
Original file line number Diff line number Diff line change
Expand Up @@ -175,6 +175,11 @@ public static function setupFS($user = '') {
return $storage;
});

// install storage checksum wrapper
\OC\Files\Filesystem::addStorageWrapper('oc_checksum', function ($mountPoint, $storage) {
return new \OC\Files\Storage\Wrapper\Checksum(['storage' => $storage]);
});

\OC\Files\Filesystem::addStorageWrapper('oc_encoding', function ($mountPoint, \OCP\Files\Storage $storage, \OCP\Files\Mount\IMountPoint $mount) {
if ($mount->getOption('encoding_compatibility', false) && !$storage->instanceOfStorage('\OCA\Files_Sharing\SharedStorage') && !$storage->isLocal()) {
return new \OC\Files\Storage\Wrapper\Encoding(['storage' => $storage]);
Expand Down

0 comments on commit 2eb954a

Please sign in to comment.