TP3.0框架中模板儲存到資料庫的實作方法

黄舟
發布: 2023-03-15 14:12:02
原創
1800 人瀏覽過

這篇文章主要介紹了thinkPHP3.0框架實現模板保存到資料庫的方法,結合實例形式分析了使用thinkPHP3.0框架開發CMS系統過程中將模板保存到數據庫的具體實現步驟與相關操作技巧,需要的朋友可以參考下

本文實例講述了thinkPHP3.0框架實作範本保存到資料庫的方法。分享給大家供大家參考,具體如下:

在開發cms的時候用到如果將模板文件存入到數據庫並顯示到頁面中

由於thinkphp3.0都是直接從模板檔案中讀取再解析的那麼對於模板存入資料庫中就只有自己開發了,還有thinkphp3.0中有mode的功能我們可以定義自己的mode這樣就可以達到目的了,那麼如何來擴展自己的mode呢?如下:

1.在你的入口文件中輸入


define('MODE_NAME','Ey');
登入後複製

其中"Ey"就是你自己擴充的mode名稱了,請在你的thinkphp/Extend/Mode檔案下面建立Ey資料夾

2.在Ey目錄中修改

新增tags.php檔案內容如下:


return array(
  'app_init'=>array(
  ),
  'app_begin'=>array(
    'ReadHtmlCache', // 读取静态缓存
  ),
  'route_check'=>array(
    'CheckRoute', // 路由检测
  ),
  'app_end'=>array(),
  'path_info'=>array(),
  'action_begin'=>array(),
  'action_end'=>array(),
  'view_begin'=>array(),
  'view_template'=>array(
    'ExtensionTemplate', // 自动定位模板文件(手动添加)
  ),
  'view_content'=>array(
    'ParseContent'//(手动添加)
  ),
  'view_filter'=>array(
    'ContentReplace', // 模板输出替换
    'TokenBuild',  // 表单令牌
    'WriteHtmlCache', // 写入静态缓存
    'ShowRuntime', // 运行时间显示
  ),
  'view_end'=>array(
    'ShowPageTrace', // 页面Trace显示
  ),
);
登入後複製

該文件中後面的註釋中添加手動添加了為我的修改,只是修改thinkphp中默認的tags中查找模板和解析模板的行為

將系統默認的action和view類複製到Ey的目錄中(由於解析內容,所以要修改action和view類別),修改action.class.php中的fetch方法:


protected function fetch($templateFile='',$templateContent='' ){
    return $this->view->fetch($templateFile,$templateContent);
}
登入後複製

view.class. php檔案中的修改為:


public function fetch($templateFile='',$templateContent = NULL) {
    $params['templateFile'] = $templateFile;
    $params['cacheFlag'] = true;
    if(isset($templateContent)) {
      $params['templateContent'] = $templateContent;
    }
    tag('view_template',$params);
    // 页面缓存
    ob_start();
    ob_implicit_flush(0);
    if('php' == strtolower(C('TMPL_ENGINE_TYPE'))) { // 使用PHP原生模板
      // 模板阵列变量分解成为独立变量
      extract($this->tVar, EXTR_OVERWRITE);
      // 直接载入PHP模板
      include $templateFile;
    }else{
      // 视图解析标签
      $params = array('var'=>$this->tVar,'content'=>$params['templateContent'],'file'=>$params['templateFile'],'cacheFlag'=>$params['cacheFlag']);
      tag('view_content',$params);
    }
    // 获取并清空缓存
    $content = ob_get_clean();
    // 内容过滤标签
    tag('view_filter',$content);
    // 输出模板文件
    return $content;
}
登入後複製

3.擴充自己的尋找範本的類別(自己擴充的行為tp讓我們放在thinkphp\Extend\Behavior中)
在thinkphp\Extend\Behavior中加入ExtensionTemplateBehavior.class.php類別,內容如下:


class ExtensionTemplateBehavior extends Behavior {
  // 行为扩展的执行入口必须是run
  public function run(&$params){
    if( is_array($params) ){
      if( array_key_exists('templateFile', $params) ){
        $params  = $this->parseTemplateFile($params);
      }else{
        //异常
        throw_exception(L('_TEMPLATE_NOT_EXIST_AND_CONTENT_NULL_').'['.$params['templateFile'].']');
      }
    }else{
      // 自动定位模板文件
      if(!file_exists_case($params))
        $params  = $this->parseTemplateFile($params);
    }
  }
  private function parseTemplateFile($params) {
    if( is_array($params) ) {
      $templateFile = $params['templateFile'];
    }else{
      $templateFile = $params;
    }
    if(!isset($params['templateContent'])) { // 是否设置 templateContent 参数
      //自动获取模板文件
      if('' == $templateFile){
        // 如果模板文件名为空 按照默认规则定位
        $templateFile = C('TEMPLATE_NAME');
      } elseif(false === strpos($templateFile,C('TMPL_TEMPLATE_SUFFIX'))) {
        $path  = explode(':',$templateFile);
        //如果是插件
        if($path[0] == 'Ext') {
          $templateFile = str_replace(array('Ext:',$path[1] . ':',$path[2] . ':'),'',$templateFile);
          $templateFile = SITE_ROOT . '/Ext/extensions/' . strtolower($path[1]) . '/' . $path[2] . '/Tpl/' . $templateFile . C('TMPL_TEMPLATE_SUFFIX');
        } else {
          // 解析规则为 模板主题:模块:操作 不支持 跨项目和跨分组调用
          $action = array_pop($path);
          $module = !empty($path)?array_pop($path):MODULE_NAME;
          if(!empty($path)) {// 设置模板主题
            $path = dirname(THEME_PATH).'/'.array_pop($path).'/';
          }else{
            $path = THEME_PATH;
          }
          $depr = defined('GROUP_NAME')?C('TMPL_FILE_DEPR'):'/';
          $templateFile = $path.$module.$depr.$action.C('TMPL_TEMPLATE_SUFFIX');
        }
      }
    } else {
      if('' == $templateFile){
        $depr = defined('GROUP_NAME')?C('TMPL_FILE_DEPR'):'/';
        $params['cacheFlag'] = false;
      } else {
        $path  = explode(':',$templateFile);
        //如果是插件
        if($path[0] == 'Ext') {
          $templateFile = str_replace(array('Ext:',$path[1] . ':',$path[2] . ':'),'',$templateFile);
          $templateFile = SITE_ROOT . '/Ext/extensions/' . strtolower($path[1]) . '/' . $path[2] . '/Tpl/' . $templateFile . C('TMPL_TEMPLATE_SUFFIX');
        } else {
          // 解析规则为 模板主题:模块:操作 不支持 跨项目和跨分组调用
          $action = array_pop($path);
          $module = !empty($path)?array_pop($path):MODULE_NAME;
          if(!empty($path)) {// 设置模板主题
            $path = dirname(THEME_PATH).'/'.array_pop($path).'/';
          }else{
            $path = THEME_PATH;
          }
          $depr = defined('GROUP_NAME')?C('TMPL_FILE_DEPR'):'/';
          $templateFile = $path.$module.$depr.$action.C('TMPL_TEMPLATE_SUFFIX');
        }
      }
    }
    if( is_array($params) ){
      $params['templateFile'] = $templateFile;
      return $params;
    }else{
      if(!file_exists_case($templateFile))
        throw_exception(L('_TEMPLATE_NOT_EXIST_').'['.$templateFile.']');
      return $templateFile;
    }
  }
}
登入後複製

4.新增解析自己的範本的行為類別(這個和thinkphp3 .0預設的ParseTemplateBehavior.class.php類似)


class ParseContentBehavior extends Behavior {
  protected $options  = array(
    // 布局设置
    'TMPL_ENGINE_TYPE'   => 'Ey',   // 默认模板引擎 以下设置仅对使用Ey模板引擎有效
    'TMPL_CACHFILE_SUFFIX' => '.php',   // 默认模板缓存后缀
    'TMPL_DENY_FUNC_LIST'  => 'echo,exit', // 模板引擎禁用函数
    'TMPL_DENY_PHP' =>false, // 默认模板引擎是否禁用PHP原生代码
    'TMPL_L_DELIM'     => '{',     // 模板引擎普通标签开始标记
    'TMPL_R_DELIM'     => '}',     // 模板引擎普通标签结束标记
    'TMPL_VAR_IDENTIFY'   => 'array',   // 模板变量识别。留空自动判断,参数为'obj'则表示对象
    'TMPL_STRIP_SPACE'   => true,    // 是否去除模板文件里面的html空格与换行
    'TMPL_CACHE_ON'     => true,    // 是否开启模板编译缓存,设为false则每次都会重新编译
    'TMPL_CACHE_TIME'    =>  0,     // 模板缓存有效期 0 为永久,(以数字为值,单位:秒)
    'TMPL_LAYOUT_ITEM'  =>  '{__CONTENT__}', // 布局模板的内容替换标识
    'LAYOUT_ON'      => false, // 是否启用布局
    'LAYOUT_NAME'    => 'layout', // 当前布局名称 默认为layout
    // Think模板引擎标签库相关设定
    &#39;TAGLIB_BEGIN&#39;     => &#39;<&#39;, // 标签库标签开始标记
    &#39;TAGLIB_END&#39;      => &#39;>&#39;, // 标签库标签结束标记
    &#39;TAGLIB_LOAD&#39;      => true, // 是否使用内置标签库之外的其它标签库,默认自动检测
    &#39;TAGLIB_BUILD_IN&#39;    => &#39;cx&#39;, // 内置标签库名称(标签使用不必指定标签库名称),以逗号分隔 注意解析顺序
    &#39;TAGLIB_PRE_LOAD&#39;    => &#39;&#39;,  // 需要额外加载的标签库(须指定标签库名称),多个以逗号分隔
    );
  public function run(&$_data){
    $engine = strtolower(C(&#39;TMPL_ENGINE_TYPE&#39;));
    //这个地方要判断是否存在文件
    if(&#39;think&#39;==$engine){
      if($this->checkCache($_data[&#39;file&#39;])) { // 缓存有效
        // 分解变量并载入模板缓存
        extract($_data[&#39;var&#39;], EXTR_OVERWRITE);
        //载入模版缓存文件
        include C(&#39;CACHE_PATH&#39;).md5($_data[&#39;file&#39;]).C(&#39;TMPL_CACHFILE_SUFFIX&#39;);
      }else{
        $tpl = Think::instance(&#39;ThinkTemplate&#39;);
        // 编译并加载模板文件
        $tpl->fetch($_data[&#39;file&#39;],$_data[&#39;var&#39;]);
      }
    } else if(&#39;ey&#39; == $engine) {
      if( !$_data[&#39;cacheFlag&#39;] ){
        $class  = &#39;Template&#39;.ucwords($engine);
        if(is_file(CORE_PATH.&#39;Driver/Template/&#39;.$class.&#39;.class.php&#39;)) {
          // 内置驱动
          $path = CORE_PATH;
        } else {
          // 扩展驱动
          $path = EXTEND_PATH;
        }
        if(require_cache($path.&#39;Driver/Template/&#39;.$class.&#39;.class.php&#39;)) {
          $tpl  = new $class;
          $tpl->fetch(&#39;&#39;,$_data[&#39;content&#39;],$_data[&#39;var&#39;]);
        } else { // 类没有定义
          throw_exception(L(&#39;_NOT_SUPPERT_&#39;).&#39;: &#39; . $class);
        }
      }else{
        //操作
        $cache_flag = true;
        if(isset($_data[&#39;content&#39;])){ //如果指定内容
          if ($_data[&#39;file&#39;]){ //指定缓存KEY
            $_data[&#39;file&#39;] = &#39;custom_&#39; . $_data[&#39;file&#39;];
          } else { //未指定缓存KEY,则不缓存
            $cache_flag = false;
          }
        } else {
          if (is_file($_data[&#39;file&#39;])){ //如果指定文件存在
            $_data[&#39;content&#39;] = file_get_contents($_data[&#39;file&#39;]);
          } else {
            throw_exception(L(&#39;_TEMPLATE_NOT_EXIST_&#39;).&#39;[&#39;.$_data[&#39;file&#39;].&#39;]&#39;);
          }
        }
        //这里文件和内容一定有一个存在,否则在之前就会有异常了
        if($cache_flag && $this->checkCache($_data[&#39;file&#39;],$_data[&#39;content&#39;]) ) { // 缓存有效
          // 分解变量并载入模板缓存
          extract($_data[&#39;var&#39;], EXTR_OVERWRITE);
          //载入模版缓存文件
          include C(&#39;CACHE_PATH&#39;).md5($_data[&#39;file&#39;]).C(&#39;TMPL_CACHFILE_SUFFIX&#39;);
        } else {
          $class  = &#39;Template&#39;.ucwords($engine);
          if(is_file(CORE_PATH.&#39;Driver/Template/&#39;.$class.&#39;.class.php&#39;)) {
            // 内置驱动
            $path = CORE_PATH;
          } else {
            // 扩展驱动
            $path = EXTEND_PATH;
          }
          if(require_cache($path.&#39;Driver/Template/&#39;.$class.&#39;.class.php&#39;)) {
            $tpl  = new $class;
            $tpl->fetch($_data[&#39;file&#39;],$_data[&#39;content&#39;],$_data[&#39;var&#39;]);
          } else { // 类没有定义
            throw_exception(L(&#39;_NOT_SUPPERT_&#39;).&#39;: &#39; . $class);
          }
        }
      }
    } else {
      //调用第三方模板引擎解析和输出
      $class  = &#39;Template&#39;.ucwords($engine);
      if(is_file(CORE_PATH.&#39;Driver/Template/&#39;.$class.&#39;.class.php&#39;)) {
        // 内置驱动
        $path = CORE_PATH;
      }else{ // 扩展驱动
        $path = EXTEND_PATH;
      }
      if(require_cache($path.&#39;Driver/Template/&#39;.$class.&#39;.class.php&#39;)) {
        $tpl  = new $class;
        $tpl->fetch($_data[&#39;file&#39;],$_data[&#39;var&#39;]);
      }else { // 类没有定义
        throw_exception(L(&#39;_NOT_SUPPERT_&#39;).&#39;: &#39; . $class);
      }
    }
  }
  protected function checkCache($tmplTemplateFile = &#39;&#39;,$tmplTemplateContent=&#39;&#39;) {
    if (!C(&#39;TMPL_CACHE_ON&#39;))// 优先对配置设定检测
      return false;
    //缓存文件名
    $tmplCacheFile = C(&#39;CACHE_PATH&#39;).md5($tmplTemplateFile).C(&#39;TMPL_CACHFILE_SUFFIX&#39;);
    if(!is_file($tmplCacheFile)){
      return false;
    }elseif (filemtime($tmplTemplateFile) > filemtime($tmplCacheFile)) {
      // 模板文件如果有更新则缓存需要更新
      return false;
    }elseif (C(&#39;TMPL_CACHE_TIME&#39;) != 0 && time() > filemtime($tmplCacheFile)+C(&#39;TMPL_CACHE_TIME&#39;)) {
      // 缓存是否在有效期
      return false;
    }
    // 开启布局模板
    if(C(&#39;LAYOUT_ON&#39;)) {
      $layoutFile = THEME_PATH.C(&#39;LAYOUT_NAME&#39;).C(&#39;TMPL_TEMPLATE_SUFFIX&#39;);
      if(filemtime($layoutFile) > filemtime($tmplCacheFile)) {
        return false;
      }
    }
    // 缓存有效
    return true;
  }
}
登入後複製

5.加入自己解析模板內容的類別TemplateEy.class.php(這個放在thinkphp\Extend\Driver \Template目錄下面)
只是將系統預設的ThinkTemplate.class.php類別修改了fetch方法修改程式碼如下:


// 加载模板
public function fetch($templateFile,$templateContent,$templateVar) {
    $this->tVar = $templateVar;
    if($templateContent && !$templateFile) { //不缓存
      if(C(&#39;LAYOUT_ON&#39;)) {
        if(false !== strpos($templateContent,&#39;{__NOLAYOUT__}&#39;)) { // 可以单独定义不使用布局
          $templateContent = str_replace(&#39;{__NOLAYOUT__}&#39;,&#39;&#39;,$templateContent);
        }else{ // 替换布局的主体内容
          $layoutFile = THEME_PATH.C(&#39;LAYOUT_NAME&#39;).$this->config[&#39;template_suffix&#39;];
          $templateContent = str_replace($this->config[&#39;layout_item&#39;],$templateContent,file_get_contents($layoutFile));
        }
      }
      //编译模板内容
      $templateContent = $this->compiler($templateContent);
      extract($templateVar, EXTR_OVERWRITE);
      echo $templateContent;
    } else {
      $templateCacheFile = $this->loadTemplate($templateFile,$templateContent);
      // 模板阵列变量分解成为独立变量
      extract($templateVar, EXTR_OVERWRITE);
      //载入模版缓存文件
      include $templateCacheFile;
    }
}
登入後複製

6.呼叫如果資料庫中模板的內容不存在那麼我們還是去讀資料庫中的內容:


if( array_key_exists( $display_mode, $params[&#39;tpl&#39;] ) && strlen($params[&#39;tpl&#39;][$display_mode]) > 0 ){
return $this->fetch("Ext:New:Frontend:show",$params[&#39;tpl&#39;][$display_mode]);
}else{
return $this->fetch("Ext:New:Frontend:show");
}
登入後複製

以上是TP3.0框架中模板儲存到資料庫的實作方法的詳細內容。更多資訊請關注PHP中文網其他相關文章!

相關標籤:
來源:php.cn
本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn
熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板
關於我們 免責聲明 Sitemap
PHP中文網:公益線上PHP培訓,幫助PHP學習者快速成長!