mirror of
https://github.com/silverstripe/silverstripe-framework
synced 2024-10-02 14:18:46 +02:00
Merge pull request #2557 from camspiers/template-parser-configurable
Feature to allow changing the SSTemplateParser used in SSViewer
This commit is contained in:
commit
77696e207a
@ -634,6 +634,13 @@ class i18nTextCollector_Parser extends SSTemplateParser {
|
|||||||
|
|
||||||
private static $currentEntity = array();
|
private static $currentEntity = array();
|
||||||
|
|
||||||
|
public function __construct($string) {
|
||||||
|
$this->string = $string;
|
||||||
|
$this->pos = 0;
|
||||||
|
$this->depth = 0;
|
||||||
|
$this->regexps = array();
|
||||||
|
}
|
||||||
|
|
||||||
public function Translate__construct(&$res) {
|
public function Translate__construct(&$res) {
|
||||||
self::$currentEntity = array(null,null,null); //start with empty array
|
self::$currentEntity = array(null,null,null); //start with empty array
|
||||||
}
|
}
|
||||||
|
@ -65,14 +65,20 @@ class SSTemplateParseException extends Exception {
|
|||||||
* Angle Bracket: angle brackets "<" and ">" are used to eat whitespace between template elements
|
* Angle Bracket: angle brackets "<" and ">" are used to eat whitespace between template elements
|
||||||
* N: eats white space including newlines (using in legacy _t support)
|
* N: eats white space including newlines (using in legacy _t support)
|
||||||
*/
|
*/
|
||||||
class SSTemplateParser extends Parser {
|
class SSTemplateParser extends Parser implements TemplateParser {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var bool - Set true by SSTemplateParser::compileString if the template should include comments intended
|
* @var bool - Set true by SSTemplateParser::compileString if the template should include comments intended
|
||||||
* for debugging (template source, included files, etc)
|
* for debugging (template source, included files, etc)
|
||||||
*/
|
*/
|
||||||
protected $includeDebuggingComments = false;
|
protected $includeDebuggingComments = false;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Override the Parser constructor to change the requirement of setting a string
|
||||||
|
*/
|
||||||
|
function __construct() {
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Override the function that constructs the result arrays to also prepare a 'php' item in the array
|
* Override the function that constructs the result arrays to also prepare a 'php' item in the array
|
||||||
*/
|
*/
|
||||||
@ -1757,7 +1763,7 @@ class SSTemplateParser extends Parser {
|
|||||||
/* CacheBlockArgument:
|
/* CacheBlockArgument:
|
||||||
!( "if " | "unless " )
|
!( "if " | "unless " )
|
||||||
(
|
(
|
||||||
:DollarMarkedLookup |
|
:DollarMarkedLookup |
|
||||||
:QuotedString |
|
:QuotedString |
|
||||||
:Lookup
|
:Lookup
|
||||||
) */
|
) */
|
||||||
@ -4548,7 +4554,8 @@ class SSTemplateParser extends Parser {
|
|||||||
// non-dynamically calculated
|
// non-dynamically calculated
|
||||||
$text = preg_replace(
|
$text = preg_replace(
|
||||||
'/href\s*\=\s*\"\#/',
|
'/href\s*\=\s*\"\#/',
|
||||||
'href="\' . (Config::inst()->get(\'SSViewer\', \'rewrite_hash_links\') ? strip_tags( $_SERVER[\'REQUEST_URI\'] ) : "") .
|
'href="\' . (Config::inst()->get(\'SSViewer\', \'rewrite_hash_links\') ?' .
|
||||||
|
' strip_tags( $_SERVER[\'REQUEST_URI\'] ) : "") .
|
||||||
\'#',
|
\'#',
|
||||||
$text
|
$text
|
||||||
);
|
);
|
||||||
@ -4563,29 +4570,28 @@ class SSTemplateParser extends Parser {
|
|||||||
/**
|
/**
|
||||||
* Compiles some passed template source code into the php code that will execute as per the template source.
|
* Compiles some passed template source code into the php code that will execute as per the template source.
|
||||||
*
|
*
|
||||||
* @static
|
|
||||||
* @throws SSTemplateParseException
|
* @throws SSTemplateParseException
|
||||||
* @param $string The source of the template
|
* @param $string The source of the template
|
||||||
* @param string $templateName The name of the template, normally the filename the template source was loaded from
|
* @param string $templateName The name of the template, normally the filename the template source was loaded from
|
||||||
* @param bool $includeDebuggingComments True is debugging comments should be included in the output
|
* @param bool $includeDebuggingComments True is debugging comments should be included in the output
|
||||||
* @return mixed|string The php that, when executed (via include or exec) will behave as per the template source
|
* @return mixed|string The php that, when executed (via include or exec) will behave as per the template source
|
||||||
*/
|
*/
|
||||||
static function compileString($string, $templateName = "", $includeDebuggingComments=false) {
|
public function compileString($string, $templateName = "", $includeDebuggingComments=false) {
|
||||||
if (!trim($string)) {
|
if (!trim($string)) {
|
||||||
$code = '';
|
$code = '';
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// Construct a parser instance
|
parent::__construct($string);
|
||||||
$parser = new SSTemplateParser($string);
|
|
||||||
$parser->includeDebuggingComments = $includeDebuggingComments;
|
$this->includeDebuggingComments = $includeDebuggingComments;
|
||||||
|
|
||||||
// Ignore UTF8 BOM at begining of string. TODO: Confirm this is needed, make sure SSViewer handles UTF
|
// Ignore UTF8 BOM at begining of string. TODO: Confirm this is needed, make sure SSViewer handles UTF
|
||||||
// (and other encodings) properly
|
// (and other encodings) properly
|
||||||
if(substr($string, 0,3) == pack("CCC", 0xef, 0xbb, 0xbf)) $parser->pos = 3;
|
if(substr($string, 0,3) == pack("CCC", 0xef, 0xbb, 0xbf)) $this->pos = 3;
|
||||||
|
|
||||||
// Match the source against the parser
|
// Match the source against the parser
|
||||||
$result = $parser->match_TopTemplate();
|
$result = $this->match_TopTemplate();
|
||||||
if(!$result) throw new SSTemplateParseException('Unexpected problem parsing template', $parser);
|
if(!$result) throw new SSTemplateParseException('Unexpected problem parsing template', $this);
|
||||||
|
|
||||||
// Get the result
|
// Get the result
|
||||||
$code = $result['php'];
|
$code = $result['php'];
|
||||||
@ -4593,7 +4599,7 @@ class SSTemplateParser extends Parser {
|
|||||||
|
|
||||||
// Include top level debugging comments if desired
|
// Include top level debugging comments if desired
|
||||||
if($includeDebuggingComments && $templateName && stripos($code, "<?xml") === false) {
|
if($includeDebuggingComments && $templateName && stripos($code, "<?xml") === false) {
|
||||||
$code = $parser->includeDebuggingComments($code, $templateName);
|
$code = $this->includeDebuggingComments($code, $templateName);
|
||||||
}
|
}
|
||||||
|
|
||||||
return $code;
|
return $code;
|
||||||
@ -4640,7 +4646,7 @@ class SSTemplateParser extends Parser {
|
|||||||
* @param $template - A file path that contains template source code
|
* @param $template - A file path that contains template source code
|
||||||
* @return mixed|string - The php that, when executed (via include or exec) will behave as per the template source
|
* @return mixed|string - The php that, when executed (via include or exec) will behave as per the template source
|
||||||
*/
|
*/
|
||||||
static function compileFile($template) {
|
public function compileFile($template) {
|
||||||
return self::compileString(file_get_contents($template), $template);
|
return $this->compileString(file_get_contents($template), $template);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -86,14 +86,20 @@ class SSTemplateParseException extends Exception {
|
|||||||
* Angle Bracket: angle brackets "<" and ">" are used to eat whitespace between template elements
|
* Angle Bracket: angle brackets "<" and ">" are used to eat whitespace between template elements
|
||||||
* N: eats white space including newlines (using in legacy _t support)
|
* N: eats white space including newlines (using in legacy _t support)
|
||||||
*/
|
*/
|
||||||
class SSTemplateParser extends Parser {
|
class SSTemplateParser extends Parser implements TemplateParser {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var bool - Set true by SSTemplateParser::compileString if the template should include comments intended
|
* @var bool - Set true by SSTemplateParser::compileString if the template should include comments intended
|
||||||
* for debugging (template source, included files, etc)
|
* for debugging (template source, included files, etc)
|
||||||
*/
|
*/
|
||||||
protected $includeDebuggingComments = false;
|
protected $includeDebuggingComments = false;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Override the Parser constructor to change the requirement of setting a string
|
||||||
|
*/
|
||||||
|
function __construct() {
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Override the function that constructs the result arrays to also prepare a 'php' item in the array
|
* Override the function that constructs the result arrays to also prepare a 'php' item in the array
|
||||||
*/
|
*/
|
||||||
@ -462,7 +468,7 @@ class SSTemplateParser extends Parser {
|
|||||||
CacheBlockArgument:
|
CacheBlockArgument:
|
||||||
!( "if " | "unless " )
|
!( "if " | "unless " )
|
||||||
(
|
(
|
||||||
:DollarMarkedLookup |
|
:DollarMarkedLookup |
|
||||||
:QuotedString |
|
:QuotedString |
|
||||||
:Lookup
|
:Lookup
|
||||||
)
|
)
|
||||||
@ -1018,29 +1024,28 @@ class SSTemplateParser extends Parser {
|
|||||||
/**
|
/**
|
||||||
* Compiles some passed template source code into the php code that will execute as per the template source.
|
* Compiles some passed template source code into the php code that will execute as per the template source.
|
||||||
*
|
*
|
||||||
* @static
|
|
||||||
* @throws SSTemplateParseException
|
* @throws SSTemplateParseException
|
||||||
* @param $string The source of the template
|
* @param $string The source of the template
|
||||||
* @param string $templateName The name of the template, normally the filename the template source was loaded from
|
* @param string $templateName The name of the template, normally the filename the template source was loaded from
|
||||||
* @param bool $includeDebuggingComments True is debugging comments should be included in the output
|
* @param bool $includeDebuggingComments True is debugging comments should be included in the output
|
||||||
* @return mixed|string The php that, when executed (via include or exec) will behave as per the template source
|
* @return mixed|string The php that, when executed (via include or exec) will behave as per the template source
|
||||||
*/
|
*/
|
||||||
static function compileString($string, $templateName = "", $includeDebuggingComments=false) {
|
public function compileString($string, $templateName = "", $includeDebuggingComments=false) {
|
||||||
if (!trim($string)) {
|
if (!trim($string)) {
|
||||||
$code = '';
|
$code = '';
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// Construct a parser instance
|
parent::__construct($string);
|
||||||
$parser = new SSTemplateParser($string);
|
|
||||||
$parser->includeDebuggingComments = $includeDebuggingComments;
|
$this->includeDebuggingComments = $includeDebuggingComments;
|
||||||
|
|
||||||
// Ignore UTF8 BOM at begining of string. TODO: Confirm this is needed, make sure SSViewer handles UTF
|
// Ignore UTF8 BOM at begining of string. TODO: Confirm this is needed, make sure SSViewer handles UTF
|
||||||
// (and other encodings) properly
|
// (and other encodings) properly
|
||||||
if(substr($string, 0,3) == pack("CCC", 0xef, 0xbb, 0xbf)) $parser->pos = 3;
|
if(substr($string, 0,3) == pack("CCC", 0xef, 0xbb, 0xbf)) $this->pos = 3;
|
||||||
|
|
||||||
// Match the source against the parser
|
// Match the source against the parser
|
||||||
$result = $parser->match_TopTemplate();
|
$result = $this->match_TopTemplate();
|
||||||
if(!$result) throw new SSTemplateParseException('Unexpected problem parsing template', $parser);
|
if(!$result) throw new SSTemplateParseException('Unexpected problem parsing template', $this);
|
||||||
|
|
||||||
// Get the result
|
// Get the result
|
||||||
$code = $result['php'];
|
$code = $result['php'];
|
||||||
@ -1048,7 +1053,7 @@ class SSTemplateParser extends Parser {
|
|||||||
|
|
||||||
// Include top level debugging comments if desired
|
// Include top level debugging comments if desired
|
||||||
if($includeDebuggingComments && $templateName && stripos($code, "<?xml") === false) {
|
if($includeDebuggingComments && $templateName && stripos($code, "<?xml") === false) {
|
||||||
$code = $parser->includeDebuggingComments($code, $templateName);
|
$code = $this->includeDebuggingComments($code, $templateName);
|
||||||
}
|
}
|
||||||
|
|
||||||
return $code;
|
return $code;
|
||||||
@ -1095,7 +1100,7 @@ class SSTemplateParser extends Parser {
|
|||||||
* @param $template - A file path that contains template source code
|
* @param $template - A file path that contains template source code
|
||||||
* @return mixed|string - The php that, when executed (via include or exec) will behave as per the template source
|
* @return mixed|string - The php that, when executed (via include or exec) will behave as per the template source
|
||||||
*/
|
*/
|
||||||
static function compileFile($template) {
|
public function compileFile($template) {
|
||||||
return self::compileString(file_get_contents($template), $template);
|
return $this->compileString(file_get_contents($template), $template);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -614,6 +614,11 @@ class SSViewer {
|
|||||||
*/
|
*/
|
||||||
protected $includeRequirements = true;
|
protected $includeRequirements = true;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var TemplateParser
|
||||||
|
*/
|
||||||
|
protected $parser;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a template from a string instead of a .ss file
|
* Create a template from a string instead of a .ss file
|
||||||
*
|
*
|
||||||
@ -691,7 +696,9 @@ class SSViewer {
|
|||||||
* array('MySpecificPage', 'MyPage', 'Page')
|
* array('MySpecificPage', 'MyPage', 'Page')
|
||||||
* </code>
|
* </code>
|
||||||
*/
|
*/
|
||||||
public function __construct($templateList) {
|
public function __construct($templateList, TemplateParser $parser = null) {
|
||||||
|
$this->setParser($parser ?: Injector::inst()->get('SSTemplateParser'));
|
||||||
|
|
||||||
// flush template manifest cache if requested
|
// flush template manifest cache if requested
|
||||||
if (isset($_GET['flush']) && $_GET['flush'] == 'all') {
|
if (isset($_GET['flush']) && $_GET['flush'] == 'all') {
|
||||||
if(Director::isDev() || Director::is_cli() || Permission::check('ADMIN')) {
|
if(Director::isDev() || Director::is_cli() || Permission::check('ADMIN')) {
|
||||||
@ -728,7 +735,25 @@ class SSViewer {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the template parser that will be used in template generation
|
||||||
|
* @param \TemplateParser $parser
|
||||||
|
*/
|
||||||
|
public function setParser(TemplateParser $parser)
|
||||||
|
{
|
||||||
|
$this->parser = $parser;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the parser that is set for template generation
|
||||||
|
* @return \TemplateParser
|
||||||
|
*/
|
||||||
|
public function getParser()
|
||||||
|
{
|
||||||
|
return $this->parser;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns true if at least one of the listed templates exists.
|
* Returns true if at least one of the listed templates exists.
|
||||||
*
|
*
|
||||||
@ -970,7 +995,7 @@ class SSViewer {
|
|||||||
|
|
||||||
if(!file_exists($cacheFile) || filemtime($cacheFile) < $lastEdited || isset($_GET['flush'])) {
|
if(!file_exists($cacheFile) || filemtime($cacheFile) < $lastEdited || isset($_GET['flush'])) {
|
||||||
$content = file_get_contents($template);
|
$content = file_get_contents($template);
|
||||||
$content = SSViewer::parseTemplateContent($content, $template);
|
$content = $this->parseTemplateContent($content, $template);
|
||||||
|
|
||||||
$fh = fopen($cacheFile,'w');
|
$fh = fopen($cacheFile,'w');
|
||||||
fwrite($fh, $content);
|
fwrite($fh, $content);
|
||||||
@ -983,7 +1008,7 @@ class SSViewer {
|
|||||||
// through $Content and $Layout placeholders.
|
// through $Content and $Layout placeholders.
|
||||||
foreach(array('Content', 'Layout') as $subtemplate) {
|
foreach(array('Content', 'Layout') as $subtemplate) {
|
||||||
if(isset($this->chosenTemplates[$subtemplate])) {
|
if(isset($this->chosenTemplates[$subtemplate])) {
|
||||||
$subtemplateViewer = new SSViewer($this->chosenTemplates[$subtemplate]);
|
$subtemplateViewer = new SSViewer($this->chosenTemplates[$subtemplate], $this->parser);
|
||||||
$subtemplateViewer->includeRequirements(false);
|
$subtemplateViewer->includeRequirements(false);
|
||||||
$subtemplateViewer->setPartialCacheStore($this->getPartialCacheStore());
|
$subtemplateViewer->setPartialCacheStore($this->getPartialCacheStore());
|
||||||
|
|
||||||
@ -1028,10 +1053,10 @@ class SSViewer {
|
|||||||
return $v->process($data, $arguments, $scope);
|
return $v->process($data, $arguments, $scope);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static function parseTemplateContent($content, $template="") {
|
public function parseTemplateContent($content, $template="") {
|
||||||
return SSTemplateParser::compileString(
|
return $this->parser->compileString(
|
||||||
$content,
|
$content,
|
||||||
$template,
|
$template,
|
||||||
Director::isDev() && Config::inst()->get('SSViewer', 'source_file_comments')
|
Director::isDev() && Config::inst()->get('SSViewer', 'source_file_comments')
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -1079,7 +1104,8 @@ class SSViewer {
|
|||||||
class SSViewer_FromString extends SSViewer {
|
class SSViewer_FromString extends SSViewer {
|
||||||
protected $content;
|
protected $content;
|
||||||
|
|
||||||
public function __construct($content) {
|
public function __construct($content, TemplateParser $parser = null) {
|
||||||
|
$this->setParser($parser ?: Injector::inst()->get('SSTemplateParser'));
|
||||||
$this->content = $content;
|
$this->content = $content;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1091,7 +1117,7 @@ class SSViewer_FromString extends SSViewer {
|
|||||||
$arguments = null;
|
$arguments = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
$template = SSViewer::parseTemplateContent($this->content, "string sha1=".sha1($this->content));
|
$template = $this->parseTemplateContent($this->content, "string sha1=".sha1($this->content));
|
||||||
|
|
||||||
$tmpFile = tempnam(TEMP_FOLDER,"");
|
$tmpFile = tempnam(TEMP_FOLDER,"");
|
||||||
$fh = fopen($tmpFile, 'w');
|
$fh = fopen($tmpFile, 'w');
|
||||||
|
19
view/TemplateParser.php
Normal file
19
view/TemplateParser.php
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This interface needs to be implemented by any template parser that is used in SSViewer
|
||||||
|
*
|
||||||
|
* @package framework
|
||||||
|
* @subpackage view
|
||||||
|
*/
|
||||||
|
interface TemplateParser {
|
||||||
|
/**
|
||||||
|
* Compiles some passed template source code into the php code that will execute as per the template source.
|
||||||
|
*
|
||||||
|
* @param $string The source of the template
|
||||||
|
* @param string $templateName The name of the template, normally the filename the template source was loaded from
|
||||||
|
* @param bool $includeDebuggingComments True is debugging comments should be included in the output
|
||||||
|
* @return mixed|string The php that, when executed (via include or exec) will behave as per the template source
|
||||||
|
*/
|
||||||
|
public function compileString($string, $templateName = "", $includeDebuggingComments = false);
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user