Joomla主进程分析纪要

Joomla的框架有许多可借鉴的编程思路,为自己更好的理解它,对主进程(index.php)的处理过程进行分析。(也是需要什么分析什么,因此,会一步一步完善这篇纪要)
(index.php)
<?php

// Set flag that this is a parent file
define( '_JEXEC', 1 );//定义执行中的参数

define('JPATH_BASE', dirname(__FILE__) );//定义系统的基本路径,__FILE__应该是PHP的全局参数(TBD

define( 'DS', DIRECTORY_SEPARATOR );//定义系统分割符,DIRECTORY_SEPARATOR是怎么来的,我还没有深入研究过(TBD

require_once ( JPATH_BASE .DS.'includes'.DS.'defines.php' );//在这里定义了Joomla运行中的很多常量,比如JPATH_ADMINISTRATOR什么的
require_once ( JPATH_BASE .DS.'includes'.DS.'framework.php' );//这是执行主程序之前的相关设置,包括判断是否要进行安装,载入配置文件configuration.php,导入基础库文件(详见另文)

JDEBUG ? $_PROFILER->mark( 'afterLoad' ) : null;//当设置进行Debug时,执行(另分析)

$mainframe =& JFactory::getApplication('site');//创建一个JSite的实例

// set the language
$mainframe->initialise();//调用JSite的函数,设置系统的默认语言

JPluginHelper::importPlugin('system');//导入系统的插件

// trigger the onAfterInitialise events
JDEBUG ? $_PROFILER->mark('afterInitialise') : null;//TBD
$mainframe->triggerEvent('onAfterInitialise');//触发了一个事件,具体实现需要用户自定义相关的处理函数,实际上,这就是Joomla插件的功能,通过插件来响应各种事件。

$mainframe->route();//这里对程序执行哪个组件进行了判断和设置。如果没有设置option(即要求执行的组件),系统会去找菜单的默认菜单项,调用这个菜单项执行。比如http://www.foo.com或www.foo.com/index.php都会触发去找这个默认菜单项,假设默认菜单项定义的组件是com_content,则option这个时候会被设置为com_content,以供下面调用
 
//这里的route函数调用的JSite重载以后的函数,仔细研究这个函数,会发现根据前面生成的不同类型应用(Administrator,Site,Installation),系统会选择不同的JRouter类别
 
//菜单项激活和Itemid的应用问题
在生成的菜单项的链接中,有一个Itemid,实际上是菜单项的数据表ID,这个值的作用之一,是设置当前被激活的菜单项,以便后续使用(比如生成breadcrumbs时,能够确定当前的菜单项)
记录过程是在($mainframe->route())时发生的,Joomla在这里主要是对提交处理的uri进行分析,分析过程中记录Itemid为活动的菜单项。

// authorization
$Itemid = JRequest::getInt( 'Itemid');//TBD,从提交的URL中得到菜单项的ID号
$mainframe->authorize($Itemid);//TBD,这里是通过一个JUser的“aid”变量进行验证,但这个变量是如何被赋值,在哪里被赋值,不知道?

// trigger the onAfterRoute events
JDEBUG ? $_PROFILER->mark('afterRoute') : null;//TBD
$mainframe->triggerEvent('onAfterRoute');//事件处理,由插件响应

$option = JRequest::getCmd('option');//获得要求执行的组件,如果客户端没有提供,则由前面的route函数提供一个默认值
$mainframe->dispatch($option);//调用该组件,在这里输出的HTML文件被赋值,注意:component的执行和渲染是在这里执行,因此后续的模版载入已经不能影响component的执行效果

// trigger the onAfterDispatch events
JDEBUG ? $_PROFILER->mark('afterDispatch') : null;//TBD
$mainframe->triggerEvent('onAfterDispatch');//事件处理,由插件响应

 
$mainframe->render();//渲染框架,实际上是显示,这个时候,将调用模板(template),如果需要根据不同的组件显示不同的模板,那么在模板中的index.php中进行设置即可
 
这是一个比较复杂的部分,系统分成两个部分:Header和Body,Joomla的输出实际上是调用JResponse的SetHeader和SetBody函数,其中setheader基本上是在JApplication基类中实现,而后者却需要具体的JSite来完成。
 
在SetBody部分,根据输出的内容不同,会调用不同的JDocument,一般情况下是JDocumentHTML,通过这个类的render函数输出需要显示的内容$data,然后SetBody($body)。
 
特别的,JDocumentHTML的render又调用其_parseTemplate函数,将模版文件中的jdoc:include全部替换为相应的module或component(component的渲染结果在前面的dispatch过程中已经被载入到DocomentHTML中),并执行各自的render函数,输出真实的模块(很有趣的部分)
 
//这里还没有真输出,通过JResponse::setBody($data)把内容放到全局变量中

// trigger the onAfterRender events
JDEBUG ? $_PROFILER->mark('afterRender') : null;//TBD
$mainframe->triggerEvent('onAfterRender');//事件处理,由插件响应

 
echo JResponse::toString($mainframe->getCfg('gzip'));//输出前面准备这么久的结果,真是不容易啊,实际上toString做了以下几件事:
//首先通过$data = JResponse::getBody();得到应该输出的页面
//然后判断是否要压缩,如果要压缩,则压缩
//第三步,处理缓存什么的TBD
//第四步,输出Head,JResponse::sendHeaders();
//最后,返回一个字符串,让主程序输出(echo)

posted on 2009-12-18 12:40  14的路  阅读(1466)  评论(0编辑  收藏  举报

导航

友情链接:源码下载