Support logging in geyser plugins (#34101)

The change creates a new interface in the GeyserPlugin interface to allow the runtime to pass the logging configuration to the plugin.
This commit is contained in:
Lijun Wang 2023-11-29 11:31:11 -08:00 committed by GitHub
parent 60c09d3d89
commit f211c86e69
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 47 additions and 0 deletions

View File

@ -321,6 +321,35 @@ pub type Result<T> = std::result::Result<T, GeyserPluginError>;
/// Geyser plugins must describe desired behavior for load and unload,
/// as well as how they will handle streamed data.
pub trait GeyserPlugin: Any + Send + Sync + std::fmt::Debug {
/// The callback to allow the plugin to setup the logging configuration using the logger
/// and log level specified by the validator. Will be called first on load/reload, before any other
/// callback, and only called once.
/// # Examples
///
/// ```
/// use solana_geyser_plugin_interface::geyser_plugin_interface::{GeyserPlugin,
/// GeyserPluginError, Result};
///
/// #[derive(Debug)]
/// struct SamplePlugin;
/// impl GeyserPlugin for SamplePlugin {
/// fn setup_logger(&self, logger: &'static dyn log::Log, level: log::LevelFilter) -> Result<()> {
/// log::set_max_level(level);
/// if let Err(err) = log::set_logger(logger) {
/// return Err(GeyserPluginError::Custom(Box::new(err)));
/// }
/// Ok(())
/// }
/// fn name(&self) -> &'static str {
/// &"sample"
/// }
/// }
/// ```
#[allow(unused_variables)]
fn setup_logger(&self, logger: &'static dyn log::Log, level: log::LevelFilter) -> Result<()> {
Ok(())
}
fn name(&self) -> &'static str;
/// The callback called when a plugin is loaded by the system,

View File

@ -107,6 +107,8 @@ impl GeyserPluginManager {
});
}
setup_logger_for_plugin(&*new_plugin)?;
// Call on_load and push plugin
new_plugin
.on_load(new_config_file, false)
@ -193,6 +195,8 @@ impl GeyserPluginManager {
});
}
setup_logger_for_plugin(&*new_plugin)?;
// Attempt to on_load with new plugin
match new_plugin.on_load(new_parsed_config_file, true) {
// On success, push plugin and library
@ -228,6 +232,20 @@ impl GeyserPluginManager {
}
}
// Initialize logging for the plugin
fn setup_logger_for_plugin(new_plugin: &dyn GeyserPlugin) -> Result<(), jsonrpc_core::Error> {
new_plugin
.setup_logger(log::logger(), log::max_level())
.map_err(|setup_logger_err| jsonrpc_core::Error {
code: ErrorCode::InvalidRequest,
message: format!(
"setup_logger method of plugin {} failed: {setup_logger_err}",
new_plugin.name()
),
data: None,
})
}
#[derive(Debug)]
pub enum GeyserPluginManagerRequest {
ReloadPlugin {