-
-
Notifications
You must be signed in to change notification settings - Fork 203
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
Add support for dynamic configuration updates #521
Conversation
Long-running, service-oriented, applications should be able to have their configurations updated without requiring restarts. These changes add methods that support periodic checks of previously loaded configuration files for changes and updates configuration-based traitlets of registered Configurable instances.
7212ab8
to
0c4b024
Compare
@kevin-bates would it be possible to mark configurable traits as dynamic via the class MyApp:
attr = Int().tag(config=True, sync_config=True) |
@rmorshea - TBH I'm not intimately familiar with traitlets. Are you trying to make explicit which configurable traits should be included in dynamic updates as opposed to all? I would not want to end up in a situation where some configurable trait requires dynamic behavior and users would be prevented from doing that w/o a code change. |
@kevin-bates Could you inherit from the application and override the trait with a new one that has the app.traits(sync_config=True) Maybe related to: #429 |
BTW calling |
@rmorshea - thanks for your comments. I think they've created more questions for me.
I appreciate you taking the time to guide me through this portion of things. |
FWIW, I can move these changes to outside the traitlets package if others feel these are not a fit. I would only need to create method for returning |
@kevin-bates I think I understand what you're trying to do now, and it may go beyond the scope of Traitlets. That said I think this is a very useful feature and may make sense in a downstream library (e.g. https://github.com/jupyter/notebook). If we were to do this in Traitlets I think you'd want to implement it at the level of the |
@kevin-bates that said, I'm also not entirely sure what it would look like to implement this configuration file syncing in the
config_syncer = ConfigFileSyncer(configurable_1, configurable_2, ...)
|
@kevin-bates another thing to consider is that Traitlets is in a bit of a holding pattern at the moment:
Given all these things, even if we could figure out how to do this in Traitlets, your work has a better chance of seeing the light of day if it were made in a different package within the Jupyter stack. |
@rmorshea - everything you said makes sense and I appreciate your responses! Yes, this is specifically targeting Jupyter projects that tend to be multi-tenant and service oriented - like the Enterprise Gateway project. The more I had been thinking about this, the more it made sense to perhaps relocate it as well. However, I would like to add the one method to access the "private" attribute I'll go ahead and submit a different PR for the accessor. Thank you for your time! |
Long-running, service-oriented, applications should be able to have their configurations updated without requiring restarts. These changes add methods that support periodic checks of previously loaded configuration files for changes and updates configuration-based traitlets of registered Configurable instances. Examples where dynamic updates can be useful is in toggling log levels or updated whitelists.
This PR will remain a WIP until the following have been completed (hoping for some feedback prior to moving on):
Applications wishing to utilize this must first register the Configurable instances that are participating in dynamic updates using
Application.add_dynamic_configurable(name, Configurable)
. The name is for informational purposes but it is suggested to use the traitlets class prefix for its configuration entry. For example, ifc.MappingKernelManager.cull_idle_timeout = 300
is in the configuration file and the application wishes to monitor traitlets on its multi kernel manager class instance, they would use a name ofMappingKernelManager
and register the Configurable instance using:It is expected that
Application.update_dynamic_configurations()
be called from a periodicCallback, but that's up to the application.Caveats:
c.MappingKernelManager.cull_interval
is used to configure a periodic callback of that interval. Updates tocull_interval
will not be reflected unless the periodic callback is stopped and re-created. As a result, applications must be aware and implement the@observe
callback to reset or reinitialize such entities in order to make those options dynamic.Example usage:
Here's an example usage from Jupyter Enterprise Gateway. This method registers the configurables of interest and initializes a periodic callback for
update_dynamic_configurables()
. It also logs the set of CLI-based options that will not be privy to dynamic updates.Output at application startup:
Because user's may want to adjust the polling interval for dynamic config updates, here's an example of an
@observe
callback that adjusts the period (again from Enterprise Gateway).