Fix sharing a single file gave 404

Added test to check that this works for a single file
This commit is contained in:
nathangray 2020-04-08 11:38:57 -06:00
parent f4e64e18b3
commit 0fb4176067
3 changed files with 100 additions and 10 deletions

View File

@ -95,16 +95,16 @@ class Sharing
*/
public static function get_token()
{
// WebDAV has no concept of a query string and clients (including cadaver)
// seem to pass '?' unencoded, so we need to extract the path info out
// of the request URI ourselves
// if request URI contains a full url, remove schema and domain
// WebDAV has no concept of a query string and clients (including cadaver)
// seem to pass '?' unencoded, so we need to extract the path info out
// of the request URI ourselves
// if request URI contains a full url, remove schema and domain
$matches = null;
if (preg_match('|^https?://[^/]+(/.*)$|', $path_info=$_SERVER['REQUEST_URI'], $matches))
{
$path_info = $matches[1];
}
$path_info = substr($path_info, strlen($_SERVER['SCRIPT_NAME']));
if (preg_match('|^https?://[^/]+(/.*)$|', $path_info=$_SERVER['REQUEST_URI'], $matches))
{
$path_info = $matches[1];
}
$path_info = substr($path_info, strlen($_SERVER['SCRIPT_NAME']));
list(, $token/*, $path*/) = preg_split('|[/?]|', $path_info, 3);
list($token) = explode(':', $token);
@ -521,8 +521,15 @@ class Sharing
Header\Content::disposition(Vfs::basename($this->share['share_path']), false);
}
$GLOBALS['egw']->session->commit_session();
// WebDAV always looks at the original request for a single file so make sure the file is found at the root
Vfs::$is_root = true;
unset($GLOBALS['egw_info']['server']['vfs_fstab']);
Vfs::mount($this->share['resolve_url'], '/', false, false, true);
Vfs::clearstatcache();
$webdav_server = new Vfs\WebDAV();
$webdav_server->ServeRequest(Vfs::concat($this->share['share_root'], $this->share['share_token']));
$webdav_server->ServeRequest(Vfs::concat('/', $this->share['share_token']));
return;
}
return $this->get_ui();

View File

@ -494,6 +494,11 @@ class SharingBase extends LoggedInTest
{
$this->checkDirectoryLink($link, $share);
}
else
{
// If it's a file, check to make sure we get the file
$this->checkSharedFile($link, $path);
}
// Load share
$this->setup_info();
@ -564,6 +569,46 @@ class SharingBase extends LoggedInTest
unset($data->data->content->nm->actions);
//var_dump($data->data->content->nm);
}
/**
* Check that we actually find the file we shared at the target link
*
* @param $link Share URL
* @param $file Vfs path to file
*/
public function checkSharedFile($link, $mimetype)
{
stream_context_set_default(
array(
'http' => array(
'method' => 'HEAD'
)
)
);
$headers = get_headers($link);
$this->assertEquals('200', substr($headers[0], 9, 3), 'Did not find the file, got ' . $headers[0]);
$indexed_headers = array();
foreach($headers as &$header)
{
list($key, $value) = explode(': ', $header);
if(is_string($indexed_headers[$key]))
{
$indexed_headers[$key] = array($indexed_headers[$key]);
}
if(is_array($indexed_headers[$key]))
{
$indexed_headers[$key][] = $value;
}
else
{
$indexed_headers[$key] = $value;
}
}
$this->assertStringContainsString($mimetype, $indexed_headers['Content-Type'], 'Wrong file type');
}
protected function setup_info()
{
// Copied from share.php

View File

@ -19,6 +19,7 @@ namespace EGroupware\Api\Vfs;
require_once __DIR__ . '/SharingBase.php';
use EGroupware\Api\LoggedInTest as LoggedInTest;
use EGroupware\Api\Vfs;
@ -260,4 +261,41 @@ class SharingTest extends SharingBase
$this->assertEquals($file, $created_share['share_path']);
}
/**
* Test that a share of a single file gives the file (uses WebDAV)
*/
public function testSingleFile()
{
$dir = Vfs::get_home_dir().'/';
// Plain text file
$file = $dir.'test_file.txt';
$content = 'Testing that sharing a single (non-editable) file gives us the file.';
$this->assertTrue(
file_put_contents(Vfs::PREFIX.$file, $content) !== FALSE,
'Unable to write test file "' . Vfs::PREFIX . $file .'" - check file permissions for CLI user'
);
$this->files[] = $file;
$mimetype = Vfs::mime_content_type($file);
// Create and use link
$extra = array();
$this->getShareExtra($file, Sharing::READONLY, $extra);
$share = $this->createShare($file, Sharing::READONLY, $extra);
$link = Vfs\Sharing::share2link($share);
// Re-init, since they look at user, fstab, etc.
// Also, further tests that access the filesystem fail if we don't
Vfs::clearstatcache();
Vfs::init_static();
Vfs\StreamWrapper::init_static();
// Log out & clear cache
LoggedInTest::tearDownAfterClass();
$this->checkSharedFile($link, $mimetype);
}
}