自定义Extensions
大多数项目都需要自定义一些个性化的功能,而不会是仅靠Nameko提供的内置Extensions就可以完成设计。利用Nameko提供的基础类,可以根据Nameko的设计思路,很方便的将个性化的功能利用Nameko的基础功能类融入到项目中。
在Nameko中能够自定义的内容都是Extensions,包括Dependency Provider和Entrypoint,这两个都是Extension的子类。要自定义一个Extension,一般需要继承nameko.extensions.Extension
并且至少定义以下三个方法。
.setup()
,在Service Container启动之前进行绑定的阶段调用,通常用来进行初始化工作。.start()
,在Service Container成功启动之后调用,会在所有的Extension的.setup()
完成初始化后调用。.stop()
,在Service Container开始关闭之前调用。
Extension的.__init__()
方法将在Service Container的.bind()
方法执行过程中调用,但Nameko为了避免一些歧义,将Extension的初始化配置改在了.setup()
方法中进行。绑定到Service Container中的Extension可以根据Extension类型,通过.entrypoints
、.dependencies
和.subextensions
三个集合类型属性来进行访问,或者可以直接通过.extensions
属性来统一进行访问。
Dependency Provider用于向RPC服务提供一些依赖环境,例如数据库连接、额外的控制功能等。要自定义个一个Dependency Provider一般需要继承nameko.extensions.DependencyProvider
并至少实现以下方法。
.worker_setup(worker_ctx)
,在一个Worker执行任务之前调用,这里需要做一些开始任务处理之前的准备工作。在此抛出异常将导致Worker产生失败事件。.worker_result(worker_ctx, result=None, exc_info=None)
,在一个Worker完成任务获得返回结果后调用,这里需要做一些针对Worker执行结果的处理,或者例如关闭数据库事务会话。.worker_teardown(work_ctx)
,在一个Worker完成执行一个任务之后调用,这里需要做一些针对工作现场的清理工作,例如提交数据库事务会话。.get_dependency(work_ctx)
,必须实现的一个方法,这个方法需要返回一个对象,可以是对象或者函数,这个被返回的对象将被注入到Worker中。
自定义Entrypoint一般用来实现新的传输机制或者新的服务初始化机制。要自定义一个Entrypoint,必须完成以下三项内容。
- 继承
nameko.extensions.Entrypoint
类。 - 实现
.start()
方法来启动Entrypoint。如果需要一个后台线程,可以使用Service Container提供的.spawn_managed_thread(function, identifier)
来启动。 - 调用Service Container的
.spawn_worker()
方法来启动一个响应。
Entrypoint通常以一个修饰器的形式出现,这可以通过调用.decorator()
方法来获取。获取到的修饰器其所接收的所有参数都会用来传递给Entrypoint的.__init__()
方法。
在实现Entrypoint必须完成的三项内容中提到了需要使用Service Container的.spawn_worker()
方法来启动一个响应,这个方法主要接受以下参数。
entrypoint
,通常是Entrypoint实例自身。args
和kwargs
,传递给服务方法的参数。context_data=None
,一般会初始化为Worker上下文。handle_result=None
,一般会指定为Entrypoint中用于处理服务方法返回内容的处理函数。如果指定处理函数,则这个函数必须能够接受以下四个参数,并且必须返回一个元组包括服务方法返回结果和抛出的异常。message
,传入的消息。worker_ctx
,执行服务方法的Worker上下文。result
,服务方法的返回结果。exc_info
,服务方法抛出的异常。