YamlFormatter.php 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103
  1. <?php
  2. /**
  3. * @package Grav\Framework\File\Formatter
  4. *
  5. * @copyright Copyright (C) 2015 - 2018 Trilby Media, LLC. All rights reserved.
  6. * @license MIT License; see LICENSE file for details.
  7. */
  8. namespace Grav\Framework\File\Formatter;
  9. use Symfony\Component\Yaml\Exception\DumpException;
  10. use Symfony\Component\Yaml\Exception\ParseException;
  11. use Symfony\Component\Yaml\Yaml as YamlParser;
  12. use RocketTheme\Toolbox\Compat\Yaml\Yaml as FallbackYamlParser;
  13. class YamlFormatter implements FormatterInterface
  14. {
  15. /** @var array */
  16. private $config;
  17. public function __construct(array $config = [])
  18. {
  19. $this->config = $config + [
  20. 'file_extension' => '.yaml',
  21. 'inline' => 5,
  22. 'indent' => 2,
  23. 'native' => true,
  24. 'compat' => true
  25. ];
  26. }
  27. /**
  28. * @deprecated 1.5 Use $formatter->getDefaultFileExtension() instead.
  29. */
  30. public function getFileExtension()
  31. {
  32. return $this->getDefaultFileExtension();
  33. }
  34. /**
  35. * {@inheritdoc}
  36. */
  37. public function getDefaultFileExtension()
  38. {
  39. $extensions = $this->getSupportedFileExtensions();
  40. return (string) reset($extensions);
  41. }
  42. /**
  43. * {@inheritdoc}
  44. */
  45. public function getSupportedFileExtensions()
  46. {
  47. return (array) $this->config['file_extension'];
  48. }
  49. /**
  50. * {@inheritdoc}
  51. */
  52. public function encode($data, $inline = null, $indent = null)
  53. {
  54. try {
  55. return (string) YamlParser::dump(
  56. $data,
  57. $inline ? (int) $inline : $this->config['inline'],
  58. $indent ? (int) $indent : $this->config['indent'],
  59. YamlParser::DUMP_EXCEPTION_ON_INVALID_TYPE
  60. );
  61. } catch (DumpException $e) {
  62. throw new \RuntimeException('Encoding YAML failed: ' . $e->getMessage(), 0, $e);
  63. }
  64. }
  65. /**
  66. * {@inheritdoc}
  67. */
  68. public function decode($data)
  69. {
  70. // Try native PECL YAML PHP extension first if available.
  71. if ($this->config['native'] && function_exists('yaml_parse')) {
  72. // Safely decode YAML.
  73. $saved = @ini_get('yaml.decode_php');
  74. @ini_set('yaml.decode_php', 0);
  75. $decoded = @yaml_parse($data);
  76. @ini_set('yaml.decode_php', $saved);
  77. if ($decoded !== false) {
  78. return (array) $decoded;
  79. }
  80. }
  81. try {
  82. return (array) YamlParser::parse($data);
  83. } catch (ParseException $e) {
  84. if ($this->config['compat']) {
  85. return (array) FallbackYamlParser::parse($data);
  86. }
  87. throw new \RuntimeException('Decoding YAML failed: ' . $e->getMessage(), 0, $e);
  88. }
  89. }
  90. }