Adds an additional parameter for prioritizing the search results from a specific plugin. The plugin may define a priority which will sort results after the initial pattern search. The web plugin will be the first plugin to utilize this feature
133 lines
3.8 KiB
Rust
133 lines
3.8 KiB
Rust
mod config;
|
|
pub(crate) mod external;
|
|
pub mod help;
|
|
|
|
pub use self::config::{PluginBinary, PluginConfig, PluginPriority, PluginQuery};
|
|
pub use self::external::ExternalPlugin;
|
|
pub use self::help::HelpPlugin;
|
|
|
|
use crate::{Indice, PluginHelp, Request};
|
|
use async_trait::async_trait;
|
|
use postage::mpsc::{Receiver, Sender};
|
|
use postage::prelude::*;
|
|
use regex::Regex;
|
|
|
|
#[async_trait]
|
|
pub trait Plugin
|
|
where
|
|
Self: Sized + Send,
|
|
{
|
|
/// Activate the selected ID from this plugin
|
|
async fn activate(&mut self, id: Indice);
|
|
|
|
async fn activate_context(&mut self, id: Indice, context: Indice);
|
|
|
|
async fn complete(&mut self, id: Indice);
|
|
|
|
async fn context(&mut self, id: Indice);
|
|
|
|
fn exit(&mut self);
|
|
|
|
async fn interrupt(&mut self);
|
|
|
|
fn name(&self) -> &str;
|
|
|
|
async fn search(&mut self, query: &str);
|
|
|
|
async fn quit(&mut self, id: Indice);
|
|
|
|
async fn run(&mut self, mut rx: Receiver<Request>) {
|
|
while let Some(request) = rx.recv().await {
|
|
tracing::event!(
|
|
tracing::Level::DEBUG,
|
|
"{}: received {:?}",
|
|
self.name(),
|
|
request
|
|
);
|
|
match request {
|
|
Request::Search(query) => self.search(&query).await,
|
|
Request::Interrupt => self.interrupt().await,
|
|
Request::Activate(id) => self.activate(id).await,
|
|
Request::ActivateContext { id, context } => {
|
|
self.activate_context(id, context).await
|
|
}
|
|
Request::Complete(id) => self.complete(id).await,
|
|
Request::Context(id) => self.context(id).await,
|
|
Request::Quit(id) => self.quit(id).await,
|
|
Request::Exit => {
|
|
self.exit();
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
tracing::event!(tracing::Level::DEBUG, "{}: exiting plugin", self.name());
|
|
}
|
|
}
|
|
|
|
/// Stores all information relevant for communicating with a plugin
|
|
///
|
|
/// Plugins may be requested to exit, and relaunched at any point in the future.
|
|
pub struct PluginConnector {
|
|
/// The deserialized configuration file for this plugin
|
|
pub config: PluginConfig,
|
|
|
|
/// Code that is executed to prepare a new instance of
|
|
/// this plugin to spawn as a background service
|
|
pub init: Box<dyn Fn() -> Sender<Request>>,
|
|
|
|
/// A compiled regular expression that a query must match
|
|
/// for the launcher service to justify spawning and sending
|
|
/// queries to this plugin
|
|
pub regex: Option<Regex>,
|
|
|
|
/// The sender of the spawned background service that will be
|
|
/// forwarded to the launncher service
|
|
pub sender: Option<Sender<Request>>,
|
|
}
|
|
|
|
impl PluginConnector {
|
|
pub fn new(
|
|
config: PluginConfig,
|
|
regex: Option<Regex>,
|
|
init: Box<dyn Fn() -> Sender<Request> + Send>,
|
|
) -> Self {
|
|
Self {
|
|
config,
|
|
init,
|
|
regex,
|
|
sender: None,
|
|
}
|
|
}
|
|
|
|
pub fn details(&self) -> PluginHelp {
|
|
PluginHelp {
|
|
name: self.config.name.as_ref().to_owned(),
|
|
description: self.config.description.as_ref().to_owned(),
|
|
help: self
|
|
.config
|
|
.query
|
|
.help
|
|
.as_ref()
|
|
.map(|x| x.as_ref().to_owned()),
|
|
}
|
|
}
|
|
|
|
/// Obtains the sender for sending messages to this plugin.
|
|
///
|
|
/// If the sender is absent, the plugin is relaunched with a new one.
|
|
pub fn sender_exec(&mut self) -> &mut Sender<Request> {
|
|
let &mut Self {
|
|
ref mut sender,
|
|
ref init,
|
|
..
|
|
} = self;
|
|
|
|
sender.get_or_insert_with(|| init())
|
|
}
|
|
|
|
/// Drops the sender, which will subsequently drop the plugin forwarder attached to it
|
|
pub fn sender_drop(&mut self) {
|
|
self.sender = None;
|
|
}
|
|
}
|