@@ -215,6 +215,10 @@ class Mustache_Tokenizer
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ($this->state !== self::IN_TEXT) {
|
||||||
|
$this->throwUnclosedTagException();
|
||||||
|
}
|
||||||
|
|
||||||
$this->flushBuffer();
|
$this->flushBuffer();
|
||||||
|
|
||||||
// Restore the user's encoding...
|
// Restore the user's encoding...
|
||||||
@@ -279,6 +283,10 @@ class Mustache_Tokenizer
|
|||||||
$close = '=' . $this->ctag;
|
$close = '=' . $this->ctag;
|
||||||
$closeIndex = strpos($text, $close, $index);
|
$closeIndex = strpos($text, $close, $index);
|
||||||
|
|
||||||
|
if ($closeIndex === false) {
|
||||||
|
$this->throwUnclosedTagException();
|
||||||
|
}
|
||||||
|
|
||||||
$token = array(
|
$token = array(
|
||||||
self::TYPE => self::T_DELIM_CHANGE,
|
self::TYPE => self::T_DELIM_CHANGE,
|
||||||
self::LINE => $this->line,
|
self::LINE => $this->line,
|
||||||
@@ -333,6 +341,10 @@ class Mustache_Tokenizer
|
|||||||
private function addPragma($text, $index)
|
private function addPragma($text, $index)
|
||||||
{
|
{
|
||||||
$end = strpos($text, $this->ctag, $index);
|
$end = strpos($text, $this->ctag, $index);
|
||||||
|
if ($end === false) {
|
||||||
|
$this->throwUnclosedTagException();
|
||||||
|
}
|
||||||
|
|
||||||
$pragma = trim(substr($text, $index + 2, $end - $index - 2));
|
$pragma = trim(substr($text, $index + 2, $end - $index - 2));
|
||||||
|
|
||||||
// Pragmas are hoisted to the front of the template.
|
// Pragmas are hoisted to the front of the template.
|
||||||
@@ -344,4 +356,23 @@ class Mustache_Tokenizer
|
|||||||
|
|
||||||
return $end + $this->ctagLen - 1;
|
return $end + $this->ctagLen - 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private function throwUnclosedTagException()
|
||||||
|
{
|
||||||
|
$name = trim($this->buffer);
|
||||||
|
if ($name !== '') {
|
||||||
|
$msg = sprintf('Unclosed tag: %s on line %d', $name, $this->line);
|
||||||
|
} else {
|
||||||
|
$msg = sprintf('Unclosed tag on line %d', $this->line);
|
||||||
|
}
|
||||||
|
|
||||||
|
throw new Mustache_Exception_SyntaxException($msg, array(
|
||||||
|
self::TYPE => $this->tagType,
|
||||||
|
self::NAME => $name,
|
||||||
|
self::OTAG => $this->otag,
|
||||||
|
self::CTAG => $this->ctag,
|
||||||
|
self::LINE => $this->line,
|
||||||
|
self::INDEX => $this->seenTag - $this->otagLen,
|
||||||
|
));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -351,4 +351,43 @@ class Mustache_Test_TokenizerTest extends PHPUnit_Framework_TestCase
|
|||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @dataProvider getUnclosedTags
|
||||||
|
* @expectedException Mustache_Exception_SyntaxException
|
||||||
|
*/
|
||||||
|
public function testUnclosedTagsThrowExceptions($text)
|
||||||
|
{
|
||||||
|
$tokenizer = new Mustache_Tokenizer();
|
||||||
|
$tokenizer->scan($text, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getUnclosedTags()
|
||||||
|
{
|
||||||
|
return array(
|
||||||
|
array('{{ name'),
|
||||||
|
array('{{ name }'),
|
||||||
|
array('{{{ name'),
|
||||||
|
array('{{{ name }'),
|
||||||
|
array('{{& name'),
|
||||||
|
array('{{& name }'),
|
||||||
|
array('{{# name'),
|
||||||
|
array('{{# name }'),
|
||||||
|
array('{{^ name'),
|
||||||
|
array('{{^ name }'),
|
||||||
|
array('{{/ name'),
|
||||||
|
array('{{/ name }'),
|
||||||
|
array('{{> name'),
|
||||||
|
array('{{< name'),
|
||||||
|
array('{{> name }'),
|
||||||
|
array('{{< name }'),
|
||||||
|
array('{{$ name'),
|
||||||
|
array('{{$ name }'),
|
||||||
|
array('{{= <% %>'),
|
||||||
|
array('{{= <% %>='),
|
||||||
|
array('{{= <% %>=}'),
|
||||||
|
array('{{% name'),
|
||||||
|
array('{{% name }'),
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user