From 261ea624720f61bd5638a458653f599836ce2d43 Mon Sep 17 00:00:00 2001 From: Matias Griese Date: Fri, 20 Apr 2018 14:03:49 +0300 Subject: [PATCH] Added compatibility mode to fall back to Symfony YAML 2.8 when needed --- composer.lock | 9 +++++---- system/config/system.yaml | 6 +++++- system/src/Grav/Common/Data/Validation.php | 20 +++++++++++++------ system/src/Grav/Common/File/CompiledFile.php | 3 --- system/src/Grav/Common/GPM/GPM.php | 11 +++++++--- system/src/Grav/Common/Page/Page.php | 10 +++++----- .../Common/Service/ConfigServiceProvider.php | 14 ++++++++++++- system/src/Grav/Common/Twig/Twig.php | 5 ++++- .../src/Grav/Console/Cli/InstallCommand.php | 9 ++++++--- system/src/Grav/Console/ConsoleTrait.php | 6 ++++-- .../src/Grav/Console/Gpm/VersionCommand.php | 7 +++++-- 11 files changed, 69 insertions(+), 31 deletions(-) diff --git a/composer.lock b/composer.lock index 7929fc0a20..d52c4fb7fe 100644 --- a/composer.lock +++ b/composer.lock @@ -1208,12 +1208,12 @@ "source": { "type": "git", "url": "https://github.com/rockettheme/toolbox.git", - "reference": "9434fb837b84fbb088b1cbcfbe482b6543c28450" + "reference": "52dfd040537ea609f6ce1d608517d3d970a27305" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/rockettheme/toolbox/zipball/9434fb837b84fbb088b1cbcfbe482b6543c28450", - "reference": "9434fb837b84fbb088b1cbcfbe482b6543c28450", + "url": "https://api.github.com/repos/rockettheme/toolbox/zipball/52dfd040537ea609f6ce1d608517d3d970a27305", + "reference": "52dfd040537ea609f6ce1d608517d3d970a27305", "shasum": "" }, "require": { @@ -1230,6 +1230,7 @@ "psr-4": { "RocketTheme\\Toolbox\\ArrayTraits\\": "ArrayTraits/src", "RocketTheme\\Toolbox\\Blueprints\\": "Blueprints/src", + "RocketTheme\\Toolbox\\Compat\\": "Compat/src", "RocketTheme\\Toolbox\\DI\\": "DI/src", "RocketTheme\\Toolbox\\Event\\": "Event/src", "RocketTheme\\Toolbox\\File\\": "File/src", @@ -1251,7 +1252,7 @@ "source": "https://github.com/rockettheme/toolbox/tree/feature/grav15", "issues": "https://github.com/rockettheme/toolbox/issues" }, - "time": "2018-04-20T08:06:27+00:00" + "time": "2018-04-20T09:18:58+00:00" }, { "name": "seld/cli-prompt", diff --git a/system/config/system.yaml b/system/config/system.yaml index c05ee4abf7..065e059f20 100644 --- a/system/config/system.yaml +++ b/system/config/system.yaml @@ -88,7 +88,7 @@ twig: cache: true # Set to true to enable Twig caching debug: true # Enable Twig debug auto_reload: true # Refresh cache on changes - autoescape: false # Autoescape Twig vars + autoescape: false # Autoescape Twig vars (DEPRECATED, always enabled in strict mode) undefined_functions: true # Allow undefined functions undefined_filters: true # Allow undefined filters umask_fix: false # By default Twig creates cached files as 755, fix switches this to 775 @@ -146,3 +146,7 @@ gpm: method: 'auto' # Either 'curl', 'fopen' or 'auto'. 'auto' will try fopen first and if not available cURL verify_peer: true # Sometimes on some systems (Windows most commonly) GPM is unable to connect because the SSL certificate cannot be verified. Disabling this setting might help. official_gpm_only: true # By default GPM direct-install will only allow URLs via the official GPM proxy to ensure security + +strict_mode: + yaml_compat: true # Grav 1.5+: Enables YAML backwards compatibility + twig_compat: true # Grav 1.5+: Enables deprecated Twig autoescape setting (autoescape: false) diff --git a/system/src/Grav/Common/Data/Validation.php b/system/src/Grav/Common/Data/Validation.php index 8ab5cf1854..2cdf6b0664 100644 --- a/system/src/Grav/Common/Data/Validation.php +++ b/system/src/Grav/Common/Data/Validation.php @@ -11,8 +11,8 @@ use Grav\Common\Grav; use Grav\Common\Utils; use Symfony\Component\Yaml\Exception\ParseException; -use Symfony\Component\Yaml\Parser; use Symfony\Component\Yaml\Yaml; +use RocketTheme\Toolbox\Compat\Yaml\Yaml as FallbackYaml; class Validation { @@ -643,13 +643,21 @@ protected static function filterList($value, array $params, array $field) public static function filterYaml($value, $params) { + if (!is_string($value)) { + return $value; + } + try { - if (is_string($value)) { - return (array) Yaml::parse($value); - } else { - return $value; - } + return (array) Yaml::parse($value); } catch (ParseException $e) { + // If YAML compatibility mode is set on, fall back to older YAML parser. + if (Grav::instance()['config']->get('system.strict_mode.yaml_compat', true)) { + try { + return (array) FallbackYaml::parse($value); + } catch (ParseException $e2) { + } + } + return $value; } } diff --git a/system/src/Grav/Common/File/CompiledFile.php b/system/src/Grav/Common/File/CompiledFile.php index a0e230f143..4da55d9eb1 100644 --- a/system/src/Grav/Common/File/CompiledFile.php +++ b/system/src/Grav/Common/File/CompiledFile.php @@ -20,9 +20,6 @@ trait CompiledFile */ public function content($var = null) { - // Set some options - $this->settings(['native' => true, 'compat' => true]); - try { // If nothing has been loaded, attempt to get pre-compiled version of the file first. if ($var === null && $this->raw === null && $this->content === null) { diff --git a/system/src/Grav/Common/GPM/GPM.php b/system/src/Grav/Common/GPM/GPM.php index a7cbee402b..696ba657cd 100644 --- a/system/src/Grav/Common/GPM/GPM.php +++ b/system/src/Grav/Common/GPM/GPM.php @@ -13,7 +13,7 @@ use Grav\Common\Inflector; use Grav\Common\Iterator; use Grav\Common\Utils; -use Symfony\Component\Yaml\Yaml; +use RocketTheme\Toolbox\File\YamlFile; class GPM extends Iterator { @@ -624,7 +624,10 @@ public static function getBlueprints($source) return false; } - $blueprint = (array)Yaml::parse(file_get_contents($blueprint_file)); + $file = YamlFile::instance($blueprint_file); + $blueprint = (array)$file->content(); + $file->free(); + return $blueprint; } @@ -873,7 +876,9 @@ public function getDependencies($packages) // get currently installed version $locator = Grav::instance()['locator']; $blueprints_path = $locator->findResource('plugins://' . $dependency_slug . DS . 'blueprints.yaml'); - $package_yaml = Yaml::parse(file_get_contents($blueprints_path)); + $file = YamlFile::instance($blueprints_path); + $package_yaml = $file->content(); + $file->free(); $currentlyInstalledVersion = $package_yaml['version']; // if requirement is next significant release, check is compatible with currently installed version, might not be diff --git a/system/src/Grav/Common/Page/Page.php b/system/src/Grav/Common/Page/Page.php index a4027a5143..072f747abd 100644 --- a/system/src/Grav/Common/Page/Page.php +++ b/system/src/Grav/Common/Page/Page.php @@ -12,6 +12,7 @@ use Grav\Common\Cache; use Grav\Common\Config\Config; use Grav\Common\Data\Blueprint; +use Grav\Common\File\CompiledYamlFile; use Grav\Common\Filesystem\Folder; use Grav\Common\Grav; use Grav\Common\Language\Language; @@ -318,8 +319,6 @@ public function header($var = null) if (!$this->header) { $file = $this->file(); if ($file) { - // Set some options - $file->settings(['native' => true, 'compat' => true]); try { $this->raw_content = $file->markdown(); $this->frontmatter = $file->frontmatter(); @@ -328,11 +327,12 @@ public function header($var = null) if (!Utils::isAdminPlugin()) { // If there's a `frontmatter.yaml` file merge that in with the page header // note page's own frontmatter has precedence and will overwrite any defaults - $frontmatter_file = $this->path . '/' . $this->folder . '/frontmatter.yaml'; - if (file_exists($frontmatter_file)) { - $frontmatter_data = (array)Yaml::parse(file_get_contents($frontmatter_file)); + $frontmatterFile = CompiledYamlFile::instance($this->path . '/' . $this->folder . '/frontmatter.yaml'); + if ($frontmatterFile->exists()) { + $frontmatter_data = (array)$frontmatterFile->content(); $this->header = (object)array_replace_recursive($frontmatter_data, (array)$this->header); + $frontmatterFile->free(); } // Process frontmatter with Twig if enabled if (Grav::instance()['config']->get('system.pages.frontmatter.process_twig') === true) { diff --git a/system/src/Grav/Common/Service/ConfigServiceProvider.php b/system/src/Grav/Common/Service/ConfigServiceProvider.php index 25c1a126ee..379c042e72 100644 --- a/system/src/Grav/Common/Service/ConfigServiceProvider.php +++ b/system/src/Grav/Common/Service/ConfigServiceProvider.php @@ -16,6 +16,7 @@ use Grav\Common\Config\Setup; use Pimple\Container; use Pimple\ServiceProviderInterface; +use RocketTheme\Toolbox\File\YamlFile; use RocketTheme\Toolbox\ResourceLocator\UniformResourceLocator; class ConfigServiceProvider implements ServiceProviderInterface @@ -31,7 +32,14 @@ public function register(Container $container) }; $container['config'] = function ($c) { - return static::load($c); + $config = static::load($c); + + // After configuration has been loaded, we can disable YAML compatibility if strict mode has been enabled. + if (!$config->get('system.strict_mode.yaml_compat', true)) { + YamlFile::globalSettings(['compat' => false, 'native' => true]); + } + + return $config; }; $container['languages'] = function ($c) { @@ -65,6 +73,10 @@ public static function blueprints(Container $container) return $blueprints->name("master-{$setup->environment}")->load(); } + /** + * @param Container $container + * @return Config + */ public static function load(Container $container) { /** Setup $setup */ diff --git a/system/src/Grav/Common/Twig/Twig.php b/system/src/Grav/Common/Twig/Twig.php index e1ba281f4a..60024b5ffc 100644 --- a/system/src/Grav/Common/Twig/Twig.php +++ b/system/src/Grav/Common/Twig/Twig.php @@ -113,7 +113,10 @@ public function init() $params['cache'] = new \Twig_Cache_Filesystem($cachePath, \Twig_Cache_Filesystem::FORCE_BYTECODE_INVALIDATION); } - if (!empty($this->autoescape)) { + if (!$config->get('system.strict_mode.twig_compat', true)) { + // Force autoescape on for all files if in strict mode. + $params['autoescape'] = true; + } elseif (!empty($this->autoescape)) { $params['autoescape'] = $this->autoescape; } diff --git a/system/src/Grav/Console/Cli/InstallCommand.php b/system/src/Grav/Console/Cli/InstallCommand.php index ac00256dd5..24d199b2a3 100644 --- a/system/src/Grav/Console/Cli/InstallCommand.php +++ b/system/src/Grav/Console/Cli/InstallCommand.php @@ -9,9 +9,9 @@ namespace Grav\Console\Cli; use Grav\Console\ConsoleCommand; +use RocketTheme\Toolbox\File\YamlFile; use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputOption; -use Symfony\Component\Yaml\Yaml; class InstallCommand extends ConsoleCommand { @@ -71,9 +71,9 @@ protected function serve() // Look for dependencies file in ROOT and USER dir if (file_exists($this->user_path . $dependencies_file)) { - $this->config = Yaml::parse(file_get_contents($this->user_path . $dependencies_file)); + $file = YamlFile::instance($this->user_path . $dependencies_file); } elseif (file_exists($this->destination . $dependencies_file)) { - $this->config = Yaml::parse(file_get_contents($this->destination . $dependencies_file)); + $file = YamlFile::instance($this->destination . $dependencies_file); } else { $this->output->writeln('ERROR Missing .dependencies file in user/ folder'); if ($this->input->getArgument('destination')) { @@ -85,6 +85,9 @@ protected function serve() return; } + $this->config = $file->content(); + $file->free(); + // If yaml config, process if ($this->config) { if (!$this->input->getOption('symlink')) { diff --git a/system/src/Grav/Console/ConsoleTrait.php b/system/src/Grav/Console/ConsoleTrait.php index b6ab3bfe0d..4498172450 100644 --- a/system/src/Grav/Console/ConsoleTrait.php +++ b/system/src/Grav/Console/ConsoleTrait.php @@ -12,11 +12,11 @@ use Grav\Common\Composer; use Grav\Common\GravTrait; use Grav\Console\Cli\ClearCacheCommand; +use RocketTheme\Toolbox\File\YamlFile; use Symfony\Component\Console\Formatter\OutputFormatterStyle; use Symfony\Component\Console\Input\ArrayInput; use Symfony\Component\Console\Input\InputInterface; use Symfony\Component\Console\Output\OutputInterface; -use Symfony\Component\Yaml\Yaml; trait ConsoleTrait { @@ -123,7 +123,9 @@ public function loadLocalConfig() $local_config_file = $home_folder . '/.grav/config'; if (file_exists($local_config_file)) { - $this->local_config = Yaml::parse(file_get_contents($local_config_file)); + $file = YamlFile::instance($local_config_file); + $this->local_config = $file->content(); + $file->free(); return $local_config_file; } diff --git a/system/src/Grav/Console/Gpm/VersionCommand.php b/system/src/Grav/Console/Gpm/VersionCommand.php index c828106c48..eb7872ead8 100644 --- a/system/src/Grav/Console/Gpm/VersionCommand.php +++ b/system/src/Grav/Console/Gpm/VersionCommand.php @@ -11,9 +11,9 @@ use Grav\Common\GPM\GPM; use Grav\Common\GPM\Upgrader; use Grav\Console\ConsoleCommand; +use RocketTheme\Toolbox\File\YamlFile; use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputOption; -use Symfony\Component\Yaml\Yaml; class VersionCommand extends ConsoleCommand { @@ -84,7 +84,10 @@ protected function serve() } } - $package_yaml = Yaml::parse(file_get_contents($blueprints_path)); + $file = YamlFile::instance($blueprints_path); + $package_yaml = $file->content(); + $file->free(); + $version = $package_yaml['version']; if (!$version) {