[ Index ]

PHP Cross Reference of Joomla 4.2.2 documentation

title

Body

[close]

/libraries/vendor/laminas/laminas-diactoros/src/ -> AbstractSerializer.php (source)

   1  <?php
   2  
   3  /**
   4   * @see       https://github.com/laminas/laminas-diactoros for the canonical source repository
   5   * @copyright https://github.com/laminas/laminas-diactoros/blob/master/COPYRIGHT.md
   6   * @license   https://github.com/laminas/laminas-diactoros/blob/master/LICENSE.md New BSD License
   7   */
   8  
   9  declare(strict_types=1);
  10  
  11  namespace Laminas\Diactoros;
  12  
  13  use Psr\Http\Message\StreamInterface;
  14  
  15  use function array_pop;
  16  use function implode;
  17  use function ltrim;
  18  use function preg_match;
  19  use function sprintf;
  20  use function str_replace;
  21  use function ucwords;
  22  
  23  /**
  24   * Provides base functionality for request and response de/serialization
  25   * strategies, including functionality for retrieving a line at a time from
  26   * the message, splitting headers from the body, and serializing headers.
  27   */
  28  abstract class AbstractSerializer
  29  {
  30      const CR  = "\r";
  31      const EOL = "\r\n";
  32      const LF  = "\n";
  33  
  34      /**
  35       * Retrieve a single line from the stream.
  36       *
  37       * Retrieves a line from the stream; a line is defined as a sequence of
  38       * characters ending in a CRLF sequence.
  39       *
  40       * @throws Exception\DeserializationException if the sequence contains a CR
  41       *     or LF in isolation, or ends in a CR.
  42       */
  43      protected static function getLine(StreamInterface $stream) : string
  44      {
  45          $line    = '';
  46          $crFound = false;
  47          while (! $stream->eof()) {
  48              $char = $stream->read(1);
  49  
  50              if ($crFound && $char === self::LF) {
  51                  $crFound = false;
  52                  break;
  53              }
  54  
  55              // CR NOT followed by LF
  56              if ($crFound && $char !== self::LF) {
  57                  throw Exception\DeserializationException::forUnexpectedCarriageReturn();
  58              }
  59  
  60              // LF in isolation
  61              if (! $crFound && $char === self::LF) {
  62                  throw Exception\DeserializationException::forUnexpectedLineFeed();
  63              }
  64  
  65              // CR found; do not append
  66              if ($char === self::CR) {
  67                  $crFound = true;
  68                  continue;
  69              }
  70  
  71              // Any other character: append
  72              $line .= $char;
  73          }
  74  
  75          // CR found at end of stream
  76          if ($crFound) {
  77              throw Exception\DeserializationException::forUnexpectedEndOfHeaders();
  78          }
  79  
  80          return $line;
  81      }
  82  
  83      /**
  84       * Split the stream into headers and body content.
  85       *
  86       * Returns an array containing two elements
  87       *
  88       * - The first is an array of headers
  89       * - The second is a StreamInterface containing the body content
  90       *
  91       * @throws Exception\DeserializationException For invalid headers.
  92       */
  93      protected static function splitStream(StreamInterface $stream) : array
  94      {
  95          $headers       = [];
  96          $currentHeader = false;
  97  
  98          while ($line = self::getLine($stream)) {
  99              if (preg_match(';^(?P<name>[!#$%&\'*+.^_`\|~0-9a-zA-Z-]+):(?P<value>.*)$;', $line, $matches)) {
 100                  $currentHeader = $matches['name'];
 101                  if (! isset($headers[$currentHeader])) {
 102                      $headers[$currentHeader] = [];
 103                  }
 104                  $headers[$currentHeader][] = ltrim($matches['value']);
 105                  continue;
 106              }
 107  
 108              if (! $currentHeader) {
 109                  throw Exception\DeserializationException::forInvalidHeader();
 110              }
 111  
 112              if (! preg_match('#^[ \t]#', $line)) {
 113                  throw Exception\DeserializationException::forInvalidHeaderContinuation();
 114              }
 115  
 116              // Append continuation to last header value found
 117              $value = array_pop($headers[$currentHeader]);
 118              $headers[$currentHeader][] = $value . ltrim($line);
 119          }
 120  
 121          // use RelativeStream to avoid copying initial stream into memory
 122          return [$headers, new RelativeStream($stream, $stream->tell())];
 123      }
 124  
 125      /**
 126       * Serialize headers to string values.
 127       */
 128      protected static function serializeHeaders(array $headers) : string
 129      {
 130          $lines = [];
 131          foreach ($headers as $header => $values) {
 132              $normalized = self::filterHeader($header);
 133              foreach ($values as $value) {
 134                  $lines[] = sprintf('%s: %s', $normalized, $value);
 135              }
 136          }
 137  
 138          return implode("\r\n", $lines);
 139      }
 140  
 141      /**
 142       * Filter a header name to wordcase
 143       */
 144      protected static function filterHeader($header) : string
 145      {
 146          $filtered = str_replace('-', ' ', $header);
 147          $filtered = ucwords($filtered);
 148          return str_replace(' ', '-', $filtered);
 149      }
 150  }


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