在 PHP 中有没有更好的方法来做动态模板
In PHP is there a better way to do dynamic templating
我正在为一个应用程序创建模块,该应用程序将具有简单的自定义模板,其中包含将被数据库中的数据替换的标签。该模块的每个实例中的字段名称都不同。我想知道是否有更好的方法来做到这一点。
下面的代码是我想出的,但我相信一定有更好的方法。我在 preg_split 和 preg_match_all 上苦苦挣扎,刚刚达到我的极限,所以我用愚蠢的方式做到了。
<?php
$customTemplate = "
<div>
<<This>>
<<that>>
</div>
";
function process_template ($template, $begin = '<<', $end = '>>') {
$begin_exploded = explode($begin, $template);
if (is_array($begin_exploded)) {
foreach ($begin_exploded as $key1 => $value1) {
$end_exploded = explode($end, $value1);
if (is_array($end_exploded)) {
foreach ($end_exploded as $key2 => $value2) {
$tag = $begin.$value2.$end;
$variable = trim($value2);
$find_it = strpos($template,$tag);
if ($find_it !== false) {
//str_replace ($tag, $MyClass->get($variable), $template );
$template = str_replace ($tag, $variable, $template);
}
}
}
}
}
return $template;
}
echo(process_template($customTemplate));
/* Will Echo
<div>
This
that
</div>
*/
?>
以后我会连接 $MyClass->get() 来用正确的数据替换标签。自定义模板将由用户构建。
而不是 preg_split
或 preg_match
我宁愿使用 preg_replace_callback
,因为你正在做替换,替换值是从看起来最终将成为一种方法的东西派生的在另一个 class.
function process_template($template, $begin = '<<', $end = '>>') {
// get $MyClass in the function scope somehow. Maybe pass it as another parameter?
return preg_replace_callback("/$begin(\w+)$end/", function($var) use ($MyClass) {
return $MyClass->get($var[1]);
}, $template);
}
这里有一个可以玩的例子:https://3v4l.org/N1p03
我想这只是为了 fun/learning。如果我真的需要为某些事情使用模板,我宁愿从 composer require "twig/twig:^2.0"
开始。事实上,如果你有兴趣了解更多关于它是如何工作的,你可以去看看一个完善的系统,比如 twig 或 blade。 (Better than I've done it in this answer.)
周围有大量的模板引擎,但有时...只是为一件可能很简单的事情增加了复杂性和依赖性。这是我用来进行一些 javascript 更正的修改示例。这适用于您的模板。
function process_template($html,$b='<<',$e='>>'){
$replace=['this'=>'<input name="this" />','that'=>'<input name="that" />'];
if(preg_match_all('/('.$b.')(.*?)('.$e.')/is',$html,$matches,PREG_SET_ORDER|PREG_OFFSET_CAPTURE)){
$t='';$o=0;
foreach($matches as $m){
//for reference $m[1][0] contains $b, $m[2][0] contains $e
$t.=substr($html,$o,$m[0][1]-$o);
$t.=$replace[$m[2][0]];
$o=$m[3][1]+strlen($m[3][0]);
}
$t.=substr($html,$o);
$html=$t;
}
return $html;
}
$html="
<div>
<<this>>
<<that>>
</div>
";
$new=process_template($html);
echo $new;
出于演示目的,我放置了处理替换的数组 $replace
。您将那些替换为将处理替换的函数。
这是一个工作片段:https://3v4l.org/MBnbR
我喜欢这个功能,因为您可以控制在最终结果中替换什么和放回什么。顺便说一下,通过在正则表达式组出现的位置上使用 PREG_OFFSET_CAPTURE
和 return。那些在 $m[x][1]
上。捕获的文本将在 $m[x][0]
.
上
我正在为一个应用程序创建模块,该应用程序将具有简单的自定义模板,其中包含将被数据库中的数据替换的标签。该模块的每个实例中的字段名称都不同。我想知道是否有更好的方法来做到这一点。
下面的代码是我想出的,但我相信一定有更好的方法。我在 preg_split 和 preg_match_all 上苦苦挣扎,刚刚达到我的极限,所以我用愚蠢的方式做到了。
<?php
$customTemplate = "
<div>
<<This>>
<<that>>
</div>
";
function process_template ($template, $begin = '<<', $end = '>>') {
$begin_exploded = explode($begin, $template);
if (is_array($begin_exploded)) {
foreach ($begin_exploded as $key1 => $value1) {
$end_exploded = explode($end, $value1);
if (is_array($end_exploded)) {
foreach ($end_exploded as $key2 => $value2) {
$tag = $begin.$value2.$end;
$variable = trim($value2);
$find_it = strpos($template,$tag);
if ($find_it !== false) {
//str_replace ($tag, $MyClass->get($variable), $template );
$template = str_replace ($tag, $variable, $template);
}
}
}
}
}
return $template;
}
echo(process_template($customTemplate));
/* Will Echo
<div>
This
that
</div>
*/
?>
以后我会连接 $MyClass->get() 来用正确的数据替换标签。自定义模板将由用户构建。
而不是 preg_split
或 preg_match
我宁愿使用 preg_replace_callback
,因为你正在做替换,替换值是从看起来最终将成为一种方法的东西派生的在另一个 class.
function process_template($template, $begin = '<<', $end = '>>') {
// get $MyClass in the function scope somehow. Maybe pass it as another parameter?
return preg_replace_callback("/$begin(\w+)$end/", function($var) use ($MyClass) {
return $MyClass->get($var[1]);
}, $template);
}
这里有一个可以玩的例子:https://3v4l.org/N1p03
我想这只是为了 fun/learning。如果我真的需要为某些事情使用模板,我宁愿从 composer require "twig/twig:^2.0"
开始。事实上,如果你有兴趣了解更多关于它是如何工作的,你可以去看看一个完善的系统,比如 twig 或 blade。 (Better than I've done it in this answer.)
周围有大量的模板引擎,但有时...只是为一件可能很简单的事情增加了复杂性和依赖性。这是我用来进行一些 javascript 更正的修改示例。这适用于您的模板。
function process_template($html,$b='<<',$e='>>'){
$replace=['this'=>'<input name="this" />','that'=>'<input name="that" />'];
if(preg_match_all('/('.$b.')(.*?)('.$e.')/is',$html,$matches,PREG_SET_ORDER|PREG_OFFSET_CAPTURE)){
$t='';$o=0;
foreach($matches as $m){
//for reference $m[1][0] contains $b, $m[2][0] contains $e
$t.=substr($html,$o,$m[0][1]-$o);
$t.=$replace[$m[2][0]];
$o=$m[3][1]+strlen($m[3][0]);
}
$t.=substr($html,$o);
$html=$t;
}
return $html;
}
$html="
<div>
<<this>>
<<that>>
</div>
";
$new=process_template($html);
echo $new;
出于演示目的,我放置了处理替换的数组 $replace
。您将那些替换为将处理替换的函数。
这是一个工作片段:https://3v4l.org/MBnbR
我喜欢这个功能,因为您可以控制在最终结果中替换什么和放回什么。顺便说一下,通过在正则表达式组出现的位置上使用 PREG_OFFSET_CAPTURE
和 return。那些在 $m[x][1]
上。捕获的文本将在 $m[x][0]
.