2013-04-08 72 views
5

在使用Plone 4时,我已成功创建订阅者事件以在保存自定义内容类型时执行额外处理。这我通过使用Products.Archetypes.interfaces.IObjectInitializedEvent接口完成。异步运行Plone订阅者事件

的configure.zcml

<subscriber 
     for="mycustom.product.interfaces.IRepositoryItem 
      Products.Archetypes.interfaces.IObjectInitializedEvent" 
     handler=".subscribers.notifyCreatedRepositoryItem" 
    /> 

subscribers.py

def notifyCreatedRepositoryItem(repositoryitem, event): 
    """ 
    This gets called on IObjectInitializedEvent - which occurs when a new object is created. 
    """ 
    my custom processing goes here. Should be asynchronous 

但是,额外的处理有时需要太长时间了,我想知道如果有一种方法可以在后台运行,它即异步。

是否可以异步运行用户的事件,例如当一个人拯救的对象?

回答

6

不开箱即用。您需要为您的环境添加异步支持。

看看plone.app.async;你需要一个ZEO环境并至少有一个额外的实例。后者将运行从站点推入队列的异步作业。

然后可以定义要异步执行的方法和推任务到队列异步执行这样一种方法。

示例代码,推一个任务到队列:

from plone.app.async.interfaces import IAsyncService 

async = getUtility(IAsyncService) 
async.queueJob(an_async_task, someobject, arg1_value, arg2_value) 

和任务本身:

def an_async_task(someobject, arg1, arg2): 
    # do something with someobject 

其中someobject是你ZODB持久对象。 IAsyncService.queueJob需要至少一个函数和一个上下文对象,但是您可以添加尽可能多的进一步参数来执行您的任务。参数必须是可以选择的。

任务将被通过一个异步工人实例时,它可以执行时,当前请求的上下文之外。

1

为了给更多的选项,你可以尝试collective.taskqueue对于这一点,很简单,真正强大的(和避免一些plone.app.async的缺点)。

PyPI上的描述已经足够让你加快速度在任何时间,您可以使用Redis的队列管理是一大利好。