-
Notifications
You must be signed in to change notification settings - Fork 650
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Convert plugin API to be purely event based #1090
Comments
I think I've found a potential problem with this. If the E.g. the attach plugin currently uses the logger in that method which would have to become a class method under this design.
So, if we consider that this method not only configures the parser but potentially defines a method to overtake the whole process, maybe it shouldn't become a classmethod? But that also changes the rest of the design. Need to give this more thought. |
If the only problem is the |
class AutoLogger:
def __get__(self, obj, cls):
if self._logger is None:
self._logger = logging.getLogger(cls.__module__ + '.' + cls.__name__)
return self._logger
class HasLogger:
logger = AutoLogger() |
I'm not sure if I understand what it does since I haven't looked into metaclasses yet and I'm also not sure if However, on a more general note: Basically, it means that plugins that want to overtake the whole process are always restricted to assign a classmethod and don't have access to anything that is related to the instance of the plugin. |
I'm gonna step back from this and let you figure it out. You're closer to the code. |
I think with the event bus proving more and more as a viable solution, and if we don't hit a big performance problem, then, I think we should retire the plugin event mechanism entirely and simply let all event based communication go through the event bus. |
We achieved this by basing our plugin architecture on the event bus. |
What things currently look like.
The current plugin API looks like this.
configure_parser
: Hook that can be implemented by plugin to modify CLI parser configurationshould_start
: Called byPluginManager
to check whether a plugin should be started based on an eventstart
: Called by thePluginManager
ifshould_start
returnsTrue
and the plugin has not been started yet.stop
: Called by thePluginManager
to stop plugins during shutdown.The Event API works through the
PluginManager
and all events are fired by thePluginManager
. The following events are currenty available.TrinityStartupEvent
- broadcast when theNodeClass
is launched/startedPluginStartedEvent
- broadcast when a specific plugin is startedResourceAvaiableEvent
- broadcast when a resource becomes availableThis API has been a good start, but it has been built in direct response to the needs presented by the transaction pool and the other initial plugin experiments. Now that we are starting to see what a plugin might look like, I propose the following changes to this API.
What I think things should look like
First, I want to better define the initialization process and plugin lifecycle.
Plugin.bootstrap(arg_parser, sub_parser)
:classmethod
since this will occur early enough in the process that I don't think we can realistically initialize plugins at this stage.Plugin.__init__(args, token)
:args
is the CLIArgparser
result.token
is aCancelToken
that the plugin should use to gracefully handle shutdowns (not fully fleshed out).Plugin.ready(chain_config, broadcast_queue, subscription_queue)
broadcast_queue
is anasyncio.Queue
that the plugin can use to broadcast an event (more below)subscription_queue
is anasyncio.Queue
that the plugin can consume events that have been broadcast by other plugins. (more below)Plugin.run()
Plugin.cancel()
After
ready
and beforeshutdown
is when the app is running. Within these boundaries, the Trinity application is running and plugins are active. During this period, plugins interact via events.Here is the best description of how I think events should work.
PluginManager
.Plugin.get_broadcast_events()
: Returns all of the events that this plugin can broadcast.Plugin.get_subscription_events(registry):
Returns all of the events that this plugin wants to subscribe to. Theregistry
would be a data structure containing all of the registered events (and probably the plugin which registered them).get_broadcast_events
using thebroadcast_queue
subscription_queue
and respond.We probably have a few core events that are provided by the plugin manager or some other built-in plugin.
DiscoveryStarted
to give plugins access to theDiscoveryService
PeerPoolStarted
to give plugins access to thePeerPool
The text was updated successfully, but these errors were encountered: