ILIAS  release_5-3 Revision v5.3.23-19-g915713cf615
Symfony\Component\Yaml\Parser Class Reference

Parser parses YAML strings to convert them to PHP arrays. More...

+ Collaboration diagram for Symfony\Component\Yaml\Parser:

Public Member Functions

 __construct ($offset=0, $totalNumberOfLines=null, array $skippedLineNumbers=array())
 Constructor. More...
 
 parse ($value, $flags=0)
 Parses a YAML string to a PHP value. More...
 

Data Fields

const TAG_PATTERN = '((?P<tag>![\w!.\/:-]+) +)?'
 
const BLOCK_SCALAR_HEADER_PATTERN = '(?P<separator>\||>)(?P<modifiers>\+|\-|\d+|\+\d+|\-\d+|\d+\+|\d+\-)?(?P<comments> +#.*)?'
 

Private Member Functions

 parseBlock ($offset, $yaml, $flags)
 
 getRealCurrentLineNb ()
 Returns the current line number (takes the offset into account). More...
 
 getCurrentLineIndentation ()
 Returns the current line indentation. More...
 
 getNextEmbedBlock ($indentation=null, $inSequence=false)
 Returns the next embed block of YAML. More...
 
 moveToNextLine ()
 Moves the parser to the next line. More...
 
 moveToPreviousLine ()
 Moves the parser to the previous line. More...
 
 parseValue ($value, $flags, $context)
 Parses a YAML value. More...
 
 parseBlockScalar ($style, $chomping='', $indentation=0)
 Parses a block scalar. More...
 
 isNextLineIndented ()
 Returns true if the next line is indented. More...
 
 isCurrentLineEmpty ()
 Returns true if the current line is blank or if it is a comment line. More...
 
 isCurrentLineBlank ()
 Returns true if the current line is blank. More...
 
 isCurrentLineComment ()
 Returns true if the current line is a comment line. More...
 
 isCurrentLineLastLineInDocument ()
 
 cleanup ($value)
 Cleanups a YAML string to be parsed. More...
 
 isNextLineUnIndentedCollection ()
 Returns true if the next line starts unindented collection. More...
 
 isStringUnIndentedCollectionItem ()
 Returns true if the string is un-indented collection item. More...
 
 isBlockScalarHeader ()
 Tests whether or not the current line is the header of a block scalar. More...
 

Private Attributes

 $offset = 0
 
 $totalNumberOfLines
 
 $lines = array()
 
 $currentLineNb = -1
 
 $currentLine = ''
 
 $refs = array()
 
 $skippedLineNumbers = array()
 
 $locallySkippedLineNumbers = array()
 

Detailed Description

Parser parses YAML strings to convert them to PHP arrays.

Author
Fabien Potencier fabie.nosp@m.n@sy.nosp@m.mfony.nosp@m..com

Definition at line 21 of file Parser.php.

Constructor & Destructor Documentation

◆ __construct()

Symfony\Component\Yaml\Parser::__construct (   $offset = 0,
  $totalNumberOfLines = null,
array  $skippedLineNumbers = array() 
)

Constructor.

Parameters
int$offsetThe offset of YAML document (used for line numbers in error messages)
int | null$totalNumberOfLinesThe overall number of lines being parsed
int[]$skippedLineNumbersNumber of comment lines that have been skipped by the parser

Definition at line 42 of file Parser.php.

43 {
44 $this->offset = $offset;
45 $this->totalNumberOfLines = $totalNumberOfLines;
46 $this->skippedLineNumbers = $skippedLineNumbers;
47 }

References Symfony\Component\Yaml\Parser\$offset, Symfony\Component\Yaml\Parser\$skippedLineNumbers, and Symfony\Component\Yaml\Parser\$totalNumberOfLines.

Member Function Documentation

◆ cleanup()

Symfony\Component\Yaml\Parser::cleanup (   $value)
private

Cleanups a YAML string to be parsed.

Parameters
string$valueThe input YAML string
Returns
string A cleaned up YAML string

Definition at line 774 of file Parser.php.

775 {
776 $value = str_replace(array("\r\n", "\r"), "\n", $value);
777
778 // strip YAML header
779 $count = 0;
780 $value = preg_replace('#^\%YAML[: ][\d\.]+.*\n#u', '', $value, -1, $count);
781 $this->offset += $count;
782
783 // remove leading comments
784 $trimmedValue = preg_replace('#^(\#.*?\n)+#s', '', $value, -1, $count);
785 if ($count == 1) {
786 // items have been removed, update the offset
787 $this->offset += substr_count($value, "\n") - substr_count($trimmedValue, "\n");
788 $value = $trimmedValue;
789 }
790
791 // remove start of the document marker (---)
792 $trimmedValue = preg_replace('#^\-\-\-.*?\n#s', '', $value, -1, $count);
793 if ($count == 1) {
794 // items have been removed, update the offset
795 $this->offset += substr_count($value, "\n") - substr_count($trimmedValue, "\n");
796 $value = $trimmedValue;
797
798 // remove end of the document marker (...)
799 $value = preg_replace('#\.\.\.\s*$#', '', $value);
800 }
801
802 return $value;
803 }

Referenced by Symfony\Component\Yaml\Parser\parse().

+ Here is the caller graph for this function:

◆ getCurrentLineIndentation()

Symfony\Component\Yaml\Parser::getCurrentLineIndentation ( )
private

Returns the current line indentation.

Returns
int The current line indentation

Definition at line 383 of file Parser.php.

384 {
385 return strlen($this->currentLine) - strlen(ltrim($this->currentLine, ' '));
386 }

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), Symfony\Component\Yaml\Parser\isNextLineIndented(), Symfony\Component\Yaml\Parser\isNextLineUnIndentedCollection(), and Symfony\Component\Yaml\Parser\parse().

+ Here is the caller graph for this function:

◆ getNextEmbedBlock()

Symfony\Component\Yaml\Parser::getNextEmbedBlock (   $indentation = null,
  $inSequence = false 
)
private

Returns the next embed block of YAML.

Parameters
int$indentationThe indent level at which the block is to be read, or null for default
bool$inSequenceTrue if the enclosing data structure is a sequence
Returns
string A YAML string
Exceptions
ParseExceptionWhen indentation problem are detected

Definition at line 398 of file Parser.php.

399 {
400 $oldLineIndentation = $this->getCurrentLineIndentation();
401 $blockScalarIndentations = array();
402
403 if ($this->isBlockScalarHeader()) {
404 $blockScalarIndentations[] = $this->getCurrentLineIndentation();
405 }
406
407 if (!$this->moveToNextLine()) {
408 return;
409 }
410
411 if (null === $indentation) {
412 $newIndent = $this->getCurrentLineIndentation();
413
414 $unindentedEmbedBlock = $this->isStringUnIndentedCollectionItem();
415
416 if (!$this->isCurrentLineEmpty() && 0 === $newIndent && !$unindentedEmbedBlock) {
417 throw new ParseException('Indentation problem.', $this->getRealCurrentLineNb() + 1, $this->currentLine);
418 }
419 } else {
420 $newIndent = $indentation;
421 }
422
423 $data = array();
424 if ($this->getCurrentLineIndentation() >= $newIndent) {
425 $data[] = substr($this->currentLine, $newIndent);
426 } else {
427 $this->moveToPreviousLine();
428
429 return;
430 }
431
432 if ($inSequence && $oldLineIndentation === $newIndent && isset($data[0][0]) && '-' === $data[0][0]) {
433 // the previous line contained a dash but no item content, this line is a sequence item with the same indentation
434 // and therefore no nested list or mapping
435 $this->moveToPreviousLine();
436
437 return;
438 }
439
440 $isItUnindentedCollection = $this->isStringUnIndentedCollectionItem();
441
442 if (empty($blockScalarIndentations) && $this->isBlockScalarHeader()) {
443 $blockScalarIndentations[] = $this->getCurrentLineIndentation();
444 }
445
446 $previousLineIndentation = $this->getCurrentLineIndentation();
447
448 while ($this->moveToNextLine()) {
449 $indent = $this->getCurrentLineIndentation();
450
451 // terminate all block scalars that are more indented than the current line
452 if (!empty($blockScalarIndentations) && $indent < $previousLineIndentation && trim($this->currentLine) !== '') {
453 foreach ($blockScalarIndentations as $key => $blockScalarIndentation) {
454 if ($blockScalarIndentation >= $this->getCurrentLineIndentation()) {
455 unset($blockScalarIndentations[$key]);
456 }
457 }
458 }
459
460 if (empty($blockScalarIndentations) && !$this->isCurrentLineComment() && $this->isBlockScalarHeader()) {
461 $blockScalarIndentations[] = $this->getCurrentLineIndentation();
462 }
463
464 $previousLineIndentation = $indent;
465
466 if ($isItUnindentedCollection && !$this->isStringUnIndentedCollectionItem() && $newIndent === $indent) {
467 $this->moveToPreviousLine();
468 break;
469 }
470
471 if ($this->isCurrentLineBlank()) {
472 $data[] = substr($this->currentLine, $newIndent);
473 continue;
474 }
475
476 // we ignore "comment" lines only when we are not inside a scalar block
477 if (empty($blockScalarIndentations) && $this->isCurrentLineComment()) {
478 // remember ignored comment lines (they are used later in nested
479 // parser calls to determine real line numbers)
480 //
481 // CAUTION: beware to not populate the global property here as it
482 // will otherwise influence the getRealCurrentLineNb() call here
483 // for consecutive comment lines and subsequent embedded blocks
484 $this->locallySkippedLineNumbers[] = $this->getRealCurrentLineNb();
485
486 continue;
487 }
488
489 if ($indent >= $newIndent) {
490 $data[] = substr($this->currentLine, $newIndent);
491 } elseif (0 == $indent) {
492 $this->moveToPreviousLine();
493
494 break;
495 } else {
496 throw new ParseException('Indentation problem.', $this->getRealCurrentLineNb() + 1, $this->currentLine);
497 }
498 }
499
500 return implode("\n", $data);
501 }
getCurrentLineIndentation()
Returns the current line indentation.
Definition: Parser.php:383
isCurrentLineEmpty()
Returns true if the current line is blank or if it is a comment line.
Definition: Parser.php:734
isCurrentLineComment()
Returns true if the current line is a comment line.
Definition: Parser.php:754
isStringUnIndentedCollectionItem()
Returns true if the string is un-indented collection item.
Definition: Parser.php:842
getRealCurrentLineNb()
Returns the current line number (takes the offset into account).
Definition: Parser.php:363
isCurrentLineBlank()
Returns true if the current line is blank.
Definition: Parser.php:744
moveToNextLine()
Moves the parser to the next line.
Definition: Parser.php:508
moveToPreviousLine()
Moves the parser to the previous line.
Definition: Parser.php:524
isBlockScalarHeader()
Tests whether or not the current line is the header of a block scalar.
Definition: Parser.php:852
$key
Definition: croninfo.php:18

References $data, $key, Symfony\Component\Yaml\Parser\getCurrentLineIndentation(), Symfony\Component\Yaml\Parser\getRealCurrentLineNb(), Symfony\Component\Yaml\Parser\isBlockScalarHeader(), Symfony\Component\Yaml\Parser\isCurrentLineBlank(), Symfony\Component\Yaml\Parser\isCurrentLineComment(), Symfony\Component\Yaml\Parser\isCurrentLineEmpty(), Symfony\Component\Yaml\Parser\isStringUnIndentedCollectionItem(), Symfony\Component\Yaml\Parser\moveToNextLine(), and Symfony\Component\Yaml\Parser\moveToPreviousLine().

Referenced by Symfony\Component\Yaml\Parser\parse().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ getRealCurrentLineNb()

Symfony\Component\Yaml\Parser::getRealCurrentLineNb ( )
private

Returns the current line number (takes the offset into account).

Returns
int The current line number

Definition at line 363 of file Parser.php.

364 {
365 $realCurrentLineNumber = $this->currentLineNb + $this->offset;
366
367 foreach ($this->skippedLineNumbers as $skippedLineNumber) {
368 if ($skippedLineNumber > $realCurrentLineNumber) {
369 break;
370 }
371
372 ++$realCurrentLineNumber;
373 }
374
375 return $realCurrentLineNumber;
376 }

References Symfony\Component\Yaml\Parser\$offset.

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), Symfony\Component\Yaml\Parser\parse(), and Symfony\Component\Yaml\Parser\parseValue().

+ Here is the caller graph for this function:

◆ isBlockScalarHeader()

Symfony\Component\Yaml\Parser::isBlockScalarHeader ( )
private

Tests whether or not the current line is the header of a block scalar.

Returns
bool

Definition at line 852 of file Parser.php.

853 {
854 return (bool) preg_match('~'.self::BLOCK_SCALAR_HEADER_PATTERN.'$~', $this->currentLine);
855 }

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock().

+ Here is the caller graph for this function:

◆ isCurrentLineBlank()

Symfony\Component\Yaml\Parser::isCurrentLineBlank ( )
private

Returns true if the current line is blank.

Returns
bool Returns true if the current line is blank, false otherwise

Definition at line 744 of file Parser.php.

745 {
746 return '' == trim($this->currentLine, ' ');
747 }

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), Symfony\Component\Yaml\Parser\isCurrentLineEmpty(), and Symfony\Component\Yaml\Parser\parseBlockScalar().

+ Here is the caller graph for this function:

◆ isCurrentLineComment()

Symfony\Component\Yaml\Parser::isCurrentLineComment ( )
private

Returns true if the current line is a comment line.

Returns
bool Returns true if the current line is a comment line, false otherwise

Definition at line 754 of file Parser.php.

755 {
756 //checking explicitly the first char of the trim is faster than loops or strpos
757 $ltrimmedLine = ltrim($this->currentLine, ' ');
758
759 return '' !== $ltrimmedLine && $ltrimmedLine[0] === '#';
760 }

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), and Symfony\Component\Yaml\Parser\isCurrentLineEmpty().

+ Here is the caller graph for this function:

◆ isCurrentLineEmpty()

Symfony\Component\Yaml\Parser::isCurrentLineEmpty ( )
private

Returns true if the current line is blank or if it is a comment line.

Returns
bool Returns true if the current line is empty or if it is a comment line, false otherwise

Definition at line 734 of file Parser.php.

735 {
736 return $this->isCurrentLineBlank() || $this->isCurrentLineComment();
737 }

References Symfony\Component\Yaml\Parser\isCurrentLineBlank(), and Symfony\Component\Yaml\Parser\isCurrentLineComment().

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), Symfony\Component\Yaml\Parser\isNextLineIndented(), Symfony\Component\Yaml\Parser\isNextLineUnIndentedCollection(), and Symfony\Component\Yaml\Parser\parse().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ isCurrentLineLastLineInDocument()

Symfony\Component\Yaml\Parser::isCurrentLineLastLineInDocument ( )
private

Definition at line 762 of file Parser.php.

763 {
764 return ($this->offset + $this->currentLineNb) >= ($this->totalNumberOfLines - 1);
765 }

Referenced by Symfony\Component\Yaml\Parser\parseBlockScalar().

+ Here is the caller graph for this function:

◆ isNextLineIndented()

Symfony\Component\Yaml\Parser::isNextLineIndented ( )
private

Returns true if the next line is indented.

Returns
bool Returns true if the next line is indented, false otherwise

Definition at line 706 of file Parser.php.

707 {
708 $currentIndentation = $this->getCurrentLineIndentation();
709 $EOF = !$this->moveToNextLine();
710
711 while (!$EOF && $this->isCurrentLineEmpty()) {
712 $EOF = !$this->moveToNextLine();
713 }
714
715 if ($EOF) {
716 return false;
717 }
718
719 $ret = false;
720 if ($this->getCurrentLineIndentation() > $currentIndentation) {
721 $ret = true;
722 }
723
724 $this->moveToPreviousLine();
725
726 return $ret;
727 }
$ret
Definition: parser.php:6

References $ret, Symfony\Component\Yaml\Parser\getCurrentLineIndentation(), Symfony\Component\Yaml\Parser\isCurrentLineEmpty(), Symfony\Component\Yaml\Parser\moveToNextLine(), and Symfony\Component\Yaml\Parser\moveToPreviousLine().

Referenced by Symfony\Component\Yaml\Parser\parse().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ isNextLineUnIndentedCollection()

Symfony\Component\Yaml\Parser::isNextLineUnIndentedCollection ( )
private

Returns true if the next line starts unindented collection.

Returns
bool Returns true if the next line starts unindented collection, false otherwise

Definition at line 810 of file Parser.php.

811 {
812 $currentIndentation = $this->getCurrentLineIndentation();
813 $notEOF = $this->moveToNextLine();
814
815 while ($notEOF && $this->isCurrentLineEmpty()) {
816 $notEOF = $this->moveToNextLine();
817 }
818
819 if (false === $notEOF) {
820 return false;
821 }
822
823 $ret = false;
824 if (
825 $this->getCurrentLineIndentation() == $currentIndentation
826 &&
828 ) {
829 $ret = true;
830 }
831
832 $this->moveToPreviousLine();
833
834 return $ret;
835 }

References $ret, Symfony\Component\Yaml\Parser\getCurrentLineIndentation(), Symfony\Component\Yaml\Parser\isCurrentLineEmpty(), Symfony\Component\Yaml\Parser\isStringUnIndentedCollectionItem(), Symfony\Component\Yaml\Parser\moveToNextLine(), and Symfony\Component\Yaml\Parser\moveToPreviousLine().

Referenced by Symfony\Component\Yaml\Parser\parse().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ isStringUnIndentedCollectionItem()

Symfony\Component\Yaml\Parser::isStringUnIndentedCollectionItem ( )
private

Returns true if the string is un-indented collection item.

Returns
bool Returns true if the string is un-indented collection item, false otherwise

Definition at line 842 of file Parser.php.

843 {
844 return '-' === rtrim($this->currentLine) || 0 === strpos($this->currentLine, '- ');
845 }

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), and Symfony\Component\Yaml\Parser\isNextLineUnIndentedCollection().

+ Here is the caller graph for this function:

◆ moveToNextLine()

Symfony\Component\Yaml\Parser::moveToNextLine ( )
private

Moves the parser to the next line.

Returns
bool

Definition at line 508 of file Parser.php.

509 {
510 if ($this->currentLineNb >= count($this->lines) - 1) {
511 return false;
512 }
513
514 $this->currentLine = $this->lines[++$this->currentLineNb];
515
516 return true;
517 }

References Symfony\Component\Yaml\Parser\$currentLineNb.

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), Symfony\Component\Yaml\Parser\isNextLineIndented(), Symfony\Component\Yaml\Parser\isNextLineUnIndentedCollection(), Symfony\Component\Yaml\Parser\parse(), and Symfony\Component\Yaml\Parser\parseBlockScalar().

+ Here is the caller graph for this function:

◆ moveToPreviousLine()

Symfony\Component\Yaml\Parser::moveToPreviousLine ( )
private

Moves the parser to the previous line.

Returns
bool

Definition at line 524 of file Parser.php.

525 {
526 if ($this->currentLineNb < 1) {
527 return false;
528 }
529
530 $this->currentLine = $this->lines[--$this->currentLineNb];
531
532 return true;
533 }

References Symfony\Component\Yaml\Parser\$currentLineNb.

Referenced by Symfony\Component\Yaml\Parser\getNextEmbedBlock(), Symfony\Component\Yaml\Parser\isNextLineIndented(), Symfony\Component\Yaml\Parser\isNextLineUnIndentedCollection(), and Symfony\Component\Yaml\Parser\parseBlockScalar().

+ Here is the caller graph for this function:

◆ parse()

Symfony\Component\Yaml\Parser::parse (   $value,
  $flags = 0 
)

Parses a YAML string to a PHP value.

Parameters
string$valueA YAML string
int$flagsA bit field of PARSE_* constants to customize the YAML parser behavior
Returns
mixed A PHP value
Exceptions
ParseExceptionIf the YAML is not valid

Definition at line 59 of file Parser.php.

60 {
61 if (is_bool($flags)) {
62 @trigger_error('Passing a boolean flag to toggle exception handling is deprecated since version 3.1 and will be removed in 4.0. Use the Yaml::PARSE_EXCEPTION_ON_INVALID_TYPE flag instead.', E_USER_DEPRECATED);
63
64 if ($flags) {
66 } else {
67 $flags = 0;
68 }
69 }
70
71 if (func_num_args() >= 3) {
72 @trigger_error('Passing a boolean flag to toggle object support is deprecated since version 3.1 and will be removed in 4.0. Use the Yaml::PARSE_OBJECT flag instead.', E_USER_DEPRECATED);
73
74 if (func_get_arg(2)) {
75 $flags |= Yaml::PARSE_OBJECT;
76 }
77 }
78
79 if (func_num_args() >= 4) {
80 @trigger_error('Passing a boolean flag to toggle object for map support is deprecated since version 3.1 and will be removed in 4.0. Use the Yaml::PARSE_OBJECT_FOR_MAP flag instead.', E_USER_DEPRECATED);
81
82 if (func_get_arg(3)) {
84 }
85 }
86
87 if (!preg_match('//u', $value)) {
88 throw new ParseException('The YAML value does not appear to be valid UTF-8.');
89 }
90 $this->currentLineNb = -1;
91 $this->currentLine = '';
92 $value = $this->cleanup($value);
93 $this->lines = explode("\n", $value);
94
95 if (null === $this->totalNumberOfLines) {
96 $this->totalNumberOfLines = count($this->lines);
97 }
98
99 if (2 /* MB_OVERLOAD_STRING */ & (int) ini_get('mbstring.func_overload')) {
100 $mbEncoding = mb_internal_encoding();
101 mb_internal_encoding('UTF-8');
102 }
103
104 $data = array();
105 $context = null;
106 $allowOverwrite = false;
107 while ($this->moveToNextLine()) {
108 if ($this->isCurrentLineEmpty()) {
109 continue;
110 }
111
112 // tab?
113 if ("\t" === $this->currentLine[0]) {
114 throw new ParseException('A YAML file cannot contain tabs as indentation.', $this->getRealCurrentLineNb() + 1, $this->currentLine);
115 }
116
117 $isRef = $mergeNode = false;
118 if (preg_match('#^\-((?P<leadspaces>\s+)(?P<value>.+?))?\s*$#u', $this->currentLine, $values)) {
119 if ($context && 'mapping' == $context) {
120 throw new ParseException('You cannot define a sequence item when in a mapping', $this->getRealCurrentLineNb() + 1, $this->currentLine);
121 }
122 $context = 'sequence';
123
124 if (isset($values['value']) && preg_match('#^&(?P<ref>[^ ]+) *(?P<value>.*)#u', $values['value'], $matches)) {
125 $isRef = $matches['ref'];
126 $values['value'] = $matches['value'];
127 }
128
129 // array
130 if (!isset($values['value']) || '' == trim($values['value'], ' ') || 0 === strpos(ltrim($values['value'], ' '), '#')) {
131 $data[] = $this->parseBlock($this->getRealCurrentLineNb() + 1, $this->getNextEmbedBlock(null, true), $flags);
132 } else {
133 if (isset($values['leadspaces'])
134 && preg_match('#^(?P<key>'.Inline::REGEX_QUOTED_STRING.'|[^ \'"\{\[].*?) *\:(\s+(?P<value>.+?))?\s*$#u', $values['value'], $matches)
135 ) {
136 // this is a compact notation element, add to next block and parse
137 $block = $values['value'];
138 if ($this->isNextLineIndented()) {
139 $block .= "\n".$this->getNextEmbedBlock($this->getCurrentLineIndentation() + strlen($values['leadspaces']) + 1);
140 }
141
142 $data[] = $this->parseBlock($this->getRealCurrentLineNb(), $block, $flags);
143 } else {
144 $data[] = $this->parseValue($values['value'], $flags, $context);
145 }
146 }
147 if ($isRef) {
148 $this->refs[$isRef] = end($data);
149 }
150 } elseif (preg_match('#^(?P<key>'.Inline::REGEX_QUOTED_STRING.'|[^ \'"\[\{].*?) *\:(\s+(?P<value>.+?))?\s*$#u', $this->currentLine, $values) && (false === strpos($values['key'], ' #') || in_array($values['key'][0], array('"', "'")))) {
151 if ($context && 'sequence' == $context) {
152 throw new ParseException('You cannot define a mapping item when in a sequence', $this->currentLineNb + 1, $this->currentLine);
153 }
154 $context = 'mapping';
155
156 // force correct settings
157 Inline::parse(null, $flags, $this->refs);
158 try {
159 $key = Inline::parseScalar($values['key']);
160 } catch (ParseException $e) {
161 $e->setParsedLine($this->getRealCurrentLineNb() + 1);
162 $e->setSnippet($this->currentLine);
163
164 throw $e;
165 }
166
167 // Convert float keys to strings, to avoid being converted to integers by PHP
168 if (is_float($key)) {
169 $key = (string) $key;
170 }
171
172 if ('<<' === $key) {
173 $mergeNode = true;
174 $allowOverwrite = true;
175 if (isset($values['value']) && 0 === strpos($values['value'], '*')) {
176 $refName = substr($values['value'], 1);
177 if (!array_key_exists($refName, $this->refs)) {
178 throw new ParseException(sprintf('Reference "%s" does not exist.', $refName), $this->getRealCurrentLineNb() + 1, $this->currentLine);
179 }
180
181 $refValue = $this->refs[$refName];
182
183 if (!is_array($refValue)) {
184 throw new ParseException('YAML merge keys used with a scalar value instead of an array.', $this->getRealCurrentLineNb() + 1, $this->currentLine);
185 }
186
187 foreach ($refValue as $key => $value) {
188 if (!isset($data[$key])) {
189 $data[$key] = $value;
190 }
191 }
192 } else {
193 if (isset($values['value']) && $values['value'] !== '') {
194 $value = $values['value'];
195 } else {
196 $value = $this->getNextEmbedBlock();
197 }
198 $parsed = $this->parseBlock($this->getRealCurrentLineNb() + 1, $value, $flags);
199
200 if (!is_array($parsed)) {
201 throw new ParseException('YAML merge keys used with a scalar value instead of an array.', $this->getRealCurrentLineNb() + 1, $this->currentLine);
202 }
203
204 if (isset($parsed[0])) {
205 // If the value associated with the merge key is a sequence, then this sequence is expected to contain mapping nodes
206 // and each of these nodes is merged in turn according to its order in the sequence. Keys in mapping nodes earlier
207 // in the sequence override keys specified in later mapping nodes.
208 foreach ($parsed as $parsedItem) {
209 if (!is_array($parsedItem)) {
210 throw new ParseException('Merge items must be arrays.', $this->getRealCurrentLineNb() + 1, $parsedItem);
211 }
212
213 foreach ($parsedItem as $key => $value) {
214 if (!isset($data[$key])) {
215 $data[$key] = $value;
216 }
217 }
218 }
219 } else {
220 // If the value associated with the key is a single mapping node, each of its key/value pairs is inserted into the
221 // current mapping, unless the key already exists in it.
222 foreach ($parsed as $key => $value) {
223 if (!isset($data[$key])) {
224 $data[$key] = $value;
225 }
226 }
227 }
228 }
229 } elseif (isset($values['value']) && preg_match('#^&(?P<ref>[^ ]+) *(?P<value>.*)#u', $values['value'], $matches)) {
230 $isRef = $matches['ref'];
231 $values['value'] = $matches['value'];
232 }
233
234 if ($mergeNode) {
235 // Merge keys
236 } elseif (!isset($values['value']) || '' == trim($values['value'], ' ') || 0 === strpos(ltrim($values['value'], ' '), '#')) {
237 // hash
238 // if next line is less indented or equal, then it means that the current value is null
239 if (!$this->isNextLineIndented() && !$this->isNextLineUnIndentedCollection()) {
240 // Spec: Keys MUST be unique; first one wins.
241 // But overwriting is allowed when a merge node is used in current block.
242 if ($allowOverwrite || !isset($data[$key])) {
243 $data[$key] = null;
244 }
245 } else {
246 $value = $this->parseBlock($this->getRealCurrentLineNb() + 1, $this->getNextEmbedBlock(), $flags);
247 // Spec: Keys MUST be unique; first one wins.
248 // But overwriting is allowed when a merge node is used in current block.
249 if ($allowOverwrite || !isset($data[$key])) {
250 $data[$key] = $value;
251 }
252 }
253 } else {
254 $value = $this->parseValue($values['value'], $flags, $context);
255 // Spec: Keys MUST be unique; first one wins.
256 // But overwriting is allowed when a merge node is used in current block.
257 if ($allowOverwrite || !isset($data[$key])) {
258 $data[$key] = $value;
259 }
260 }
261 if ($isRef) {
262 $this->refs[$isRef] = $data[$key];
263 }
264 } else {
265 // multiple documents are not supported
266 if ('---' === $this->currentLine) {
267 throw new ParseException('Multiple documents are not supported.', $this->currentLineNb + 1, $this->currentLine);
268 }
269
270 // 1-liner optionally followed by newline(s)
271 if (is_string($value) && $this->lines[0] === trim($value)) {
272 try {
273 $value = Inline::parse($this->lines[0], $flags, $this->refs);
274 } catch (ParseException $e) {
275 $e->setParsedLine($this->getRealCurrentLineNb() + 1);
276 $e->setSnippet($this->currentLine);
277
278 throw $e;
279 }
280
281 if (is_array($value)) {
282 $first = reset($value);
283 if (is_string($first) && 0 === strpos($first, '*')) {
284 $data = array();
285 foreach ($value as $alias) {
286 $data[] = $this->refs[substr($alias, 1)];
287 }
288 $value = $data;
289 }
290 }
291
292 if (isset($mbEncoding)) {
293 mb_internal_encoding($mbEncoding);
294 }
295
296 return $value;
297 }
298
299 switch (preg_last_error()) {
300 case PREG_INTERNAL_ERROR:
301 $error = 'Internal PCRE error.';
302 break;
303 case PREG_BACKTRACK_LIMIT_ERROR:
304 $error = 'pcre.backtrack_limit reached.';
305 break;
306 case PREG_RECURSION_LIMIT_ERROR:
307 $error = 'pcre.recursion_limit reached.';
308 break;
309 case PREG_BAD_UTF8_ERROR:
310 $error = 'Malformed UTF-8 data.';
311 break;
312 case PREG_BAD_UTF8_OFFSET_ERROR:
313 $error = 'Offset doesn\'t correspond to the begin of a valid UTF-8 code point.';
314 break;
315 default:
316 $error = 'Unable to parse.';
317 }
318
319 throw new ParseException($error, $this->getRealCurrentLineNb() + 1, $this->currentLine);
320 }
321 }
322
323 if (isset($mbEncoding)) {
324 mb_internal_encoding($mbEncoding);
325 }
326
327 if (Yaml::PARSE_OBJECT_FOR_MAP & $flags && !is_object($data) && 'mapping' === $context) {
328 $object = new \stdClass();
329
330 foreach ($data as $key => $value) {
331 $object->$key = $value;
332 }
333
334 $data = $object;
335 }
336
337 return empty($data) ? null : $data;
338 }
sprintf('%.4f', $callTime)
static parse($value, $flags=0, $references=array())
Converts a YAML string to a PHP array.
Definition: Inline.php:43
static parseScalar($scalar, $flags=0, $delimiters=null, $stringDelimiters=array('"', "'"), &$i = 0, $evaluate = true, $references = array())
Parses a scalar to a YAML string.
Definition: Inline.php:285
isNextLineUnIndentedCollection()
Returns true if the next line starts unindented collection.
Definition: Parser.php:810
parseBlock($offset, $yaml, $flags)
Definition: Parser.php:340
parseValue($value, $flags, $context)
Parses a YAML value.
Definition: Parser.php:546
getNextEmbedBlock($indentation=null, $inSequence=false)
Returns the next embed block of YAML.
Definition: Parser.php:398
isNextLineIndented()
Returns true if the next line is indented.
Definition: Parser.php:706
cleanup($value)
Cleanups a YAML string to be parsed.
Definition: Parser.php:774
const PARSE_EXCEPTION_ON_INVALID_TYPE
Definition: Yaml.php:24
$error
Definition: Error.php:17

References $data, $error, $key, Symfony\Component\Yaml\Parser\cleanup(), Symfony\Component\Yaml\Parser\getCurrentLineIndentation(), Symfony\Component\Yaml\Parser\getNextEmbedBlock(), Symfony\Component\Yaml\Parser\getRealCurrentLineNb(), Symfony\Component\Yaml\Parser\isCurrentLineEmpty(), Symfony\Component\Yaml\Parser\isNextLineIndented(), Symfony\Component\Yaml\Parser\isNextLineUnIndentedCollection(), Symfony\Component\Yaml\Parser\moveToNextLine(), Symfony\Component\Yaml\Inline\parse(), Symfony\Component\Yaml\Yaml\PARSE_EXCEPTION_ON_INVALID_TYPE, Symfony\Component\Yaml\Yaml\PARSE_OBJECT, Symfony\Component\Yaml\Yaml\PARSE_OBJECT_FOR_MAP, Symfony\Component\Yaml\Parser\parseBlock(), Symfony\Component\Yaml\Inline\parseScalar(), Symfony\Component\Yaml\Parser\parseValue(), Symfony\Component\Yaml\Inline\REGEX_QUOTED_STRING, Symfony\Component\Yaml\Exception\ParseException\setParsedLine(), Symfony\Component\Yaml\Exception\ParseException\setSnippet(), and sprintf.

+ Here is the call graph for this function:

◆ parseBlock()

Symfony\Component\Yaml\Parser::parseBlock (   $offset,
  $yaml,
  $flags 
)
private

Definition at line 340 of file Parser.php.

341 {
343
344 foreach ($this->locallySkippedLineNumbers as $lineNumber) {
345 if ($lineNumber < $offset) {
346 continue;
347 }
348
349 $skippedLineNumbers[] = $lineNumber;
350 }
351
353 $parser->refs = &$this->refs;
354
355 return $parser->parse($yaml, $flags);
356 }
$parser
Definition: BPMN2Parser.php:23

References Symfony\Component\Yaml\Parser\$offset, $parser, Symfony\Component\Yaml\Parser\$refs, Symfony\Component\Yaml\Parser\$skippedLineNumbers, and Symfony\Component\Yaml\Parser\$totalNumberOfLines.

Referenced by Symfony\Component\Yaml\Parser\parse().

+ Here is the caller graph for this function:

◆ parseBlockScalar()

Symfony\Component\Yaml\Parser::parseBlockScalar (   $style,
  $chomping = '',
  $indentation = 0 
)
private

Parses a block scalar.

Parameters
string$styleThe style indicator that was used to begin this block scalar (| or >)
string$chompingThe chomping indicator that was used to begin this block scalar (+ or -)
int$indentationThe indentation indicator that was used to begin this block scalar
Returns
string The text value

Definition at line 599 of file Parser.php.

600 {
601 $notEOF = $this->moveToNextLine();
602 if (!$notEOF) {
603 return '';
604 }
605
606 $isCurrentLineBlank = $this->isCurrentLineBlank();
607 $blockLines = array();
608
609 // leading blank lines are consumed before determining indentation
610 while ($notEOF && $isCurrentLineBlank) {
611 // newline only if not EOF
612 if ($notEOF = $this->moveToNextLine()) {
613 $blockLines[] = '';
614 $isCurrentLineBlank = $this->isCurrentLineBlank();
615 }
616 }
617
618 // determine indentation if not specified
619 if (0 === $indentation) {
620 if (preg_match('/^ +/', $this->currentLine, $matches)) {
621 $indentation = strlen($matches[0]);
622 }
623 }
624
625 if ($indentation > 0) {
626 $pattern = sprintf('/^ {%d}(.*)$/', $indentation);
627
628 while (
629 $notEOF && (
630 $isCurrentLineBlank ||
631 preg_match($pattern, $this->currentLine, $matches)
632 )
633 ) {
634 if ($isCurrentLineBlank && strlen($this->currentLine) > $indentation) {
635 $blockLines[] = substr($this->currentLine, $indentation);
636 } elseif ($isCurrentLineBlank) {
637 $blockLines[] = '';
638 } else {
639 $blockLines[] = $matches[1];
640 }
641
642 // newline only if not EOF
643 if ($notEOF = $this->moveToNextLine()) {
644 $isCurrentLineBlank = $this->isCurrentLineBlank();
645 }
646 }
647 } elseif ($notEOF) {
648 $blockLines[] = '';
649 }
650
651 if ($notEOF) {
652 $blockLines[] = '';
653 $this->moveToPreviousLine();
654 } elseif (!$notEOF && !$this->isCurrentLineLastLineInDocument()) {
655 $blockLines[] = '';
656 }
657
658 // folded style
659 if ('>' === $style) {
660 $text = '';
661 $previousLineIndented = false;
662 $previousLineBlank = false;
663
664 for ($i = 0; $i < count($blockLines); ++$i) {
665 if ('' === $blockLines[$i]) {
666 $text .= "\n";
667 $previousLineIndented = false;
668 $previousLineBlank = true;
669 } elseif (' ' === $blockLines[$i][0]) {
670 $text .= "\n".$blockLines[$i];
671 $previousLineIndented = true;
672 $previousLineBlank = false;
673 } elseif ($previousLineIndented) {
674 $text .= "\n".$blockLines[$i];
675 $previousLineIndented = false;
676 $previousLineBlank = false;
677 } elseif ($previousLineBlank || 0 === $i) {
678 $text .= $blockLines[$i];
679 $previousLineIndented = false;
680 $previousLineBlank = false;
681 } else {
682 $text .= ' '.$blockLines[$i];
683 $previousLineIndented = false;
684 $previousLineBlank = false;
685 }
686 }
687 } else {
688 $text = implode("\n", $blockLines);
689 }
690
691 // deal with trailing newlines
692 if ('' === $chomping) {
693 $text = preg_replace('/\n+$/', "\n", $text);
694 } elseif ('-' === $chomping) {
695 $text = preg_replace('/\n+$/', '', $text);
696 }
697
698 return $text;
699 }
$i
Definition: disco.tpl.php:19
$style
Definition: example_012.php:70
$text
Definition: errorreport.php:18

References $i, $style, $text, Symfony\Component\Yaml\Parser\isCurrentLineBlank(), Symfony\Component\Yaml\Parser\isCurrentLineLastLineInDocument(), Symfony\Component\Yaml\Parser\moveToNextLine(), Symfony\Component\Yaml\Parser\moveToPreviousLine(), and sprintf.

Referenced by Symfony\Component\Yaml\Parser\parseValue().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ parseValue()

Symfony\Component\Yaml\Parser::parseValue (   $value,
  $flags,
  $context 
)
private

Parses a YAML value.

Parameters
string$valueA YAML value
int$flagsA bit field of PARSE_* constants to customize the YAML parser behavior
string$contextThe parser context (either sequence or mapping)
Returns
mixed A PHP value
Exceptions
ParseExceptionWhen reference does not exist

Definition at line 546 of file Parser.php.

547 {
548 if (0 === strpos($value, '*')) {
549 if (false !== $pos = strpos($value, '#')) {
550 $value = substr($value, 1, $pos - 2);
551 } else {
552 $value = substr($value, 1);
553 }
554
555 if (!array_key_exists($value, $this->refs)) {
556 throw new ParseException(sprintf('Reference "%s" does not exist.', $value), $this->currentLineNb + 1, $this->currentLine);
557 }
558
559 return $this->refs[$value];
560 }
561
562 if (preg_match('/^'.self::TAG_PATTERN.self::BLOCK_SCALAR_HEADER_PATTERN.'$/', $value, $matches)) {
563 $modifiers = isset($matches['modifiers']) ? $matches['modifiers'] : '';
564
565 $data = $this->parseBlockScalar($matches['separator'], preg_replace('#\d+#', '', $modifiers), (int) abs($modifiers));
566
567 if (isset($matches['tag']) && '!!binary' === $matches['tag']) {
569 }
570
571 return $data;
572 }
573
574 try {
575 $parsedValue = Inline::parse($value, $flags, $this->refs);
576
577 if ('mapping' === $context && is_string($parsedValue) && '"' !== $value[0] && "'" !== $value[0] && '[' !== $value[0] && '{' !== $value[0] && '!' !== $value[0] && false !== strpos($parsedValue, ': ')) {
578 throw new ParseException('A colon cannot be used in an unquoted mapping value.');
579 }
580
581 return $parsedValue;
582 } catch (ParseException $e) {
583 $e->setParsedLine($this->getRealCurrentLineNb() + 1);
584 $e->setSnippet($this->currentLine);
585
586 throw $e;
587 }
588 }
static evaluateBinaryScalar($scalar)
Definition: Inline.php:631
parseBlockScalar($style, $chomping='', $indentation=0)
Parses a block scalar.
Definition: Parser.php:599

References $data, Symfony\Component\Yaml\Inline\evaluateBinaryScalar(), Symfony\Component\Yaml\Parser\getRealCurrentLineNb(), Symfony\Component\Yaml\Inline\parse(), Symfony\Component\Yaml\Parser\parseBlockScalar(), Symfony\Component\Yaml\Exception\ParseException\setParsedLine(), Symfony\Component\Yaml\Exception\ParseException\setSnippet(), and sprintf.

Referenced by Symfony\Component\Yaml\Parser\parse().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

Field Documentation

◆ $currentLine

Symfony\Component\Yaml\Parser::$currentLine = ''
private

Definition at line 30 of file Parser.php.

◆ $currentLineNb

Symfony\Component\Yaml\Parser::$currentLineNb = -1
private

◆ $lines

Symfony\Component\Yaml\Parser::$lines = array()
private

Definition at line 28 of file Parser.php.

◆ $locallySkippedLineNumbers

Symfony\Component\Yaml\Parser::$locallySkippedLineNumbers = array()
private

Definition at line 33 of file Parser.php.

◆ $offset

Symfony\Component\Yaml\Parser::$offset = 0
private

◆ $refs

Symfony\Component\Yaml\Parser::$refs = array()
private

Definition at line 31 of file Parser.php.

Referenced by Symfony\Component\Yaml\Parser\parseBlock().

◆ $skippedLineNumbers

Symfony\Component\Yaml\Parser::$skippedLineNumbers = array()
private

◆ $totalNumberOfLines

Symfony\Component\Yaml\Parser::$totalNumberOfLines
private

◆ BLOCK_SCALAR_HEADER_PATTERN

const Symfony\Component\Yaml\Parser::BLOCK_SCALAR_HEADER_PATTERN = '(?P<separator>\||>)(?P<modifiers>\+|\-|\d+|\+\d+|\-\d+|\d+\+|\d+\-)?(?P<comments> +#.*)?'

Definition at line 24 of file Parser.php.

◆ TAG_PATTERN

const Symfony\Component\Yaml\Parser::TAG_PATTERN = '((?P<tag>![\w!.\/:-]+) +)?'

Definition at line 23 of file Parser.php.


The documentation for this class was generated from the following file: