diff options
author | Kyle Fazzari <kyrofa@ubuntu.com> | 2017-11-22 21:30:21 -0800 |
---|---|---|
committer | Kyle Fazzari <kyrofa@ubuntu.com> | 2017-11-22 21:41:40 -0800 |
commit | 7f8f3dc21bdfa8373b79f17933aaad33ec315aed (patch) | |
tree | f1b1778aeae42a5b7659b48a2273453dea3b7ed9 /lib/private/Template | |
parent | fd46475f6efa445d906a07b9f1f47f188623be5b (diff) | |
download | nextcloud-server-7f8f3dc21bdfa8373b79f17933aaad33ec315aed.tar.gz nextcloud-server-7f8f3dc21bdfa8373b79f17933aaad33ec315aed.zip |
CSSResourceLocator: handle SCSS in apps outside root
Currently static CSS files work fine in apps outside of the root.
However, as soon as an app uses SCSS, Nextcloud starts being unable to
find the web root.
Fix this problem by backporting select snippets from master
specifically targeting this issue, and add a test to ensure it doesn't
regress.
Fix #5289
Signed-off-by: Kyle Fazzari <kyrofa@ubuntu.com>
Diffstat (limited to 'lib/private/Template')
-rw-r--r-- | lib/private/Template/CSSResourceLocator.php | 53 | ||||
-rwxr-xr-x | lib/private/Template/ResourceLocator.php | 90 |
2 files changed, 74 insertions, 69 deletions
diff --git a/lib/private/Template/CSSResourceLocator.php b/lib/private/Template/CSSResourceLocator.php index 29f3efaa8da..d5e9ce732cc 100644 --- a/lib/private/Template/CSSResourceLocator.php +++ b/lib/private/Template/CSSResourceLocator.php @@ -6,6 +6,7 @@ * @author Joas Schilling <coding@schilljs.com> * @author Morris Jobke <hey@morrisjobke.de> * @author Thomas Müller <thomas.mueller@tmit.eu> + * @author Kyle Fazzari <kyrofa@ubuntu.com> * * @license AGPL-3.0 * @@ -122,45 +123,25 @@ class CSSResourceLocator extends ResourceLocator { parent::append($root, $file, $webRoot, $throw); } else { if (!$webRoot) { - $tmpRoot = realpath($root); - /* - * traverse the potential web roots upwards in the path - * - * example: - * - root: /srv/www/apps/myapp - * - available mappings: ['/srv/www'] - * - * First we check if a mapping for /srv/www/apps/myapp is available, - * then /srv/www/apps, /srv/www/apps, /srv/www, ... until we find a - * valid web root - */ - do { - if (isset($this->mapping[$tmpRoot])) { - $webRoot = $this->mapping[$tmpRoot]; - break; + $webRoot = $this->findWebRoot($root); + + if ($webRoot === null) { + $webRoot = ''; + $this->logger->error('ResourceLocator can not find a web root (root: {root}, file: {file}, webRoot: {webRoot}, throw: {throw})', [ + 'app' => 'lib', + 'root' => $root, + 'file' => $file, + 'webRoot' => $webRoot, + 'throw' => $throw ? 'true' : 'false' + ]); + + if ($throw && $root === '/') { + throw new ResourceNotFoundException($file, $webRoot); } - - if ($tmpRoot === '/') { - $webRoot = ''; - $this->logger->error('ResourceLocator can not find a web root (root: {root}, file: {file}, webRoot: {webRoot}, throw: {throw})', [ - 'app' => 'lib', - 'root' => $root, - 'file' => $file, - 'webRoot' => $webRoot, - 'throw' => $throw ? 'true' : 'false' - ]); - break; - } - $tmpRoot = dirname($tmpRoot); - } while(true); - - } - - if ($throw && $tmpRoot === '/') { - throw new ResourceNotFoundException($file, $webRoot); + } } - $this->resources[] = array($tmpRoot, $webRoot, $file); + $this->resources[] = array($webRoot? : '/', $webRoot, $file); } } } diff --git a/lib/private/Template/ResourceLocator.php b/lib/private/Template/ResourceLocator.php index f721906e12b..0d7767fdd0b 100755 --- a/lib/private/Template/ResourceLocator.php +++ b/lib/private/Template/ResourceLocator.php @@ -7,6 +7,7 @@ * @author Jörn Friedrich Dreyer <jfd@butonic.de> * @author Morris Jobke <hey@morrisjobke.de> * @author Robin McCorkell <robin@mccorkell.me.uk> + * @author Kyle Fazzari <kyrofa@ubuntu.com> * * @license AGPL-3.0 * @@ -107,6 +108,50 @@ abstract class ResourceLocator { } /** + * Attempt to find the webRoot + * + * traverse the potential web roots upwards in the path + * + * example: + * - root: /srv/www/apps/myapp + * - available mappings: ['/srv/www'] + * + * First we check if a mapping for /srv/www/apps/myapp is available, + * then /srv/www/apps, /srv/www/apps, /srv/www, ... until we find a + * valid web root + * + * @param string $root + * @return string|null The web root or null on failure + */ + protected function findWebRoot($root) { + $webRoot = null; + $tmpRoot = $root; + + while ($webRoot === null) { + if (isset($this->mapping[$tmpRoot])) { + $webRoot = $this->mapping[$tmpRoot]; + break; + } + + if ($tmpRoot === '/') { + break; + } + + $tmpRoot = dirname($tmpRoot); + } + + if ($webRoot === null) { + $realpath = realpath($root); + + if ($realpath && ($realpath !== $root)) { + return $this->findWebRoot($realpath); + } + } + + return $webRoot; + } + + /** * append the $file resource at $root * * @param string $root path to check @@ -116,7 +161,6 @@ abstract class ResourceLocator { * @throws ResourceNotFoundException Only thrown when $throw is true and the resource is missing */ protected function append($root, $file, $webRoot = null, $throw = true) { - if (!is_string($root)) { if ($throw) { throw new ResourceNotFoundException($file, $webRoot); @@ -125,38 +169,18 @@ abstract class ResourceLocator { } if (!$webRoot) { - $tmpRoot = realpath($root); - /* - * traverse the potential web roots upwards in the path - * - * example: - * - root: /srv/www/apps/myapp - * - available mappings: ['/srv/www'] - * - * First we check if a mapping for /srv/www/apps/myapp is available, - * then /srv/www/apps, /srv/www/apps, /srv/www, ... until we find a - * valid web root - */ - do { - if (isset($this->mapping[$tmpRoot])) { - $webRoot = $this->mapping[$tmpRoot]; - break; - } - - if ($tmpRoot === '/') { - $webRoot = ''; - $this->logger->error('ResourceLocator can not find a web root (root: {root}, file: {file}, webRoot: {webRoot}, throw: {throw})', [ - 'app' => 'lib', - 'root' => $root, - 'file' => $file, - 'webRoot' => $webRoot, - 'throw' => $throw ? 'true' : 'false' - ]); - break; - } - $tmpRoot = dirname($tmpRoot); - } while(true); - + $webRoot = $this->findWebRoot($root); + + if ($webRoot === null) { + $webRoot = ''; + $this->logger->error('ResourceLocator can not find a web root (root: {root}, file: {file}, webRoot: {webRoot}, throw: {throw})', [ + 'app' => 'lib', + 'root' => $root, + 'file' => $file, + 'webRoot' => $webRoot, + 'throw' => $throw ? 'true' : 'false' + ]); + } } $this->resources[] = array($root, $webRoot, $file); |