/** * {@inheritdoc} */ public function check(\Twig_TokenStream $tokens) { $this->reset(); while (!$tokens->isEOF()) { $token = $tokens->getCurrent(); if ($token->getType() === \Twig_Token::NAME_TYPE && preg_match('/[A-Z]/', $token->getValue())) { if ($tokens->look(Lexer::PREVIOUS_TOKEN)->getType() === Token::WHITESPACE_TYPE && $tokens->look(-2)->getValue() === 'set') { $this->addViolation($tokens->getFilename(), $token->getLine(), $token->getColumn(), sprintf('The "%s" variable should be in lower case (use _ as a separator).', $token->getValue())); } } $tokens->next(); } return $this->violations; }
public function testRewind() { $stream = new Twig_TokenStream(self::$tokens, '', false); $this->assertEquals(2, $stream->look()->getValue(), '->look() returns the next token'); $this->assertEquals(3, $stream->look()->getValue(), '->look() can be called several times to look more than one upcoming token'); $this->assertEquals(4, $stream->look()->getValue(), '->look() can be called several times to look more than one upcoming token'); $this->assertEquals(5, $stream->look()->getValue(), '->look() can be called several times to look more than one upcoming token'); $stream->rewind(); $repr = array(); while (!$stream->isEOF()) { $token = $stream->next(false); $repr[] = $token->getValue(); } $this->assertEquals('1, 2, 3, 4, 5, 6, 7', implode(', ', $repr), '->rewind() pushes all pushed tokens to the token array'); }
/** * @param \Twig_TokenStream $tokens * * @return \Twig_Token */ protected function seekTernaryElse(\Twig_TokenStream $tokens) { $i = 1; $depth = 0; $found = false; $token = null; while ($depth || !$found) { $token = $tokens->look($i); if ($token->getType() === \Twig_Token::VAR_END_TYPE || $token->getType() === \Twig_Token::INTERPOLATION_END_TYPE) { return; } // End of hash value means end of short ternary (eg. "foo ? bar" syntax) if ($token->getType() === \Twig_Token::PUNCTUATION_TYPE && $token->getValue() === ',') { return; } if ($token->getType() === \Twig_Token::PUNCTUATION_TYPE && in_array($token->getValue(), ['(', '[', '{'])) { $depth++; } if ($depth && $token->getType() === \Twig_Token::PUNCTUATION_TYPE && in_array($token->getValue(), [')', ']', '}'])) { $depth--; } $found = $token->getType() === \Twig_Token::PUNCTUATION_TYPE && $token->getValue() === ':'; $i++; } return $token; }
/** * @param \Twig_TokenStream $tokens * @param integer $position * @param message $target * @param boolean $acceptNewLines */ protected function assertSpacing(\Twig_TokenStream $tokens, $position, $spacing, $acceptNewLines = true) { $current = $tokens->getCurrent(); $token = $tokens->look($position); $orientation = round($position / abs($position)); $positionName = $orientation > 0 ? 'after' : 'before'; if ($this->whitelist && !$this->whitelist->pass($tokens, $orientation)) { return; } if ($acceptNewLines && $token->getType() == Token::NEWLINE_TYPE) { return; } // special case of no spaces allowed. if ($spacing === 0) { if ($token->getType() === Token::WHITESPACE_TYPE) { $this->addViolation($tokens->getFilename(), $current->getLine(), $current->getColumn(), sprintf('There should be no space %s "%s".', $positionName, $current->getValue())); } if ($token->getType() === Token::NEWLINE_TYPE) { $this->addViolation($tokens->getFilename(), $current->getLine(), $current->getColumn(), sprintf('There should be no new line %s "%s".', $positionName, $current->getValue())); } return; } if ($token->getType() !== Token::WHITESPACE_TYPE || strlen($token->getValue()) < $spacing) { $this->addViolation($tokens->getFilename(), $current->getLine(), $current->getColumn(), sprintf('There should be %d space(s) %s "%s".', $spacing, $positionName, $current->getValue())); } if ($token->getType() === Token::WHITESPACE_TYPE && strlen($token->getValue()) > $spacing) { $this->addViolation($tokens->getFilename(), $current->getLine(), $current->getColumn(), sprintf('More than %d space(s) found %s "%s".', $spacing, $positionName, $current->getValue())); } }
/** * {@inheritdoc} */ public function check(\Twig_TokenStream $tokens) { $this->violations = []; $arrayDepth = 0; $skip = false; while (!$tokens->isEOF()) { $token = $tokens->getCurrent(); if ($token->getType() === \Twig_Token::PUNCTUATION_TYPE && $token->getValue() === '(') { $skip = true; // Ignore function arguments or embedded expressions (eg. [ func(1, 2) ] ) // This prevents this rule from having influence on arguments spacing. } if ($token->getType() === \Twig_Token::PUNCTUATION_TYPE && $token->getValue() === '?') { $skip = true; } if ($token->getValue() === '[' && $token->getType() === \Twig_Token::PUNCTUATION_TYPE) { if ($tokens->look(-1)->getType() === \Twig_Token::NAME_TYPE) { break; // This is not an array declaration, but an array access ( eg. : foo[1] ) } $arrayDepth++; $skip = false; // We entered a new array or hash, from now on do not skip anything. } if ($token->getValue() === ']' && $token->getType() === \Twig_Token::PUNCTUATION_TYPE) { $arrayDepth--; } if (!$skip && $arrayDepth > 0 && $token->getType() === \Twig_Token::PUNCTUATION_TYPE && $token->getValue() === ',') { $this->assertSpacing($tokens, Lexer::NEXT_TOKEN, $this->spaceAfter); $this->assertSpacing($tokens, Lexer::PREVIOUS_TOKEN, $this->spaceBefore, false); } $tokens->next(); } return $this->violations; }
/** * @expectedException Twig_Error_Syntax * @expectedMessage Unexpected end of template */ public function testEndOfTemplateLook() { $stream = new Twig_TokenStream(array(new Twig_Token(Twig_Token::BLOCK_START_TYPE, 1, 1))); while (!$stream->isEOF()) { $stream->look(); $stream->next(); } }
/** * @param \Twig_TokenStream $tokens * @param integer $position * @param message $target */ private function assertSpacing(\Twig_TokenStream $tokens, $position, $target) { $token = $tokens->look($position); if ($token->getType() !== Token::WHITESPACE_TYPE || strlen($token->getValue()) < $this->spacing) { $this->addViolation($tokens->getFilename(), $token->getLine(), $token->getColumn(), sprintf('There should be %d space(s) %s.', $this->spacing, $target)); } if ($token->getType() === Token::WHITESPACE_TYPE && strlen($token->getValue()) > $this->spacing) { $this->addViolation($tokens->getFilename(), $token->getLine(), $token->getColumn(), sprintf('More than %d space(s) found %s.', $this->spacing, $target)); } }
/** * {@inheritdoc} */ public function check(\Twig_TokenStream $tokens) { $this->reset(); $variables = []; while (!$tokens->isEOF()) { $token = $tokens->getCurrent(); if ($token->getType() === \Twig_Token::NAME_TYPE) { if ($tokens->look(Lexer::PREVIOUS_TOKEN)->getType() === Token::WHITESPACE_TYPE && $tokens->look(-2)->getValue() === 'set') { $variables[$token->getValue()] = $token; } else { unset($variables[$token->getValue()]); } } $tokens->next(); } foreach ($variables as $name => $originalToken) { $this->addViolation($tokens->getFilename(), $originalToken->getLine(), $originalToken->getColumn(), sprintf('Unused variable "%s".', $name)); } return $this->violations; }
/** * {@inheritdoc} */ public function pass(\Twig_TokenStream $tokens, $orientation) { foreach ($this->offsets as $offset) { $token = $tokens->look($offset * $orientation); if (in_array($token->getValue(), $this->tokens)) { return true; } if (in_array($token->getType(), $this->tokens)) { return true; } } return false; }
/** * {@inheritdoc} */ public function check(\Twig_TokenStream $tokens) { $this->reset(); while (!$tokens->isEOF()) { $token = $tokens->getCurrent(); if ($token->getType() === Token::NEWLINE_TYPE && $tokens->look(-1)->getType() === Token::WHITESPACE_TYPE || $token->getType() === Token::TEXT_TYPE) { if (preg_match("/[[:blank:]]+\n/", $token->getValue())) { $this->addViolation($tokens->getFilename(), $token->getLine(), $token->getColumn(), 'A line should not end with blank space(s).'); } } $tokens->next(); } return $this->violations; }
/** * @param \Twig_TokenStream $tokens * @param integer $skip * * @return null|Token */ protected function getPreviousSignicantToken(\Twig_TokenStream $tokens, $skip = 0) { $i = 1; $token = null; while ($token = $tokens->look(-$i)) { if (!in_array($token->getType(), [Token::WHITESPACE_TYPE, Token::NEWLINE_TYPE])) { if ($skip === 0) { return $token; } $skip--; } $i++; } return null; }
/** * {@inheritdoc} */ public function check(\Twig_TokenStream $tokens) { $this->violations = []; while (!$tokens->isEOF()) { $token = $tokens->getCurrent(); if ($token->getType() === \Twig_Token::OPERATOR_TYPE && in_array($token->getValue(), $this->operators)) { // allows unary operators to be next to an opening parenthesis. if (!($this->isUnary($token->getValue()) && $tokens->look(-1)->getValue() == '(')) { $this->assertSpacing($tokens, Lexer::PREVIOUS_TOKEN, $this->spacing); } $this->assertSpacing($tokens, Lexer::NEXT_TOKEN, $this->spacing); } $tokens->next(); } return $this->violations; }
/** * {@inheritdoc} */ public function check(\Twig_TokenStream $tokens) { $this->violations = []; $sliceOpened = false; while (!$tokens->isEOF()) { $token = $tokens->getCurrent(); if ($token->getValue() === '[' && $tokens->look(-1)->getType() === \Twig_Token::NAME_TYPE) { $sliceOpened = true; } if ($sliceOpened > 0 && $token->getValue() === ':') { $this->assertSpacing($tokens, Lexer::NEXT_TOKEN, $this->spaces); $this->assertSpacing($tokens, Lexer::PREVIOUS_TOKEN, $this->spaces, false); } if ($token->getValue() === ']') { $sliceOpened = false; } $tokens->next(); } return $this->violations; }
$repr = array(); while (!$stream->isEOF()) { $token = $stream->next(); $repr[] = $token->getValue(); } $t->is(implode(', ', $repr), '1, 2, 3, 4, 5, 6, 7', '->look() pushes the token to the stack'); $stream = new Twig_TokenStream($tokens, '', false); $t->is($stream->look()->getValue(), 2, '->look() returns the next token'); $t->is($stream->look()->getValue(), 3, '->look() can be called several times to look more than one upcoming token'); $t->is($stream->look()->getValue(), 4, '->look() can be called several times to look more than one upcoming token'); $t->is($stream->look()->getValue(), 5, '->look() can be called several times to look more than one upcoming token'); $repr = array(); while (!$stream->isEOF()) { $token = $stream->next(); $repr[] = $token->getValue(); } $t->is(implode(', ', $repr), '1, 2, 3, 4, 5, 6, 7', '->look() pushes the token to the stack'); // ->rewind() $t->diag('->rewind()'); $stream = new Twig_TokenStream($tokens, '', false); $t->is($stream->look()->getValue(), 2, '->look() returns the next token'); $t->is($stream->look()->getValue(), 3, '->look() can be called several times to look more than one upcoming token'); $t->is($stream->look()->getValue(), 4, '->look() can be called several times to look more than one upcoming token'); $t->is($stream->look()->getValue(), 5, '->look() can be called several times to look more than one upcoming token'); $stream->rewind(); $repr = array(); while (!$stream->isEOF()) { $token = $stream->next(false); $repr[] = $token->getValue(); } $t->is(implode(', ', $repr), '1, 2, 3, 4, 5, 6, 7', '->rewind() pushes all pushed tokens to the token array');