diff --git a/modules/cms/classes/CmsObject.php b/modules/cms/classes/CmsObject.php index d6451a0fc..9316dbc45 100644 --- a/modules/cms/classes/CmsObject.php +++ b/modules/cms/classes/CmsObject.php @@ -13,6 +13,7 @@ use RecursiveDirectoryIterator; use RecursiveIteratorIterator; use ArrayAccess; use Exception; +use Cms\Contracts\CmsObject as CmsObjectContract; /** * This is a base class for all CMS objects - content files, pages, partials and layouts. @@ -21,7 +22,7 @@ use Exception; * @package october\cms * @author Alexey Bobkov, Samuel Georges */ -class CmsObject extends Extendable implements ArrayAccess +class CmsObject extends Extendable implements ArrayAccess, CmsObjectContract { /** * @var string Specifies the file name corresponding the CMS object. diff --git a/modules/cms/classes/ComponentPartial.php b/modules/cms/classes/ComponentPartial.php index d93b2fc2d..775867da8 100644 --- a/modules/cms/classes/ComponentPartial.php +++ b/modules/cms/classes/ComponentPartial.php @@ -1,20 +1,55 @@ find($fileName); } /** - * Returns the full path to the template file corresponding to this object. + * There is not much point caching a component partial, so this behavior + * reverts to a regular load call. + * @param Cms\Classes\ComponentBase $component + * @param string $fileName + * @return mixed + */ + public static function loadCached($component, $fileName) + { + return static::load($component, $fileName); + } + + /** + * Find a single template by its file name. + * + * @param string $fileName + * @return mixed|static + */ + public function find($fileName) + { + $fileName = $this->validateFileName($fileName); + + $filePath = $this->getFilePath($fileName); + + if (!File::isFile($filePath)) { + return null; + } + + if (($content = @File::get($filePath)) === false) { + return null; + } + + $this->fileName = $fileName; + $this->mtime = File::lastModified($filePath); + $this->content = $content; + return $this; + } + + /** + * Returns true if the specific component contains a matching partial. + * @param \Cms\Classes\ComponentBase $component Specifies a component the file belongs to. + * @param string $fileName Specifies the file name to check. + * @return bool + */ + public static function check(ComponentBase $component, $fileName) + { + $partial = new static($component); + $filePath = $partial->getFilePath($fileName); + if (!strlen(File::extension($filePath))) { + $filePath .= '.'.$partial->getDefaultExtension(); + } + + return File::isFile($filePath); + } + + /** + * Checks the supplied file name for validity. + * @param string $fileName * @return string */ - public function getFullPath() + protected function validateFileName($fileName) { - return static::getFilePath($this->component, $this->fileName); + if (!FileHelper::validatePath($fileName, $this->maxNesting)) { + throw new ApplicationException(Lang::get('cms::lang.cms_object.invalid_file', ['name'=>$fileName])); + } + + if (!strlen(File::extension($fileName))) { + $fileName .= '.'.$this->defaultExtension; + } + + return $fileName; + } + + /** + * Returns the file content. + * @return string + */ + public function getContent() + { + return $this->content; + } + + /** + * Returns the Twig content string. + * @return string + */ + public function getTwigContent() + { + return $this->content; + } + + /** + * Returns the file name. + * @return string + */ + public function getFileName() + { + return $this->fileName; + } + + /** + * Returns the default extension used by this template. + * @return string + */ + public function getDefaultExtension() + { + return $this->defaultExtension; + } + + /** + * Returns the file name without the extension. + * @return string + */ + public function getBaseFileName() + { + $pos = strrpos($this->fileName, '.'); + if ($pos === false) { + return $this->fileName; + } + + return substr($this->fileName, 0, $pos); } /** * Returns the absolute file path. - * @param \Cms\Classes\ComponentBase $component Specifies a component the file belongs to. - * @param string$fileName Specifies the file name to return the path to. + * @param string $fileName Specifies the file name to return the path to. * @return string */ - public static function getFilePath($component, $fileName) + public function getFilePath($fileName = null) { + if ($fileName === null) { + $fileName = $this->fileName; + } + + $component = $this->component; $path = $component->getPath().'/'.$fileName; /* @@ -66,4 +222,12 @@ class ComponentPartial extends CmsObject return $path; } + + // @deprecated This method should be removed globally + // remove if year >= 2016 + public function getFullPath() + { + return $this->getFilePath(); + } + } diff --git a/modules/cms/classes/Controller.php b/modules/cms/classes/Controller.php index b92bb4a99..9663a25c2 100644 --- a/modules/cms/classes/Controller.php +++ b/modules/cms/classes/Controller.php @@ -1276,23 +1276,13 @@ class Controller public function findComponentByPartial($partial) { foreach ($this->page->components as $component) { - $fileName = ComponentPartial::getFilePath($component, $partial); - if (!strlen(File::extension($fileName))) { - $fileName .= '.htm'; - } - - if (File::isFile($fileName)) { + if (ComponentPartial::check($component, $partial)) { return $component; } } foreach ($this->layout->components as $component) { - $fileName = ComponentPartial::getFilePath($component, $partial); - if (!strlen(File::extension($fileName))) { - $fileName .= '.htm'; - } - - if (File::isFile($fileName)) { + if (ComponentPartial::check($component, $partial)) { return $component; } }