CodeIgniter钩子用法实例详解

本文实例讲述了CodeIgniter钩子用法。分享给大家供大家参考,具体如下:

CodeIgniter执行流程图中有7个椭圆的框,这表示在执行的过程中埋了7个钩子。那先来看看什么是钩子?

网上找到的两段文字:

钩子的完整实现应该叫事件驱动。事件驱动分为两个阶段,第一个阶段是注册事件,目的是给未来可能发生的“事件”起一个名字,简单的实现方法是用单例模式产生一个持久的对象或者注册一个全局变量,然后将事件名称,以及该事件对应的类与方法插入全局变量即可。也就是挂载一个钩子。

第二个阶段是触发事件,本质上就是在事件的全局变量中查询要触发的事件名称,然后找到注册好的类与方法,实例化并运行。这样子就可以摆脱传统方式中程序必须按顺序的规则,进一步实现解除耦合的目的。

钩子函数可以截获并处理其他应用程序的消息。每当特定的消息发出,在没有到达目的窗口前,钩子程序就先捕获该消息,亦即钩子函数先得到控制权。这时钩子函数即可以加工处理(改变)该消息,也可以不作处理而继续传递该消息,还可以强制结束消息的传递。

可以看到:

1、钩子函数是预设并在特定的条件下触发的。

2、钩子函数接管程序后可以影响到程序的走向。

CI预设钩子

CI中设定了7个钩子,钩子与钩子之间相对独立。前3个钩子是在实例化之前设定的,意味着无法使用get_instance实例,要使用已实例化的类需要global。7个钩子的作用手册上说的比较清楚了,可以重写缓存输出、可以对输出进行处理等。

如何触发CI钩子?

CI在配置文件中设置了钩子开关,要使用钩子首先得打开该开关,然后配置config/hook.php中的hook数组,比如设置post_controller_constructor钩子:

$hook['post_controller_constructor'] = array(
  'class'  => 'Hook',
  'function' => 'post_controller_constructor',
  'filename' => 'Hook.php',
  'filepath' => 'hooks',
  'params'  => array('beer', 'wine', 'snacks')
);

当控制器实例化之后,调用action之前就会触发去执行hooks目录下的Hook.php中的post_controller_constructor方法。我们可以在该方法中做一些处理。

钩子的应用

到目前为止还未体会到CI钩子的绝妙之处,查看网上有一些应用CI钩子来实现权限控制的程序,即在post_controller_constructor做权限判断,由于这个钩子就好比一个构造函数,在构造函数里判断接下来要执行的方法是否有权限,确实可行。但这个功能也完全可以放在MY_Controller中去实现,甚至会更好。因为CI的钩子是全局的,不管是前台还是后台都会启动该钩子,虽然说这个钩子程序可以做判断,但这里判断不一定是最好的。前面提到过MY_Controller中不同模块公用控制器分开,前台后台继承不同的控制器,如果我只需要对后台进行权限控制,完全可以直接在后台公用控制器中来实现,不影响到前台,只对需要的部分做控制。

这里有个非CI中的例子,思维是一样的。合作渠道的用户登录注册功能,有很多的合作方,不同的合作方需要注册的基本资料相同,但每个合作方可能会有一些特殊的字段或者不同的校验方式。

很多时候碰到问题我们都可以放到日常生活中来看。以注册处理逻辑为例,可以看看其中有个流程是不变的。接受参数->注册资料之前处理->注册->注册资料之后处理。变化的是什么?每一步都可能变化,但流程不变化。所以可以对前、后、处理等相关地方设置钩子,把处理的逻辑分发到特定的情况下去,下面有个参考图,具体的如何设置钩子还需要根据项目来:

事实也证明这种方式是可行的,合作方虽然很多,但是也可以分组,上百个注册页面很容易就实现了。所以利用钩子处理这种流程不变,而中间的某个步骤变化多端的需求是很方便的。

简单点说, 钩子就是特定条件下执行一段程序;再简单点,钩子就是实现解除if判断的一种方式。

过多的if判断会导致程序难以阅读和维护,而通过钩子的处理可以让程序更灵活。钩子有一定的触发条件,条件可以是配置、从数据库读取,或者通过一些技术来实现,比如反射等,使用钩子可以达到解耦的目的。

更多关于CodeIgniter相关内容感兴趣的读者可查看本站专题:《codeigniter入门教程》和《CI(CodeIgniter)框架进阶教程》

希望本文所述对大家基于CodeIgniter框架的PHP程序设计有所帮助。

(0)

相关推荐

  • CodeIgniter针对数据库的连接、配置及使用方法

    本文实例讲述了CodeIgniter针对数据库的连接.配置及使用方法.分享给大家供大家参考,具体如下: 1. 数据库: create database test; create table users( id int not null, name varchar(10), pwd varchar(10), email varchar(20) ) insert into users values(1,'shunping','shunping','aa@163.com'); insert into

  • CodeIgniter辅助之第三方类库third_party用法分析

    本文实例分析了CodeIgniter辅助之第三方类库third_party用法.分享给大家供大家参考,具体如下: third_party用来存放系统中引入的第三方类库,类库通常提供的功能比较丰富,相应的学习成本也要高些,系统中能用到功能有限,所以建议在引入类库时进行适当的封装,让系统中更方便使用,其他人使用时只需关注扩展的方法而无法关注具体的实现.以CI集成Twig模版为例吧. 首先需要下载Twig类库,并放在third_party中,然后在libraries中进行一次封装,示例如下: <?ph

  • CodeIgniter基于Email类发邮件的方法

    本文实例讲述了CodeIgniter基于Email类发邮件的方法.分享给大家供大家参考,具体如下: CodeIgniter拥有功能强大的Email类.以下为利用其发送邮件的代码. 关于CI的Email类的详情请参考:http://codeigniter.org.cn/user_guide/libraries/email.html 文件路径为/application/controllers/welcome.php <?php if ( ! defined('BASEPATH')) exit('No

  • CodeIgniter表单验证方法实例详解

    本文实例讲述了CodeIgniter表单验证方法.分享给大家供大家参考,具体如下: 1.在D:\CodeIgniter\system\application\views目录下写一个视图文件myform.php <html> <head> <title>My Form</title> </head> <body> <?php echo $this->validation->error_string;?> <

  • CodeIgniter自定义控制器MY_Controller用法分析

    本文实例讲述了CodeIgniter自定义控制器MY_Controller用法.分享给大家供大家参考,具体如下: Codeigniter所有的控制器都必须继承CI_Controller类,但CI_Controller类位于system目录下,不太方便修改.为方便做一些公用的处理,通常情况下我们会在core下创建MY_Controller,用来继承CI_Controller,从而项目中所有的控制器继承MY_Controller. 那么,MY_Controller 通常会做些什么呢? 所有的控制器都

  • Codeigniter中集成smarty和adodb的方法

    本文实例讲述了Codeigniter中集成smarty和adodb的方法.分享给大家供大家参考,具体如下: 在CodeIgniter中要写自己的库,就需要写两个文件,一个是在application/init下面的init_myclass.php文件(如果没有init目录,自己创建).另外一个就是在application/libraries目录下创建myclass.php文件. 这里myclass是你的类名.一些规则大家看手册就好了,我这里直接就说步骤了. 1)在application/libra

  • CodeIgniter连贯操作的底层原理分析

    本文分析了CodeIgniter连贯操作的底层原理.分享给大家供大家参考,具体如下: php oop连贯操作原理 ->符号其实是传递对象指针的.或许这么说是不对的. 但是,我们可以这么的理解. 不多说.放代码. 普通用法: <?php class test { public $a=''; public $b=''; public function actiona() { $this->a="hello"; return $this; } public function

  • CodeIgniter多语言实现方法详解

    本文实例分析了CodeIgniter多语言实现方法.分享给大家供大家参考,具体如下: CI应用目录下有一个language语言包目录,用来配置多种不同的语言.语言的配置位于config文件中,配置格式如下: 复制代码 代码如下: $config['language'] = 'english'; 定义语言文件 language下有个空的english目录,即上面定义的系统默认语言目录,系统会从该目录加载语言包文件.如果要定义不同的语言包,如zh_cn,则创建zh_cn目录并配置相应语言包文件即可.

  • CodeIgniter配置之autoload.php自动加载用法分析

    本文实例分析了CodeIgniter配置之autoload.php自动加载用法.分享给大家供大家参考,具体如下: CodeIgniter带了自动加载的功能,可以全局加载类库.模型.配置.语言包等,对于需要全局使用的功能相当方便. 例如:有个全局函数写在app_helper.php中,需要全局加载这个函数,只需设置autoload.php: 复制代码 代码如下: $autoload['helper'] = array('app'); 接下来,所有的地方都可以使用了,配置.模型等配置相似.但方便的同

  • CodeIgniter记录错误日志的方法全面总结

    本文实例讲述了CodeIgniter记录错误日志的方法.分享给大家供大家参考,具体如下: CI工作流程: 所有的入口都从根目录下的index.php进入,确定应用所在目录后,加载 codeigniter/CodeIgniter.php 文件,该文件会顺序加载以下文件执行整个流程. index.php:检测文件路径,加载codeigniter.php文件 codeigniter.php: 加载 Common/constants....文件.获取文件模式.设置计时器.实例化类(错误类.扩展类.钩子类

  • CodeIgniter生成静态页的方法

    本文实例讲述了CodeIgniter生成静态页的方法.分享给大家供大家参考,具体如下: 现在我们来开发如何让CI框架生成静态页面.下面直接帖代码: $this->output->get_output(); 使用这个方法,你可以可以得到将要输出的数据,并把它保存起来,留着它用(我们做新闻类型网站的时候,常常需要生成静态的HTML文件). $string = $this->output->get_output(); $this->load->helper('file');

  • CodeIgniter分页类pagination使用方法示例

    本文实例讲述了CodeIgniter分页类pagination使用方法.分享给大家供大家参考,具体如下: controller控制器(application/controller/page.php文件): public function index() { $this->load->model ( 'home_model' , '' , TRUE); $config= array(); $config['per_page'] = $this->per_page; //每页显示的数据数 $

  • CodeIgniter常用知识点小结

    本文简单总结了CodeIgniter开发中的常用知识点.分享给大家供大家参考,具体如下: 跳转: $this->load->helper('url'); redirect(); 常量定义: config/constants.php 关于语言文件: 只说我自己的做法 为了统一管理错误信息 决定做一个error_lang.php 在application/language下新建文件夹chinese 新建文件 error_lang.php 在config.php里: $config['languag

随机推荐