[ Index ]

PHP Cross Reference of Joomla 4.2.2 documentation

title

Body

[close]

/libraries/vendor/joomla/registry/src/Format/ -> Ini.php (source)

   1  <?php
   2  /**
   3   * Part of the Joomla Framework Registry Package
   4   *
   5   * @copyright  Copyright (C) 2005 - 2021 Open Source Matters, Inc. All rights reserved.
   6   * @license    GNU General Public License version 2 or later; see LICENSE
   7   */
   8  
   9  namespace Joomla\Registry\Format;
  10  
  11  use Joomla\Registry\FormatInterface;
  12  use Joomla\Utilities\ArrayHelper;
  13  
  14  /**
  15   * INI format handler for Registry.
  16   *
  17   * @since  1.0
  18   */
  19  class Ini implements FormatInterface
  20  {
  21      /**
  22       * Default options array
  23       *
  24       * @var    array
  25       * @since  1.3.0
  26       */
  27      protected static $options = [
  28          'supportArrayValues' => false,
  29          'parseBooleanWords'  => false,
  30          'processSections'    => false,
  31      ];
  32  
  33      /**
  34       * A cache used by stringToObject.
  35       *
  36       * @var    array
  37       * @since  1.0
  38       */
  39      protected static $cache = [];
  40  
  41      /**
  42       * Converts an object into an INI formatted string
  43       * - Unfortunately, there is no way to have ini values nested further than two
  44       * levels deep.  Therefore we will only go through the first two levels of
  45       * the object.
  46       *
  47       * @param   object  $object   Data source object.
  48       * @param   array   $options  Options used by the formatter.
  49       *
  50       * @return  string  INI formatted string.
  51       *
  52       * @since   1.0
  53       */
  54  	public function objectToString($object, array $options = [])
  55      {
  56          $options            = array_merge(static::$options, $options);
  57          $supportArrayValues = $options['supportArrayValues'];
  58  
  59          $local  = [];
  60          $global = [];
  61  
  62          $variables = get_object_vars($object);
  63  
  64          $last = \count($variables);
  65  
  66          // Assume that the first element is in section
  67          $inSection = true;
  68  
  69          // Iterate over the object to set the properties.
  70          foreach ($variables as $key => $value)
  71          {
  72              // If the value is an object then we need to put it in a local section.
  73              if (\is_object($value))
  74              {
  75                  // Add an empty line if previous string wasn't in a section
  76                  if (!$inSection)
  77                  {
  78                      $local[] = '';
  79                  }
  80  
  81                  // Add the section line.
  82                  $local[] = '[' . $key . ']';
  83  
  84                  // Add the properties for this section.
  85                  foreach (get_object_vars($value) as $k => $v)
  86                  {
  87                      if (\is_array($v) && $supportArrayValues)
  88                      {
  89                          $assoc = ArrayHelper::isAssociative($v);
  90  
  91                          foreach ($v as $arrayKey => $item)
  92                          {
  93                              $arrayKey = $assoc ? $arrayKey : '';
  94                              $local[]  = $k . '[' . $arrayKey . ']=' . $this->getValueAsIni($item);
  95                          }
  96                      }
  97                      else
  98                      {
  99                          $local[] = $k . '=' . $this->getValueAsIni($v);
 100                      }
 101                  }
 102  
 103                  // Add empty line after section if it is not the last one
 104                  if (--$last !== 0)
 105                  {
 106                      $local[] = '';
 107                  }
 108              }
 109              elseif (\is_array($value) && $supportArrayValues)
 110              {
 111                  $assoc = ArrayHelper::isAssociative($value);
 112  
 113                  foreach ($value as $arrayKey => $item)
 114                  {
 115                      $arrayKey = $assoc ? $arrayKey : '';
 116                      $global[] = $key . '[' . $arrayKey . ']=' . $this->getValueAsIni($item);
 117                  }
 118              }
 119              else
 120              {
 121                  // Not in a section so add the property to the global array.
 122                  $global[]  = $key . '=' . $this->getValueAsIni($value);
 123                  $inSection = false;
 124              }
 125          }
 126  
 127          return implode("\n", array_merge($global, $local));
 128      }
 129  
 130      /**
 131       * Parse an INI formatted string and convert it into an object.
 132       *
 133       * @param   string  $data     INI formatted string to convert.
 134       * @param   array   $options  An array of options used by the formatter, or a boolean setting to process sections.
 135       *
 136       * @return  object   Data object.
 137       *
 138       * @since   1.0
 139       */
 140  	public function stringToObject($data, array $options = [])
 141      {
 142          $options = array_merge(static::$options, $options);
 143  
 144          // Check the memory cache for already processed strings.
 145          $hash = md5($data . ':' . (int) $options['processSections']);
 146  
 147          if (isset(static::$cache[$hash]))
 148          {
 149              return static::$cache[$hash];
 150          }
 151  
 152          // If no lines present just return the object.
 153          if (empty($data))
 154          {
 155              return new \stdClass;
 156          }
 157  
 158          $obj     = new \stdClass;
 159          $section = false;
 160          $array   = false;
 161          $lines   = explode("\n", $data);
 162  
 163          // Process the lines.
 164          foreach ($lines as $line)
 165          {
 166              // Trim any unnecessary whitespace.
 167              $line = trim($line);
 168  
 169              // Ignore empty lines and comments.
 170              if (empty($line) || ($line[0] === ';'))
 171              {
 172                  continue;
 173              }
 174  
 175              if ($options['processSections'])
 176              {
 177                  $length = \strlen($line);
 178  
 179                  // If we are processing sections and the line is a section add the object and continue.
 180                  if ($line[0] === '[' && ($line[$length - 1] === ']'))
 181                  {
 182                      $section       = substr($line, 1, $length - 2);
 183                      $obj->$section = new \stdClass;
 184  
 185                      continue;
 186                  }
 187              }
 188              elseif ($line[0] === '[')
 189              {
 190                  continue;
 191              }
 192  
 193              // Check that an equal sign exists and is not the first character of the line.
 194              if (!strpos($line, '='))
 195              {
 196                  // Maybe throw exception?
 197                  continue;
 198              }
 199  
 200              // Get the key and value for the line.
 201              list($key, $value) = explode('=', $line, 2);
 202  
 203              // If we have an array item
 204              if (substr($key, -1) === ']' && ($openBrace = strpos($key, '[', 1)) !== false)
 205              {
 206                  if ($options['supportArrayValues'])
 207                  {
 208                      $array    = true;
 209                      $arrayKey = substr($key, $openBrace + 1, -1);
 210  
 211                      // If we have a multi-dimensional array or malformed key
 212                      if (strpos($arrayKey, '[') !== false || strpos($arrayKey, ']') !== false)
 213                      {
 214                          // Maybe throw exception?
 215                          continue;
 216                      }
 217  
 218                      $key = substr($key, 0, $openBrace);
 219                  }
 220                  else
 221                  {
 222                      continue;
 223                  }
 224              }
 225  
 226              // Validate the key.
 227              if (preg_match('/[^A-Z0-9_]/i', $key))
 228              {
 229                  // Maybe throw exception?
 230                  continue;
 231              }
 232  
 233              // If the value is quoted then we assume it is a string.
 234              $length = \strlen($value);
 235  
 236              if ($length && ($value[0] === '"') && ($value[$length - 1] === '"'))
 237              {
 238                  // Strip the quotes and Convert the new line characters.
 239                  $value = stripcslashes(substr($value, 1, $length - 2));
 240                  $value = str_replace('\n', "\n", $value);
 241              }
 242              else
 243              {
 244                  // If the value is not quoted, we assume it is not a string.
 245  
 246                  // If the value is 'false' assume boolean false.
 247                  if ($value === 'false')
 248                  {
 249                      $value = false;
 250                  }
 251                  elseif ($value === 'true')
 252                  {
 253                      // If the value is 'true' assume boolean true.
 254                      $value = true;
 255                  }
 256                  elseif ($options['parseBooleanWords'] && \in_array(strtolower($value), ['yes', 'no'], true))
 257                  {
 258                      // If the value is 'yes' or 'no' and option is enabled assume appropriate boolean
 259                      $value = (strtolower($value) === 'yes');
 260                  }
 261                  elseif (is_numeric($value))
 262                  {
 263                      // If the value is numeric than it is either a float or int.
 264                      // If there is a period then we assume a float.
 265                      if (strpos($value, '.') !== false)
 266                      {
 267                          $value = (float) $value;
 268                      }
 269                      else
 270                      {
 271                          $value = (int) $value;
 272                      }
 273                  }
 274              }
 275  
 276              // If a section is set add the key/value to the section, otherwise top level.
 277              if ($section)
 278              {
 279                  if ($array)
 280                  {
 281                      if (!isset($obj->$section->$key))
 282                      {
 283                          $obj->$section->$key = [];
 284                      }
 285  
 286                      if (!empty($arrayKey))
 287                      {
 288                          $obj->$section->{$key}[$arrayKey] = $value;
 289                      }
 290                      else
 291                      {
 292                          $obj->$section->{$key}[] = $value;
 293                      }
 294                  }
 295                  else
 296                  {
 297                      $obj->$section->$key = $value;
 298                  }
 299              }
 300              else
 301              {
 302                  if ($array)
 303                  {
 304                      if (!isset($obj->$key))
 305                      {
 306                          $obj->$key = [];
 307                      }
 308  
 309                      if (!empty($arrayKey))
 310                      {
 311                          $obj->{$key}[$arrayKey] = $value;
 312                      }
 313                      else
 314                      {
 315                          $obj->{$key}[] = $value;
 316                      }
 317                  }
 318                  else
 319                  {
 320                      $obj->$key = $value;
 321                  }
 322              }
 323  
 324              $array = false;
 325          }
 326  
 327          // Cache the string to save cpu cycles -- thus the world :)
 328          static::$cache[$hash] = clone $obj;
 329  
 330          return $obj;
 331      }
 332  
 333      /**
 334       * Method to get a value in an INI format.
 335       *
 336       * @param   mixed  $value  The value to convert to INI format.
 337       *
 338       * @return  string  The value in INI format.
 339       *
 340       * @since   1.0
 341       */
 342  	protected function getValueAsIni($value)
 343      {
 344          $string = '';
 345  
 346          switch (\gettype($value))
 347          {
 348              case 'integer':
 349              case 'double':
 350                  $string = $value;
 351  
 352                  break;
 353  
 354              case 'boolean':
 355                  $string = $value ? 'true' : 'false';
 356  
 357                  break;
 358  
 359              case 'string':
 360                  // Sanitize any CRLF characters..
 361                  $string = '"' . str_replace(["\r\n", "\n"], '\\n', $value) . '"';
 362  
 363                  break;
 364          }
 365  
 366          return $string;
 367      }
 368  }


Generated: Wed Sep 7 05:41:13 2022 Chilli.vc Blog - For Webmaster,Blog-Writer,System Admin and Domainer