CodeIgniter网站静态化管理系统
CodeIgniter本身带了一套静态化系统
使用方法如下:
$this->output->cache( 3 );//每三分钟重新生成一次静态页面
不过这个在系统化的编辑中不方便管理 由此开发者可以自定义一套自己的缓存管理系统
比如加载相关的ctrl + act配置到memcache中以方便配置的查询 及缓存的清理重新生成等
增加数据库表如下
CREATE TABLE `chewu_news` (
`id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,
`delsign` tinyint(3) unsigned NOT NULL,
`mid` bigint(20) unsigned NOT NULL,
`comment` varchar(128) DEFAULT NULL,
`modtime` datetime NOT NULL,
`addtime` datetime NOT NULL,
`controller' varchar(128) NOT NULL,
'action' varchar(128) NOT NULL,
'minutes' mediumint default 0;
PRIMARY KEY (`id`)
) ENGINE=MyISAM AUTO_INCREMENT=138 DEFAULT CHARSET=utf8 COMMENT='缓存管理表;
添加ctrl action到数据库中
/**
* dev
* 加载ctrl action到数据库中 只在开发时使用
*/
public function loadCtrlActIntoDb()
{
$this->_load_ctrls_into_db( dirname( dirname( __FILE__ ) ));
}
//////////////////////////////////////////////////////////////////////////////////
//load cache info into database
private function _load_ctrls_into_db( $dir )
{
include_once APPPATH . 'utils/TimeUtils.php';
$list = scandir( $dir ); // 得到该文件下的所有文件和文件夹
foreach( $list as $file)
{ //遍历
$file_location = $dir . "/" . $file; //生成路径
if( is_file( $file_location ) && (-1 != strstr( $file_location, '.php' ) || -1 != strstr( $file_location, '.PHP' )) )
{
//取class
$iBegin = strpos( $file_location, 'controllers' );
$iBegin += strlen( 'controllers' );
$iEnd = strrpos( $file_location, '/' );
$strModel = '';
$strModel = substr( $file_location, $iBegin + 1, strrpos( $file_location, '.php' ) - $iBegin - 1 );
if( $iBegin != $iEnd )
{ //model为文件夹名+文件名
$strModel = str_replace( '/', '_', $strModel );
}
if( 0 === strpos( $strModel, 'learn' ) || 0 === strpos( $strModel, 'test' ) || 0 === strpos( $strModel, 'config' ) )
{
continue;
}
$strClsFile = file_get_contents( $file_location );
$iPos = strpos( $strClsFile, 'class' );
if( false == $iPos )
{ //非类文件
continue;
}
$strClsFile = substr( $strClsFile, $iPos );
$arrRes = preg_split( '/public[ ]+function[ ]+/', $strClsFile );
$strCls = $arrRes [0];
$strCls = preg_replace( '/[ ]+/', ' ', $strCls );
$arrCls = explode( ' ', $strCls );
$strCtrl = trim( $arrCls [1] );
$iSize = count( $arrRes );
for( $i = 1; $i < $iSize; ++ $i )
{ //
$strAction = trim( $arrRes [$i] );
$iEnd = strpos( $strAction, '(' );
$strFunc = substr( $strAction, 0, $iEnd );
if( '__construct' != $strFunc && '__destruct' != $strFunc && !isset( $this->objCtrls->$strCtrl->actions [$strFunc] ) )
{
//
$recCtrlAction = array (
'addtime' => TimeUtils::getFullTime(),
'modtime' => TimeUtils::getFullTime(),
'delsign' => MallEnum::DEL_SIGN_NO,
'mid' => 1,
'controller' => $strCtrl,
'action' => $strFunc,
'minutes' => 0 );
$this->db->insert( TableNames::CHEWU_CACHE_TIME_MGR, $recCtrlAction );
}
}
}
if( is_dir( $file_location ) && $file != "." && $file != ".." )
{ //判断是不是文件夹
$this->_load_ctrls_into_db( $file_location ); //继续遍历
}
}
}
加载ctrl action信息到memcache
private function _loadCtrls( )
{
$this->objCtrls = new stdClass();
$query = $this->db->get_where( TableNames::CHEWU_CACHE_TIME_MGR, array (
'delsign' => MallEnum::DEL_SIGN_NO ) );
$arrRes = $query->result();
foreach( $arrRes as $row)
{
if( !isset( $this->objCtrls->{$row->controller} ) )
{
$this->objCtrls->{$row->controller} = new stdClass();
}
$this->objCtrls->{ $row->controller }->actions [$row->action] = $row;
}
}
/**
* 加载到内存
*/
public function loadStaticMgrInfoIntoMem( )
{
$this->_loadCtrls();
$this->memcacheutils->set( 'ctrlsInfo', $this->objCtrls, 0 );
$this->memcacheutils->set( 'bCtrlInfo', 1, 0 );
foreach( $this->objCtrls as $ctrl => $actions)
{
if( isset( $actions->actions ) )
{
foreach( $actions->actions as $actname => $act)
{
$this->memcacheutils->set( MallEnum::CTRL_ACTION . $act->controller . $act->action, $act->minutes, 0 );
}
}
}
echo 'ret=0';
}
之后可开发一管理端 对某些需要的action进行管理
这时使用静态化的访求如下
public function index( )
{
$this->output->cache( intval( $this->memcacheutils->get( MallEnum::CTRL_ACTION . __CLASS__ . __FUNCTION__ ) ));
$this->mallBiz->index();
}
为了方便管理这里要对CodeIgniter的框架进行一些修改如下(system/core/Output.php):
/**
* Write a Cache File
*
* @access public
* @param string
* @return void
*/
function _write_cache($output)
{
$CI =& get_instance();
$path = $CI->config->item('cache_path');
$cache_path = ($path == '') ? APPPATH.'cache/' : $path;
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//以上为方便管理cache所做的修改
$Rtr = $GLOBALS[ 'RTR' ];
$cache_path .= $Rtr->fetch_class() . $Rtr->fetch_method() . '/';
if( !is_dir( $cache_path ) )
{
mkdir( $cache_path );
}
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
if ( ! is_dir($cache_path) OR ! is_really_writable($cache_path))
{
log_message('error', "Unable to write cache file: ".$cache_path);
return;
}
$uri = $CI->config->item('base_url').
$CI->config->item('index_page').
$CI->uri->uri_string();
$cache_path .= md5($uri);
if ( ! $fp = @fopen($cache_path, FOPEN_WRITE_CREATE_DESTRUCTIVE))
{
log_message('error', "Unable to write cache file: ".$cache_path);
return;
}
$expire = time() + ($this->cache_expiration * 60);
if (flock($fp, LOCK_EX))
{
fwrite($fp, $expire.'TS--->'.$output);
flock($fp, LOCK_UN);
}
else
{
log_message('error', "Unable to secure a file lock for file at: ".$cache_path);
return;
}
fclose($fp);
@chmod($cache_path, FILE_WRITE_MODE);
log_message('debug', "Cache file written: ".$cache_path);
}
/**
* Update/serve a cached file
*
* @access public
* @param object config class
* @param object uri class
* @return void
*/
function _display_cache(&$CFG, &$URI)
{
$cache_path = ($CFG->item('cache_path') == '') ? APPPATH.'cache/' : $CFG->item('cache_path');
// Build the file path. The file name is an MD5 hash of the full URI
$uri = $CFG->item('base_url').
$CFG->item('index_page').
$URI->uri_string;
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//此为方便管理cache而做的修改
$Rtr = $GLOBALS[ 'RTR' ];
$cache_path .= $Rtr->fetch_class() . $Rtr->fetch_method() . '/';
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
$filepath = $cache_path . md5($uri);
if ( ! @file_exists($filepath))
{
return FALSE;
}
if ( ! $fp = @fopen($filepath, FOPEN_READ))
{
return FALSE;
}
flock($fp, LOCK_SH);
$cache = '';
if (filesize($filepath) > 0)
{
$cache = fread($fp, filesize($filepath));
}
flock($fp, LOCK_UN);
fclose($fp);
// Strip out the embedded timestamp
if ( ! preg_match("/(\d+TS--->)/", $cache, $match))
{
return FALSE;
}
// Has the file expired? If so we'll delete it.
if (time() >= trim(str_replace('TS--->', '', $match['1'])))
{
if (is_really_writable($cache_path))
{
@unlink($filepath);
log_message('debug', "Cache file has expired. File deleted");
return FALSE;
}
}
// Display the cache
$this->_display(str_replace($match['0'], '', $cache));
log_message('debug', "Cache file is current. Sending it to browser.");
return TRUE;
}
}
经以上修改后生成的cache不再是以前的只有md5 hash后的文件名 而是每个ctrlaction放在同一个文件夹里这样可以方便cache的管理(比如删除等)
缓存清理方法如下
//ajax方法
public function clearStaticCache()
{
$strCtrl = trim( $this->uri->segment( 4 ));
$strAct = trim( $this->uri->segment( 5 ));
if( $strCtrl === false || $strCtrl == '' ||
$strAct === false || $strAct == '' )
{
show_404();
}
$strPath = $this->config->item( 'cache_path' ) . $strCtrl .$strAct;
if( file_exists( $strPath ) )
{
$this->load->helper( 'file' );
delete_files( $strPath, true );
rmdir( $strPath );
}
echo 'ret=0';
}
经过以上CodeIgniter的可行宜用的静态缓存系统已经建立完毕
CodeIgniter网站静态化管理系统的更多相关文章
- 关于大型网站技术演进的思考(二十一)--网站静态化处理—web前端优化—下【终篇】(13)
本篇继续web前端优化的讨论,开始我先讲个我所知道的一个故事,有家大型的企业顺应时代发展的潮流开始投身于互联网行业了,它们为此专门设立了一个事业部,不过该企业把这个事业部里的人事成本,系统运维成本特别 ...
- 关于大型网站技术演进的思考(十九)--网站静态化处理—web前端优化—上(11)
网站静态化处理这个系列马上就要结束了,今天我要讲讲本系列最后一个重要的主题web前端优化.在开始谈论本主题之前,我想问大家一个问题,网站静态化处理技术到底是应该归属于web服务端的技术范畴还是应该归属 ...
- 关于大型网站技术演进的思考(十三)--网站静态化处理—CSI(5)
讲完了SSI,ESI,下面就要讲讲CSI了 ,CSI是浏览器端的动静整合方案,当我文章发表后有朋友就问我,CSI技术是不是就是通过ajax来加载数据啊,我当时的回答只是说你的理解有点片面,那么到底什么 ...
- 网站静态化处理—web前端优化—下【终篇】(13)
网站静态化处理—web前端优化—下[终篇](13) 本篇继续web前端优化的讨论,开始我先讲个我所知道的一个故事,有家大型的企业顺应时代发展的潮流开始投身于互联网行业了,它们为此专门设立了一个事业部, ...
- 网站静态化处理—web前端优化—中(12)
网站静态化处理—web前端优化—中(12) Web前端很多优化原则都是从如何提升网络通讯效率的角度提出的,但是这些原则使用的时候还是有很多陷阱在里面,如果我们不能深入理解这些优化原则背后所隐藏的技术原 ...
- 网站静态化处理—web前端优化—上
网站静态化处理—web前端优化—上(11) 网站静态化处理这个系列马上就要结束了,今天我要讲讲本系列最后一个重要的主题web前端优化.在开始谈论本主题之前,我想问大家一个问题,网站静态化处理技术到底是 ...
- 网站静态化处理—CSI(5)
网站静态化处理—CSI(5) 讲完了SSI,ESI,下面就要讲讲CSI了 ,CSI是浏览器端的动静整合方案,当我文章发表后有朋友就问我,CSI技术是不是就是通过ajax来加载数据啊,我当时的回答只是说 ...
- 网站静态化处理—web前端优化—上(11)
网站静态化处理这个系列马上就要结束了,今天我要讲讲本系列最后一个重要的主题web前端优化.在开始谈论本主题之前,我想问大家一个问题,网站静态化处理技术到底是应该归属于web服务端的技术范畴还是应该归属 ...
- 思考ASP.NET网站静态化的利与弊
最近在思考网站要不要进行静态化的问题,在网上收集和整理了有关静态化利与弊的资料,于是写下此博文分享到网络上.由于本人是一名asp.net开发人员,所以本文的观点可能无法涉及到全部方面,但是比较注重于使 ...
随机推荐
- Revit 二次开发 沿弧形路径创建拉伸屋顶
沿弧形路径创建拉伸屋顶 Revit的API中只能按照直线创建拉伸屋顶,不能按照曲线创建拉伸屋顶.在Revit的界面当中,可以用 构建->内建模型,进行放样创建屋顶.但是没有办法代码内建模型. 可 ...
- FPGA中latency与delay概念的区别
2013-06-17 21:09:26 最近学习流水线以及状态机,总遇到注入加入寄存器可以分割组合逻辑,从而提高电路的运行频率的说法:还有流水线可以提高速度的说法,刚开始很是疑惑,觉得流水线的方法,输 ...
- java网络基本类使用(一)
1.怎么获取ip相关信息 import java.net.InetAddress; import java.net.NetworkInterface; import java.util.Enumera ...
- 关于web会话中的session过期时间的设置
关于web会话中的session过期时间的设置 1.操作系统: 步骤:开始——〉管理工具——〉Internet信息服务(IIS)管理器——〉网站——〉默认网站——〉右键“属性”——〉主目录——〉配置— ...
- 【HDOJ】4373 Mysterious For
1. 题目描述有两种不同类型的循环,并给出一个由1.2组成的序列,表示嵌套的循环类型.问这样组着的循环一共需要多少次循环?并将结果模364875103. 2.基本思路显然,每当遇到一个类型1的序列,即 ...
- 解决JDeveloper运行慢的设置/BPM/SOA Server JVM参数设定
最近在使用 Jdeveloper 10.1.3.3 版本时发现速度奇慢无比,后经Google,发现如下解决方案:在 jdev.conf 文件的末尾加上如下两行,速度即可得到显着的提高, jdev.co ...
- UVa 11040 (水题) Add bricks in the wall
题意: 45块石头如图排列,每块石头上的数等于下面支撑它的两数之和,求其余未表示的数. 分析: 首先来计算最下面一行的数,A71 = A81 + A82 = A91 + 2A92 + A93,变形得到 ...
- 用TIMESTAMP类型取代INT和DATETIME
时间在我们开发中应用非常普遍,大部分开发中我们将用Mysql的datetime格式来存储,但是对于经常用时间来排序或者查询的应用中,我们要将时间做成索引,这个就跟查询效率很有关系,但是很多程序员会用i ...
- 陈正冲老师对于c语言野指针的解释
那到底什么是野指针呢?怎么去理解这个“野”呢?我们先看别的两个关于“野”的词: 野孩子:没人要,没人管的孩子:行为动作不守规矩,调皮捣蛋的孩子.野狗:没有主人的狗,没有链子锁着的狗,喜欢四处咬人. 对 ...
- J2EE的若干问题
1.问题:jsp中out.println页面显示不出换行效果.例如: out.println("唱歌"); out.println("跳舞"); 以上代码的结果 ...