1.index.php :入口文件--define('environment') 主要用于设置errors日志输出级别--$system_path 设置系统路径--设置basepath、fcpath、sysdir、apppath等 |设置路径信息变量,为加载相应文件信息准备--require_once basepath.core/codeigniter.php | 最后
1.index.php :入口文件|-->define('environment') |主要用于设置errors日志输出级别|-->$system_path |设置系统路径|-->设置basepath、fcpath、sysdir、apppath等 |设置路径信息变量,为加载相应文件信息准备|-->require_once basepath.core/codeigniter.php | 最后加载codeigniter.php作为总控制器2.codeigniter.php加载过程,主要用于加载core核心目录下相应文件|-->require(basepath.'core/common.php'); |加载core目录下的common文件,见2.1解析|-->require(apppath.'config/'.environment.'/constants.php'); |加载constants目录,与开发环境无关时直接使用config目录下的constants目录|-->get_config(array('subclass_prefix' => $assign_to_config['subclass_prefix'])); |设置子文件,扩展类的前缀|-->$bm =& load_class('benchmark', 'core'); |加载benchmark类,mark记录当前的时间|-->$ext =& load_class('hooks', 'core'); |加载core目录下的hooks钩子类|-->$ext->_call_hook('pre_system'); |调用_call_hook(pre_system),根据pre_system内部调用_run_hook执行钩子,在系统开始正式工作前作预处理|-->$cfg =& load_class('config', 'core'); |继续执行core下的config配置文件,|-->$cfg->_assign_to_config($assign_to_config); |-->|$this->set_item($key, $val); |解析指定给config的配置文件,实质为对config[]赋值|-->$uni =& load_class('utf8', 'core'); |加载了utf-8编码类,ci_utf8|-->$uri =& load_class('uri', 'core'); |加载core目录的uri类,ci_uri|-->$rtr =& load_class('router', 'core'); |设置route路由及覆盖信息,见2.2解析|-->_set_routing()|-->_set_overrides()|-->$out =& load_class('output', 'core'); |实例化输出类,加载core目录下的output文件|-->$out->_display_cache($cfg, $uri) |判断是否存在页面缓存,是则输出文件|-->$sec =& load_class('security', 'core'); |加载core目录下的安全处理文件|-->$in =& load_class('input', 'core'); |实例化输入类,加载core目录下的input文件|-->$lang =& load_class('lang', 'core'); |加载语言类|-->require basepath.'core/controller.php'; |加载基本控制器类,见2.3解析|-->require apppath.'core/'.$cfg->config['subclass_prefix'].'controller.php'; |尝试加载扩展的自定义子类控制器|-->include(apppath.'controllers/'.$rtr->fetch_directory().$rtr->fetch_class().'.php'); |加载自定义控制器下的控制器类|-->$bm->mark('loading_time:_base_classes_end'); |设定一个benchmark测试点|-->$class = $rtr->fetch_class(); |分别获取uri地址的控制器类名和方法名|-->$method = $rtr->fetch_method();|-->if ( ! class_exists($class) |判断方法及类是否合理or strncmp($method, '_', 1) == 0or in_array(strtolower($method), array_map('strtolower', get_class_methods('ci_controller'))))|-->$ext->_call_hook('pre_controller'); |处理器执行前进行预处理,并做benchmark设置|-->$ci = new $class(); |获取执行的控制器实例,实例化构造器|-->$ext->_call_hook('post_controller_constructor'); |实例化控制器类后的钩子处理|-->if (method_exists($ci, '_remap'))|-->$ci->_remap($method, array_slice($uri->rsegments, 2)) |如果控制器存在_remap()方法,则执行, 判断条件$ci为控制器类 |-->else |判断方法在类当中的存在似,如果不存在,则设置|-->call_user_func_array(array(&$ci, $method), array_slice($uri->rsegments, 2)); |最终传递参数供调用控制类方法|-->$bm->mark('controller_execution_time_( '.$class.' / '.$method.' )_end'); |benchmark标记时间结束点|-->$ext->_call_hook('post_controller'); |控制器生存周期,在控制器执行完成后执行后续操作|-->$out->_display(); |输出页面进行展示|-->$ext->_call_hook('post_system'); |请求生存周期完成后的终结操作|-->$ci->db->close(); |自动关闭数据库资源2.1 core/common.php加载|-->function is_php($version) |用于比较版本号的函数|-->function is_really_writable($file) |用于判断是否可以写文件,在不同的系统中可靠程度不同, w中通过判断is_readonly,u中如果safe_mode为开则不确定性|-->function load_class($class, $directory = 'libraries', $prefix = 'ci_') |用于加载目录下的php文件的class类|-->foreach (array(apppath, basepath) as $path) |分别在application和system目录下轮循|-->file_exists($path.$directory.'/'.$class.'.php' |找到对应的php文件|-->require($path.$directory.'/'.$class.'.php'); |require加载对应的php文件内的类,加了前缀,此处可扩展|-->break; |如正确加载则退出,否则继续尝试加载文件|-->file_exists(apppath.$directory.'/'.config_item('subclass_prefix').$class.'.php') |自扩展的class类,如my_test|-->if ($name === false) |如果$name不存在,则exit()退出 ,(在自定义类加载时,此处可作为扩展点,增加边际条件)|-->is_loaded($class); |确类已经加载|-->$_classes[$class] = new $name(); |加载至静态的classes数祖中,用于缓存,调用时首先从classes中获取|-->function is_loaded($class = '') |-->设置$_is_loaded数祖,参数$class不为空,判断是否存在gf $_is_loaded,否则设置|-->function &get_config($replace = array())|用于获取config的实例化文件|-->static $_config; |定义config类型|-->$file_path = apppath.'config/config.php'; |确定application目录路径下定义的config.php的路径|-->require($file_path); |加载application/config/config.php类|-->count($replace) > 0 |对于config.php中定义的变量,如果有replace,则逐个替代|-->foreach ($replace as $key => $val)|-->$config[$key] = $val;|-->return $_config[0] =& $config; |最后返回定义的config的结果集|-->function config_item($item) |配置选项,从config的数祖对象中返还特殊的配置项|-->$config =& get_config();|-->$_config_item[$item] = $config[$item];|-->function show_error |用于错误信息输出|-->$_error =& load_class('exceptions', 'core'); |加载exceptions类|-->echo $_error->show_error($heading, $message, 'error_general', $status_code); |直接输出错误|-->function show_404 |用于输出404页面,输出的错误信息页面可配置|-->function log_message |用于写日志信息|-->$_log =& load_class('log');|-->$_log->write_log($level, $message, $php_error);|-->function set_status_header |用于输出状态的heade信息|-->function _exception_handler|-->function remove_invisible_characters|-->function html_escape |过滤html变量|-->return htmlspecialchars($var, ent_quotes, config_item('charset'));2.2router路由信息设置|-->_set_routing() |-->$segments = array() |根据目录,控制器,函数的触发器设定segment[]的uri段值,分别fetch()方法去取对象值|-->include(apppath.'config/routes.php'); |加载config下的routes文件|-->$this->routes |设置routes数祖值,从config的route中获取|-->$this->default_controller |设置routes的控制器值,从config的route中获取|-->return $this->_validate_request($segments); |验证uri的segment合法性|-->$this->uri->_remove_url_suffix();$this->uri->_reindex_segments(); |进一步清理解析uri,使segment从1开始x|-->_set_overrides() |根据$routing的值,重新设定directory、controller、function参数|-->$this->set_directory($routing['directory']);|-->$this->set_class($routing['controller']);|-->$this->set_method($routing['function']);2.3 core/controller.php加载|-->__construct() |构造函数|-->self::$instance =& $this; |-->foreach (is_loaded() as $var => $class) |根据is_loaded()的信息加载相应的类|-->$this->$var =& load_class($class); |-->$this->load =& load_class('loader', 'core'); |加载core/loader的php文件|-->$this->load->initialize(); |主要用于autoload加载信息,如libraries、database等等|-->function &get_instance |返回当前实例|-->return self::$instance扩展点:php自动加载机制在codeigniter中的应用1.php自动加载机制:php5后,提供了类的自动加载机制,即类在加载时才被使用,即lazy loading,共有二种方式1.1: __autoload()通过扩展可实现,实质为设定规则加载相应路径的php文件(require、include方式)1.2: 将autoload_func指向php文件,这个一般用c语言扩展实现 详见:http://blog.csdn.net/flyingpig4/article/details/72864382.在codeigniter中的应用根据上述源码分析可知:codeigniter中所有的操作都是以controller为起始,只需在cotroller加载的过程中,使__autoload()函数自动加载即可,目前的加载方式为在application/config/config.php中设置__autoload()函数 原文地址:php codeigniter框架源码解析, 感谢原作者分享。