Joomla!+Nginx+Memcached让网站飞的更快

时间:2021-08-31 11:32:21

Joomla!系统以建站的简单方便,获得了大众的喜爱,但是,他“太完美”的内部架构,也带来了执行效率的损失,特别是作为一个大部分内容都为静态的资讯站点,访问每个资讯页让Joomla!每次都“完美”的表演一次,无疑是对效率最大的浪费。
对于这个自身的性能缺陷,缓存作为一种解决方案,Joomla!本身已经支持。但是对于追求完美的PHPer来说,应该绝不满足这个,而且在访问上一定规模量的应用场景中,可能Joomla!自身的“缓存绝技”也不能应付。
怎么办呢?让我们从每次对Joomla!访问的细节来着手分析。首先,用户访问一个页面,www服务器接受请求,启动PHP解析器,解析器开始解析PHP程序,进入Joomla!程序入口点,Joomla!缓冲机制开始启动,如果已经访问过的且Joomla!本身缓存的,Joomla!就不再继续向下执行,直接从缓存里提取结果返回www服务器。
大家可能有了些想法?让我们来验证下,大家是这样想的吗?
每次访问Joomla!系统后,系统直接把执行结果放到一个www能访问到的缓存里,下一次访问,就直接让www服务器判断,已经有缓存的话,绕开PHP解析器,直接给用户输出结果。太棒了,意识到没,这样做直接连PHP程序执行都绕过了,更不要说Joomla!,而且这套方案很透明,不需要我们对原有Joomla!系统作修改,需要的仅仅只是花费10分钟,开发一个Joomla!插件。
接下来,首先介绍www服务器Nginx加缓存的配置,缓存选用当下最流行的Memcache.
然后,简单介绍插件的逻辑和关键代码,至于插件写法不再罗嗦,插件入门请看《Joomla!建站步步通》插件章节。
Nginx+Memcache配置
Nginx的具体安装配置请参看Nginx的文档。这里篇幅有限,只讲解Nginx和Memcache配置的关键点。
首先Nginx源码包安装,配置如下。
然后:make & make install
按Nginx文档配置好Nginx,然后选用vhost方式配置我们的虚机。

接下来,要仔细看好了,假设域名叫abc.com,虚机配置文件叫www.abc.conf,配置文件如下:
接下来,先介绍Joomla!里是如何继续运行,然后,简单介绍Joomla!插件的逻辑和关键代码。
Nginx无缓存的请求被直接传给PHP应用服务器,PHP应用服务器从Joomla!入口点进入,开始Joomla!“完美的表演”。
Joomla!经过若干层的调用执行后,形成该页面,这时候,Joomla!调用插件将内容以“URL=>内容”的键值方式插入Memcache。下面对插件关键代码进行分析:
server {
listen 80;
server_name www.abc.com;
......................... #省略次要的配置
# pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
location ~ /.php$ {
if ($request_method = POST) { #POST过来的一般是动态需求,所以直接不判断缓存,直接扔给php应用服务器
proxy_pass http://dynamic_srv; #主配置里定义的php应用服务器地址, upstream dynamic_srv { server 127.0.0.1:9000; }
break;
}
include fastcgi_params;
set $memcached_key http://$host$request_uri; #关键点 : 看是否有形如 abc.com/xxxxx的连接在memcache里,有的话就直接输出呢
memcached_pass localhost:11211; #关键点 :无缓存,扔给php应用服务器地址接招继续执行
fastcgi_intercept_errors on;
default_type text/html;
error_page 404 405 502 504 = @fastcgi;
}
}
//插件入门请参看<<Joomla!建站步步通>>第六章
function onAfterRender(){ //在Joomla!生成内容后的事件里进行处理
global $mainframe,$_SERVER;
if($mainframe->isAdmin() || JDEBUG) {//后台不需要缓存
return;
}
$uri="http://".$_SERVER['HTTP_HOST'].JRequest::getURI();//对应url
if($this->_isCache) { //开启了插件缓存选项
$data = JResponse::getBody(); //得到要缓存的内容
$this->setKey($uri,$data); //设置到memcache里,哈哈,很简单的一句话,Joomla!功能强大吧
}
}
《草根》第 2 期 技术营地

当然,上边的解决方案在一般情况下已经可以很不错的解决一个中小型网站的负载,但是如果该网站还有一些不能缓存的东西,比如收费区等,就要对该方案进行仔细琢磨了。