/** * @param string $internalPath * @param int $time * @return array[] all propagated entries */ public function propagateChange($internalPath, $time) { $cache = $this->storage->getCache($internalPath); $parentId = $cache->getParentId($internalPath); $propagatedEntries = []; while ($parentId !== -1) { $entry = $cache->get($parentId); $propagatedEntries[] = $entry; if (!$entry) { return $propagatedEntries; } $mtime = max($time, $entry['mtime']); $cache->update($parentId, ['mtime' => $mtime, 'etag' => $this->storage->getETag($entry['path'])]); $parentId = $entry['parent']; } return $propagatedEntries; }
/** * get all the metadata of a file or folder * * * * @param string $path * @return array with metadata of the file */ public function getData($path) { if (!$this->storage->isReadable($path)) { //cant read, nothing we can do \OCP\Util::writeLog('OC\\Files\\Cache\\Scanner', "!!! Path '{$path}' is not readable !!!", \OCP\Util::DEBUG); return null; } $data = array(); $data['mimetype'] = $this->storage->getMimeType($path); $data['mtime'] = $this->storage->filemtime($path); if ($data['mimetype'] == 'httpd/unix-directory') { $data['size'] = -1; //unknown } else { $data['size'] = $this->storage->filesize($path); } $data['etag'] = $this->storage->getETag($path); $data['storage_mtime'] = $data['mtime']; return $data; }
/** * @param string $internalPath * @param int $time * @param int $sizeDifference number of bytes the file has grown * @return array[] all propagated entries */ public function propagateChange($internalPath, $time, $sizeDifference = 0) { $cache = $this->storage->getCache($internalPath); $parentId = $cache->getParentId($internalPath); $propagatedEntries = []; while ($parentId !== -1) { $entry = $cache->get($parentId); $propagatedEntries[] = $entry; if (!$entry) { return $propagatedEntries; } $mtime = max($time, $entry['mtime']); if ($entry['size'] === -1) { $newSize = -1; } else { $newSize = $entry['size'] + $sizeDifference; } $cache->update($parentId, ['mtime' => $mtime, 'etag' => $this->storage->getETag($entry['path']), 'size' => $newSize]); $parentId = $entry['parent']; } return $propagatedEntries; }
/** * get all the metadata of a file or folder * * * * @param string $path * @return array an array of metadata of the file */ public function getData($path) { $permissions = $this->storage->getPermissions($path); if (!$permissions & \OCP\PERMISSION_READ) { //cant read, nothing we can do \OCP\Util::writeLog('OC\\Files\\Cache\\Scanner', "!!! Path '{$path}' is not accessible or present !!!", \OCP\Util::DEBUG); return null; } $data = array(); $data['mimetype'] = $this->storage->getMimeType($path); $data['mtime'] = $this->storage->filemtime($path); if ($data['mimetype'] == 'httpd/unix-directory') { $data['size'] = -1; //unknown } else { $data['size'] = $this->storage->filesize($path); } $data['etag'] = $this->storage->getETag($path); $data['storage_mtime'] = $data['mtime']; $data['permissions'] = $permissions; return $data; }
/** * scan a single file and store it in the cache * * @param string $file * @param int $reuseExisting * @param bool $parentExistsInCache * @return array with metadata of the scanned file */ public function scanFile($file, $reuseExisting = 0, $parentExistsInCache = false) { if (!self::isPartialFile($file) and !Filesystem::isFileBlacklisted($file)) { $this->emit('\\OC\\Files\\Cache\\Scanner', 'scanFile', array($file, $this->storageId)); \OC_Hook::emit('\\OC\\Files\\Cache\\Scanner', 'scan_file', array('path' => $file, 'storage' => $this->storageId)); $data = $this->getData($file); if ($data) { if ($file and !$parentExistsInCache) { $parent = dirname($file); if ($parent === '.' or $parent === '/') { $parent = ''; } if (!$this->cache->inCache($parent)) { $this->scanFile($parent); } } $newData = $data; $cacheData = $this->cache->get($file); if ($cacheData) { if (isset($cacheData['fileid'])) { $this->permissionsCache->remove($cacheData['fileid']); } if ($reuseExisting) { // prevent empty etag $etag = $cacheData['etag']; $propagateETagChange = false; if (empty($etag)) { $etag = $data['etag']; $propagateETagChange = true; } // only reuse data if the file hasn't explicitly changed if (isset($data['mtime']) && isset($cacheData['mtime']) && $data['mtime'] === $cacheData['mtime']) { if ($reuseExisting & self::REUSE_SIZE && $data['size'] === -1) { $data['size'] = $cacheData['size']; } if ($reuseExisting & self::REUSE_ETAG) { $data['etag'] = $etag; if ($propagateETagChange) { $parent = $file; while ($parent !== '') { $parent = dirname($parent); if ($parent === '.') { $parent = ''; } $parentCacheData = $this->cache->get($parent); $this->cache->update($parentCacheData['fileid'], array('etag' => $this->storage->getETag($parent))); } } } } // Only update metadata that has changed $newData = array_diff_assoc($data, $cacheData); if (isset($newData['etag'])) { $cacheDataString = print_r($cacheData, true); $dataString = print_r($data, true); \OCP\Util::writeLog('OC\\Files\\Cache\\Scanner', "!!! No reuse of etag for '{$file}' !!! \ncache: {$cacheDataString} \ndata: {$dataString}", \OCP\Util::DEBUG); } } } if (!empty($newData)) { $this->cache->put($file, $newData); $this->emit('\\OC\\Files\\Cache\\Scanner', 'postScanFile', array($file, $this->storageId)); \OC_Hook::emit('\\OC\\Files\\Cache\\Scanner', 'post_scan_file', array('path' => $file, 'storage' => $this->storageId)); } } else { $this->cache->remove($file); } return $data; } return null; }
/** * get the ETag for a file or folder * * @param string $path * @return string */ public function getETag($path) { return $this->storage->getETag($path); }