summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJörn Friedrich Dreyer <jfd@butonic.de>2014-07-31 18:27:47 +0200
committerJörn Friedrich Dreyer <jfd@butonic.de>2014-07-31 18:27:47 +0200
commitdc6180427c8b0729ce00fb1cae210e34b173e005 (patch)
treeedb98dc2c8a1eb9a6c349588e9fd47726eb4429d
parent4eb2b4e1b087234499f2721bc474fa979a47f1e0 (diff)
parent1af436cb59dcb28892edc2c2edc33f178cbeb66f (diff)
downloadnextcloud-server-dc6180427c8b0729ce00fb1cae210e34b173e005.tar.gz
nextcloud-server-dc6180427c8b0729ce00fb1cae210e34b173e005.zip
Merge pull request #10048 from owncloud/fix_search_in_shared_files
traverse folders in php to search in shared files
-rw-r--r--apps/files_sharing/lib/cache.php85
-rw-r--r--apps/files_sharing/tests/cache.php78
2 files changed, 101 insertions, 62 deletions
diff --git a/apps/files_sharing/lib/cache.php b/apps/files_sharing/lib/cache.php
index 209aa49dfa4..7f7197307bd 100644
--- a/apps/files_sharing/lib/cache.php
+++ b/apps/files_sharing/lib/cache.php
@@ -275,12 +275,34 @@ class Shared_Cache extends Cache {
*/
public function search($pattern) {
- $where = '`name` LIKE ? AND ';
+ $pattern = trim($pattern,'%');
- // normalize pattern
- $value = $this->normalize($pattern);
+ $normalizedPattern = $this->normalize($pattern);
- return $this->searchWithWhere($where, $value);
+ $result = array();
+ $exploreDirs = array('');
+ while (count($exploreDirs) > 0) {
+ $dir = array_pop($exploreDirs);
+ $files = $this->getFolderContents($dir);
+ // no results?
+ if (!$files) {
+ // maybe it's a single shared file
+ $file = $this->get('');
+ if ($normalizedPattern === '' || stristr($file['name'], $normalizedPattern) !== false) {
+ $result[] = $file;
+ }
+ continue;
+ }
+ foreach ($files as $file) {
+ if ($normalizedPattern === '' || stristr($file['name'], $normalizedPattern) !== false) {
+ $result[] = $file;
+ }
+ if ($file['mimetype'] === 'httpd/unix-directory') {
+ $exploreDirs[] = ltrim($dir . '/' . $file['name'], '/');
+ }
+ }
+ }
+ return $result;
}
@@ -297,10 +319,6 @@ class Shared_Cache extends Cache {
$mimetype = null;
}
- // note: searchWithWhere is currently broken as it doesn't
- // recurse into subdirs nor returns the correct
- // file paths, so using getFolderContents() for now
-
$result = array();
$exploreDirs = array('');
while (count($exploreDirs) > 0) {
@@ -327,57 +345,6 @@ class Shared_Cache extends Cache {
}
/**
- * The maximum number of placeholders that can be used in an SQL query.
- * Value MUST be <= 1000 for oracle:
- * see ORA-01795 maximum number of expressions in a list is 1000
- * FIXME we should get this from doctrine as other DBs allow a lot more placeholders
- */
- const MAX_SQL_CHUNK_SIZE = 1000;
-
- /**
- * search for files with a custom where clause and value
- * the $wherevalue will be array_merge()d with the file id chunks
- *
- * @param string $sqlwhere
- * @param string $wherevalue
- * @return array
- */
- private function searchWithWhere($sqlwhere, $wherevalue, $chunksize = self::MAX_SQL_CHUNK_SIZE) {
-
- $ids = $this->getAll();
-
- $files = array();
-
- // divide into chunks
- $chunks = array_chunk($ids, $chunksize);
-
- foreach ($chunks as $chunk) {
- $placeholders = join(',', array_fill(0, count($chunk), '?'));
- $sql = 'SELECT `fileid`, `storage`, `path`, `parent`, `name`, `mimetype`, `mimepart`, `size`, `mtime`,
- `encrypted`, `unencrypted_size`, `etag`
- FROM `*PREFIX*filecache` WHERE ' . $sqlwhere . ' `fileid` IN (' . $placeholders . ')';
-
- $stmt = \OC_DB::prepare($sql);
-
- $result = $stmt->execute(array_merge(array($wherevalue), $chunk));
-
- while ($row = $result->fetchRow()) {
- if (substr($row['path'], 0, 6) === 'files/') {
- $row['path'] = substr($row['path'], 6); // remove 'files/' from path as it's relative to '/Shared'
- }
- $row['mimetype'] = $this->getMimetype($row['mimetype']);
- $row['mimepart'] = $this->getMimetype($row['mimepart']);
- if ($row['encrypted'] or ($row['unencrypted_size'] > 0 and $row['mimetype'] === 'httpd/unix-directory')) {
- $row['encrypted_size'] = $row['size'];
- $row['size'] = $row['unencrypted_size'];
- }
- $files[] = $row;
- }
- }
- return $files;
- }
-
- /**
* get the size of a folder and set it in the cache
*
* @param string $path
diff --git a/apps/files_sharing/tests/cache.php b/apps/files_sharing/tests/cache.php
index 8472c7f1ab0..1b0fe6fdc6d 100644
--- a/apps/files_sharing/tests/cache.php
+++ b/apps/files_sharing/tests/cache.php
@@ -95,6 +95,80 @@ class Test_Files_Sharing_Cache extends Test_Files_Sharing_Base {
parent::tearDown();
}
+ function searchDataProvider() {
+ return array(
+ array('%another%',
+ array(
+ array('name' => 'another too.txt', 'path' => 'subdir/another too.txt'),
+ array('name' => 'another.txt', 'path' => 'subdir/another.txt'),
+ )
+ ),
+ array('%Another%',
+ array(
+ array('name' => 'another too.txt', 'path' => 'subdir/another too.txt'),
+ array('name' => 'another.txt', 'path' => 'subdir/another.txt'),
+ )
+ ),
+ array('%dir%',
+ array(
+ array('name' => 'emptydir', 'path' => 'emptydir'),
+ array('name' => 'subdir', 'path' => 'subdir'),
+ array('name' => 'shareddir', 'path' => ''),
+ )
+ ),
+ array('%Dir%',
+ array(
+ array('name' => 'emptydir', 'path' => 'emptydir'),
+ array('name' => 'subdir', 'path' => 'subdir'),
+ array('name' => 'shareddir', 'path' => ''),
+ )
+ ),
+ array('%txt%',
+ array(
+ array('name' => 'bar.txt', 'path' => 'bar.txt'),
+ array('name' => 'another too.txt', 'path' => 'subdir/another too.txt'),
+ array('name' => 'another.txt', 'path' => 'subdir/another.txt'),
+ )
+ ),
+ array('%Txt%',
+ array(
+ array('name' => 'bar.txt', 'path' => 'bar.txt'),
+ array('name' => 'another too.txt', 'path' => 'subdir/another too.txt'),
+ array('name' => 'another.txt', 'path' => 'subdir/another.txt'),
+ )
+ ),
+ array('%',
+ array(
+ array('name' => 'bar.txt', 'path' => 'bar.txt'),
+ array('name' => 'emptydir', 'path' => 'emptydir'),
+ array('name' => 'subdir', 'path' => 'subdir'),
+ array('name' => 'another too.txt', 'path' => 'subdir/another too.txt'),
+ array('name' => 'another.txt', 'path' => 'subdir/another.txt'),
+ array('name' => 'not a text file.xml', 'path' => 'subdir/not a text file.xml'),
+ array('name' => 'shareddir', 'path' => ''),
+ )
+ ),
+ array('%nonexistant%',
+ array(
+ )
+ ),
+ );
+ }
+
+ /**
+ * we cannot use a dataProvider because that would cause the stray hook detection to remove the hooks
+ * that were added in setUpBeforeClass.
+ */
+ function testSearch() {
+ foreach ($this->searchDataProvider() as $data) {
+ list($pattern, $expectedFiles) = $data;
+
+ $results = $this->sharedStorage->getCache()->search($pattern);
+
+ $this->verifyFiles($expectedFiles, $results);
+ }
+
+ }
/**
* Test searching by mime type
*/
@@ -115,8 +189,6 @@ class Test_Files_Sharing_Cache extends Test_Files_Sharing_Base {
),
);
$this->verifyFiles($check, $results);
-
- $this->verifyFiles($check, $results);
}
function testGetFolderContentsInRoot() {
@@ -245,7 +317,7 @@ class Test_Files_Sharing_Cache extends Test_Files_Sharing_Base {
}
}
}
- $this->assertTrue(empty($results));
+ $this->assertEquals(array(), $results);
}
/**