经典教程翻译系列: 插件的设计

这一章主要讲插件的实际和使用.

 

对插件的剖析

 

插件是提供某些方法的组件.这些方法供当前事件上下文(eventContext)(类型为MachII.framework.EventContext的对象)在请求的生命周期的不同点调用:

1.          preProcess() – 在每个请求的开始被调用:eventContext将当前事件放入事件队列,getCurrentEvent() 不会返回这个事件(见处理请求里的第一个事件一节).

2.        preEvent() – 在执行相关事件句柄标签前立即调用各个事件:eventContext包含当前事件(那个将被触发的事件).

3.        preView() – 在执行相关页面标签前立即调用各个页面:eventContext包含当前页面(那个将被触发的页面).

4.        postView() -  在执行相关页面标签后立即调用各个页面:eventContext包含当前页面(那个执行完毕的页面).

5.        postEvent() - 在执行相关事件句柄标签后立即调用各个事件:eventContext包含当前事件(那个执行完毕的事件).

6.        postProcess() - 在每个请求的结束被调用:eventContext将不再包含当前事件.

7.        handleException() – 在异常被抛回框架时调用: eventContext包含当前事件(如果有的话).这个插件方法同样传递给异常对象(类型为MachII.util.Exception).

 

插件在需要的时候可以定义configure()方法来实现初始化这将被框架自动调用.Mach-II框架的其他部件一样,插件也被储存在application,所以它们的实例变量是有效的application域变量.

 

最简单的插件像这样子: 
    
    
<cfcomponent extends="MachII.framework.Plugin">
   
   
          <cffunction name="configure" returntype="void" access="public" output="false">
   
   
                    <!--- perform any initialization --->
   
   
          </cffunction>
   
   
          <cffunction name="preEvent" returntype="void" access="public" output="false">
   
   
                    <cfargument name="eventContext" type="MachII.framework.EventContext" required="yes" />
   
   
                    <!--- perform processing prior to every event being handled --->
   
   
          </cffunction>
   
   
</cfcomponent>
   
   

 

这个插件重写了preEvent()方法,其实它可以重写以上七种方法的任何一种.

插件被声明在mach-ii.xml <plugins> .. </plugins>标签里:

          <plugin name="pluginName" type="Path.To.YourPlugin" />
   
   

你也可以为插件定义变量:

<plugin name="pluginName" type="Path.To.YourPlugin">
   
   
          <parameters>
   
   
                    <parameter name="param1" value="value1" />
   
   
                    <parameter name="param2" value="value2" />
   
   
          </parameters>
   
   
</plugin>
   
   

 

这样可以为param1 param2 提供默认参数(分别是value1 value2).

 

handleException()插件指针

 

你可以使用异常事件或者单一的事件句柄来触发异常.对于很多程序而言,这是是可以完全可行的.你也可以通过在插件上实现handleException()方法的方式,添加自定义异常.这个插件指针是在框架遭遇异常之后,通告和触发异常事件之前,被执行.在执行这个插件指针之后,事件队列将被清除,特定的异常事件(定义在mach-ii.xml<properties>部分)被通告和触发.

 

不可以在handleException()中抛出异常或使用abortEvent()—这两种操作会导致未被触发的异常,并显示给终端用户.不可以通告新的事件(因为事件队列在handleException()被执行后已经被清除).你可以可以添加信息给当前事件对象,它们以后可以被异常事件句柄接收到.

<cfif arguments.eventContext.hasCurrentEvent()>
   
   
          <cfset arguments.eventContext.getCurrentEvent().setArg("argName",argValue) />
   
   
</cfif>
   
   

在遭遇异常的时候,这样做可以设置事件变量argName值为argValue,如果有一个事件被定义的话.

 

在异常事件句柄内部,当前事件是带有以下变量的异常事件本身:

  • exception - MachII.util.Exception对象,包含了原始异常的详细信息;
  • exceptionEvent - MachII.framework.Event对象,在异常抛出时被触发(这仅出现在异常发生时存在被定义的事件的情况下).

 

你可以在事件句柄里使用<event-mapping>来对异常事件提供更精细的操作.

 

处理请求里的第一个事件

因为当前事件没有在preProess()执行阶段被调用,不容易看出如何在每个请求里处理第一个事件 :

cffunction name="preProcess" returntype="void">
          <cfargument name="eventContext" type="MachII.framework.EventContext" />
          <!--- peek at the first event in the queue: --->
          <cfset var firstEvent = arguments.eventContext.getNextEvent() />
          <!--- ...process firstEvent here... --->
   
   
</cffunction>
   
   

注意:1.0.9 之前,以上对getNextEvent()的调用会从队列里清除第一个事件!

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值