跳转到主内容
趣航编程网 - 趣学编程,启航技术之路!

自个儿动手写一个简单的php模板引擎

自己动手写一个简单的 php 模板引擎 模板引擎中最核心的思想是:将模板中的变量编译为php的变量进行输出。 例如:demo.tpl PHP 8.5.5 PHP 8.5.5 是 PHP 8.5 分支的维护更新版本。该版本延续了“小步快跑”的迭代逻辑,通过深度错误修复、底层性能微调以及安全加固,旨在为开发者提供一个更健壮、更高效的运行环境。该版本严格遵守语义化版本规范,不包含破坏性变更。 下载
{$data} {$title}
那么模板引擎就要将{$data} {$title} 编译为 php echo $data; ? php echo $title; ? 立即学习 “ PHP免费学习笔记(深入) ”; 要实现这个功能使用正则替换就可以了:
$content = '{$data}{$title}'; $pattern = "/{\$([a-zA-Z_][a-zA-Z0-9_]*)}/"; $content = preg_replace($pattern,'tmpValue["$1"] ?>',$content); echo $content; //
这就是php模板引擎的核心功能了。下面是我写的一个简单的php模板引擎 首先是tempTool.class.php 它的作用的提供模板引擎需要用到的一些小工具
error[$k] = $v; }else { exit('tempTool.class.php的error方法收到了不确定的参数错误!'); } } /** * 获取错误信息 **/ public function getError() { foreach($this->error as $k=>$v) { echo $k.$v.'
'; } } } ?>
然后是template.class.php 它的作用是提供模板引擎应该有的功能
'template/', // 模板文件目录 'cmpDir'=>'compile/', // 编译文件目录 'cacheDir'=>'cache/', // 缓存文件目录 'tmpSuffix' =>'.tpl', // 模板文件后缀 'cacheSuffix' =>'.html', // 缓存文件后缀 'caching' =>false // 是否开启缓存 ); private $tmpFile; // 模板文件 private $cmpFile; // 编译文件 private $cacheFile; // 缓存文件 private $tmpValue = array(); // 变量值栈 public function __construct($config = null) { // 同步配置 if(is_array($config)) { $this->config = array_merge($this->config,$config); } // 检查模板编译缓存目录是否存在不存在创建 if( !$this->checkDir($this->config['tmpDir']) || !$this->checkDir($this->config['cmpDir']) || !$this->checkDir($this->config['cacheDir']) ) { exit; } } /** * 检查目录是否存在不存在自动创建 **/ private function checkDir($dir) { if(!is_dir($dir)) { if(!mkdir($dir)) { $this->errorLog[] = array('创建文件夹失败:'=>$dir); return false; } } return true; } /** * 像模板中分配变量 * **/ public function assign($k,$v) { if(!empty($k) && !empty($v)) { $this->tmpValue[$k] = $v; }else { $this->error('分配变量失败:','分配到模板中变量的key或者value为空!'); } } /** * 编译文件 **/ public function display($tmpFile) { // 获取模板文件 $tmpFile = $this->config['tmpDir'].$tmpFile.$this->config['tmpSuffix']; // 获取编译文件 $cmpFile = $this->config['cmpDir'].md5($tmpFile.'compile').'.php'; if(!file_exists($tmpFile)) { $this->error('模板文件不存在:',$tmpFile.'不存在'); } // 当编译文件不存在或者是模板文件被修改过了才重新编译 if(!file_exists($cmpFile) || filemtime($cmpFile) < filemtime($tmpFile)) { include_once "compile.class.php"; $cmp = new compile(); $cmp->cmp($tmpFile,$cmpFile); } // 是否开启缓存 if($this->config['caching']) { // 获取缓存文件 $cacheFile = $this->config['cacheDir'].md5($tmpFile.'cache').$this->config['cacheSuffix']; // 当缓存文件不存在或者是模板文件被修改过重新生成缓存文件 if(!file_exists($cacheFile) || filemtime($cacheFile) < filemtime($tmpFile)) { ob_start(); include_once $cmpFile; $content = ob_get_clean(); if(!file_put_contents($cacheFile,$content)){ $this->error('编译文件生成失败:',$cacheFile); } } //载入缓存文件 include $cacheFile; }else { // 载入编译文件 include_once $cmpFile; } } }
compile.class.php  编译类将模板文件编译为php文件
error("文件读取失败:",$tmpFile); } $pattern = "/{\$([a-zA-Z_][a-zA-Z0-9_]*)}/"; $this->content = preg_replace($pattern,'tmpValue["$1"] ?>',$content); $this->parse($cmpFile); } /** * 将编译好的内容写入文件 **/ public function parse($cmpFile) { if(!file_put_contents($cmpFile,$this->content)){ $this->error('文件写入失败:',$cmpFile); } } } ?>
下面进行一下测试: 1. 新建一个 template 文件夹 在里面写 一个模板 demo.tpl
{$data} {$title}
2.新建一个demo.php
true); include_once "template.class.php"; $tmp = new template($config); $tmp->assign('data','ccc'); $tmp->assign('title','这时测试用例'); $tmp->display('demo');
结果输出 ccc这时测试用例 可以看一下cache目录和 compile目录下  会生成一个缓存文件 和一个编译文件 这时就成功了

相关文章