From 9e9da11f795644c8d243c51b8f418c6bbbdcc7c6 Mon Sep 17 00:00:00 2001 From: Adrian Malacoda Date: Tue, 9 May 2017 22:44:33 -0500 Subject: [PATCH] begin tenquestionmarks 0.0.2. Separate Module trait into Module struct (which holds metadata and config about the module) and EventLoop trait, which implements the event loop. The constructors still return Modules, but they are structs and not boxes. --- Cargo.toml | 2 +- src/event/mod.rs | 34 ++++++++++++++++++++++++++++++++-- src/lib.rs | 3 ++- src/modules/autolink.rs | 12 ++++++++---- src/modules/discord.rs | 19 ++++++++++++------- src/modules/echo.rs | 16 ++++++++++------ src/modules/echobox.rs | 18 +++++++++++------- src/modules/loader.rs | 22 +++++++++++----------- src/modules/lua.rs | 20 ++++++++++++-------- src/modules/mod.rs | 12 ++++++++++-- src/modules/pvn.rs | 12 ++++++++---- src/modules/random.rs | 18 +++++++++++------- src/modules/stdin.rs | 12 ++++++++---- 13 files changed, 136 insertions(+), 64 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 92e5ce8..933ed9a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name="tenquestionmarks" -version="0.0.1" +version="0.0.2" authors=["Adrian Malacoda "] [dependencies] diff --git a/src/event/mod.rs b/src/event/mod.rs index 1992097..70271ce 100644 --- a/src/event/mod.rs +++ b/src/event/mod.rs @@ -15,15 +15,45 @@ pub enum Event { pub struct Envelope { pub from: Option, pub event: Event, - pub to: Vec + pub to: Vec, + pub tags: Vec } impl Envelope { pub fn new (event: Event) -> Envelope { + let mut tags: Vec = vec![]; + + match &event { + &Event::Message { ref message } => { + tags.push(format!("user:{:}", message.author.name)); + match message.channel { + Some(ref channel) => { + tags.push(format!("channel:{:}", channel.name)); + }, + None => {} + } + }, + &Event::SelfJoin { ref channel } => { + tags.push(format!("channel:{:}", channel.name)); + }, + &Event::SelfQuit { ref channel } => { + tags.push(format!("channel:{:}", channel.name)); + }, + &Event::UserJoin { ref channel, ref user } => { + tags.push(format!("channel:{:}", channel.name)); + tags.push(format!("user:{:}", user.name)); + }, + &Event::UserQuit { ref channel, ref user } => { + tags.push(format!("channel:{:}", channel.name)); + tags.push(format!("user:{:}", user.name)); + } + } + Envelope { from: None, event: event, - to: vec![] + to: vec![], + tags: tags } } } diff --git a/src/lib.rs b/src/lib.rs index d03b45d..23968c7 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -75,7 +75,8 @@ impl Tenquestionmarks { Envelope { from: Some(from.clone()), event: envelope.event, - to: envelope.to + to: envelope.to, + tags: envelope.tags } }); diff --git a/src/modules/autolink.rs b/src/modules/autolink.rs index 145fb62..957f7fc 100644 --- a/src/modules/autolink.rs +++ b/src/modules/autolink.rs @@ -1,4 +1,4 @@ -use modules::Module; +use modules::{Module, EventLoop}; use toml::Table; use std::sync::Arc; @@ -19,8 +19,12 @@ use regex::Regex; pub struct AutolinkModule {} impl AutolinkModule { - pub fn new (_: &Table, _: &Table) -> Box { - Box::new(AutolinkModule {}) + pub fn new (_: &Table, config: &Table) -> Module { + Module { + event_loop: Box::new(AutolinkModule {}), + module_type: String::from("autolink"), + config: config.clone() + } } } @@ -94,7 +98,7 @@ fn print_any_link (link: &Link, message: &Message) { message.reply(&format!("**Autolink:** {} -> {}", link.label(), link.url())); } -impl Module for AutolinkModule { +impl EventLoop for AutolinkModule { fn run (&self, _: Box>, receiver: Receiver>) { let link_regex = Regex::new(r"\[\[([^\[\]]*)\]\]").expect("Invalid regex..."); let mut searchers = AggregateSearcher::new(); diff --git a/src/modules/discord.rs b/src/modules/discord.rs index ffc8f8e..74fb518 100644 --- a/src/modules/discord.rs +++ b/src/modules/discord.rs @@ -3,6 +3,7 @@ use discord::Discord; use discord::model::{Event, PossibleServer}; use modules::Module; +use modules::EventLoop; use toml::Table; use event; @@ -19,10 +20,10 @@ pub struct DiscordModule { playing: String } -const DEFAULT_PLAYING: &'static str = "tenquestionmarks 0.0.1"; +const DEFAULT_PLAYING: &'static str = "tenquestionmarks 0.0.2"; impl DiscordModule { - pub fn new (_: &Table, configuration: &Table) -> Box { + pub fn new (_: &Table, configuration: &Table) -> Module { let token = configuration.get("token") .and_then(|value| value.as_str()) .unwrap_or(""); @@ -31,10 +32,14 @@ impl DiscordModule { .and_then(|value| value.as_str()) .unwrap_or(DEFAULT_PLAYING); - Box::new(DiscordModule { - token: String::from(token), - playing: String::from(playing) - }) + Module { + module_type: String::from("Discord"), + event_loop: Box::new(DiscordModule { + token: String::from(token), + playing: String::from(playing) + }), + config: configuration.clone() + } } } @@ -53,7 +58,7 @@ impl MessageSender for DiscordMessageSender { } } -impl Module for DiscordModule { +impl EventLoop for DiscordModule { fn run (&self, sender: Box>, _: Receiver>) { let discord = Arc::new(Discord::from_bot_token(&self.token[..]).expect("Discord module: Login failed")); let (mut connection, _) = discord.connect().expect("Discord module: Connection failed"); diff --git a/src/modules/echo.rs b/src/modules/echo.rs index ce72542..1da86a2 100644 --- a/src/modules/echo.rs +++ b/src/modules/echo.rs @@ -1,4 +1,4 @@ -use modules::Module; +use modules::{Module, EventLoop}; use toml::Table; use std::sync::Arc; @@ -13,18 +13,22 @@ pub struct EchoModule { } impl EchoModule { - pub fn new (_: &Table, configuration: &Table) -> Box { + pub fn new (_: &Table, configuration: &Table) -> Module { let prefix = configuration.get("prefix") .and_then(|value| value.as_str()) .unwrap_or("!echo"); - Box::new(EchoModule { - prefix: String::from(prefix) - }) + Module { + module_type: String::from("echo"), + event_loop: Box::new(EchoModule { + prefix: String::from(prefix) + }), + config: configuration.clone() + } } } -impl Module for EchoModule { +impl EventLoop for EchoModule { fn run(&self, _: Box>, receiver: Receiver>) { loop { match receiver.recv() { diff --git a/src/modules/echobox.rs b/src/modules/echobox.rs index c50b9ca..49b86a6 100644 --- a/src/modules/echobox.rs +++ b/src/modules/echobox.rs @@ -1,4 +1,4 @@ -use modules::Module; +use modules::{Module, EventLoop}; use toml::Table; use std::sync::Arc; @@ -15,7 +15,7 @@ pub struct EchoboxModule { } impl EchoboxModule { - pub fn new (_: &Table, configuration: &Table) -> Box { + pub fn new (_: &Table, configuration: &Table) -> Module { let prefix = configuration.get("prefix") .and_then(|value| value.as_str()) .unwrap_or("?echobox"); @@ -24,14 +24,18 @@ impl EchoboxModule { .and_then(|value| value.as_str()) .unwrap_or("echobox.db"); - Box::new(EchoboxModule { - prefix: String::from(prefix), - file: String::from(file) - }) + Module { + module_type: String::from("echo"), + event_loop: Box::new(EchoboxModule { + prefix: String::from(prefix), + file: String::from(file) + }), + config: configuration.clone() + } } } -impl Module for EchoboxModule { +impl EventLoop for EchoboxModule { fn run(&self, _: Box>, receiver: Receiver>) { let echobox = Echobox::with_file(&self.file).unwrap(); diff --git a/src/modules/loader.rs b/src/modules/loader.rs index 0b14d54..4dd78ce 100644 --- a/src/modules/loader.rs +++ b/src/modules/loader.rs @@ -15,26 +15,26 @@ use modules::echobox::EchoboxModule; use modules::autolink::AutolinkModule; pub struct ModuleLoader { - types: BTreeMap<&'static str, fn(&Table, &Table) -> Box> + types: BTreeMap<&'static str, fn(&Table, &Table) -> Module> } impl ModuleLoader { pub fn new () -> ModuleLoader { let mut types = BTreeMap::new(); - types.insert("discord", DiscordModule::new as fn(&Table, &Table) -> Box); - types.insert("lua", LuaModule::new as fn(&Table, &Table) -> Box); - types.insert("stdin", StdinModule::new as fn(&Table, &Table) -> Box); - types.insert("echo", EchoModule::new as fn(&Table, &Table) -> Box); - types.insert("random", RandomModule::new as fn(&Table, &Table) -> Box); - types.insert("pvn", PvnModule::new as fn(&Table, &Table) -> Box); - types.insert("echobox", EchoboxModule::new as fn(&Table, &Table) -> Box); - types.insert("autolink", AutolinkModule::new as fn(&Table, &Table) -> Box); + types.insert("discord", DiscordModule::new as fn(&Table, &Table) -> Module); + types.insert("lua", LuaModule::new as fn(&Table, &Table) -> Module); + types.insert("stdin", StdinModule::new as fn(&Table, &Table) -> Module); + types.insert("echo", EchoModule::new as fn(&Table, &Table) -> Module); + types.insert("random", RandomModule::new as fn(&Table, &Table) -> Module); + types.insert("pvn", PvnModule::new as fn(&Table, &Table) -> Module); + types.insert("echobox", EchoboxModule::new as fn(&Table, &Table) -> Module); + types.insert("autolink", AutolinkModule::new as fn(&Table, &Table) -> Module); ModuleLoader { types: types } } - pub fn load_from_configuration (&self, configuration: Table) -> Result>, ModuleLoaderError> { + pub fn load_from_configuration (&self, configuration: Table) -> Result, ModuleLoaderError> { let general_config = configuration.get("general") .and_then(|value| value.as_table()) .map(|value| value.clone()) @@ -53,7 +53,7 @@ impl ModuleLoader { }).collect() } - pub fn load_single_module (&self, name: &str, general_configuration: &Table, module_configuration: &Table) -> Result, ModuleLoaderError> { + pub fn load_single_module (&self, name: &str, general_configuration: &Table, module_configuration: &Table) -> Result { /* * The Module type defaults to the instance name (in the tenquestionmarks configuration) * but can explicitly be set by using the special "type" parameter. diff --git a/src/modules/lua.rs b/src/modules/lua.rs index 38bacdf..67fee26 100644 --- a/src/modules/lua.rs +++ b/src/modules/lua.rs @@ -1,4 +1,4 @@ -use modules::Module; +use modules::{Module, EventLoop}; use toml::{Table, Value}; @@ -22,12 +22,16 @@ pub struct LuaModule { } impl LuaModule { - pub fn new (_: &Table, config: &Table) -> Box { - Box::new(LuaModule { - code: config.get("code").and_then(|value| value.as_str()).map(String::from), - file: config.get("file").and_then(|value| value.as_str()).map(String::from), - variables: config.clone() - }) + pub fn new (_: &Table, config: &Table) -> Module { + Module { + module_type: String::from("lua"), + event_loop: Box::new(LuaModule { + code: config.get("code").and_then(|value| value.as_str()).map(String::from), + file: config.get("file").and_then(|value| value.as_str()).map(String::from), + variables: config.clone() + }), + config: config.clone() + } } } @@ -48,7 +52,7 @@ implement_lua_push!(Message, |mut metatable| { index.set("reply", hlua::function2(|message: &mut Message, reply: String| message.reply(&reply))); }); -impl Module for LuaModule { +impl EventLoop for LuaModule { fn run (&self, _: Box>, receiver: Receiver>) { let mut lua = Lua::new(); lua.openlibs(); diff --git a/src/modules/mod.rs b/src/modules/mod.rs index 5e6b71d..0424ba7 100644 --- a/src/modules/mod.rs +++ b/src/modules/mod.rs @@ -16,7 +16,15 @@ use std::sync::Arc; use std::sync::mpsc::Receiver; use transformable_channels::mpsc::ExtSender; -pub trait Module : Sync { - fn register (&self, _: &Tenquestionmarks) {} +use toml::Table; + +pub struct Module { + event_loop: Box, + module_type: String, + config: Table +} + +impl Module {} +pub trait EventLoop : Sync { fn run (&self, _: Box>, _: Receiver>) {} } diff --git a/src/modules/pvn.rs b/src/modules/pvn.rs index 153b66c..8aa67ab 100644 --- a/src/modules/pvn.rs +++ b/src/modules/pvn.rs @@ -1,4 +1,4 @@ -use modules::Module; +use modules::{Module, EventLoop}; use toml::Table; use std::sync::Arc; @@ -17,8 +17,12 @@ use pvn::ninjas::{Ninja, Ninjas}; pub struct PvnModule {} impl PvnModule { - pub fn new (_: &Table, _: &Table) -> Box { - Box::new(PvnModule {}) + pub fn new (_: &Table, configuration: &Table) -> Module { + Module { + module_type: String::from("pvn"), + event_loop: Box::new(PvnModule {}), + config: configuration.clone() + } } } @@ -136,7 +140,7 @@ impl PirateVsNinja { } } -impl Module for PvnModule { +impl EventLoop for PvnModule { fn run(&self, _: Box>, receiver: Receiver>) { let mut pvn = PirateVsNinja { pirates: Pirates::new(), diff --git a/src/modules/random.rs b/src/modules/random.rs index 35dd239..a3b57bd 100644 --- a/src/modules/random.rs +++ b/src/modules/random.rs @@ -1,4 +1,4 @@ -use modules::Module; +use modules::{Module, EventLoop}; use toml::Table; use std::sync::Arc; @@ -15,7 +15,7 @@ pub struct RandomModule { } impl RandomModule { - pub fn new (_: &Table, configuration: &Table) -> Box { + pub fn new (_: &Table, configuration: &Table) -> Module { let prefix = configuration.get("prefix") .and_then(|value| value.as_str()) .unwrap_or("?random"); @@ -28,14 +28,18 @@ impl RandomModule { .map(|value| { String::from(value.as_str().unwrap()) }) .collect(); - Box::new(RandomModule { - prefix: String::from(prefix), - responses: responses - }) + Module { + module_type: String::from("random"), + event_loop: Box::new(RandomModule { + prefix: String::from(prefix), + responses: responses + }), + config: configuration.clone() + } } } -impl Module for RandomModule { +impl EventLoop for RandomModule { fn run(&self, _: Box>, receiver: Receiver>) { let mut rng = rand::thread_rng(); diff --git a/src/modules/stdin.rs b/src/modules/stdin.rs index c6bff53..395d5a4 100644 --- a/src/modules/stdin.rs +++ b/src/modules/stdin.rs @@ -1,6 +1,6 @@ use std::io; -use modules::Module; +use modules::{Module, EventLoop}; use toml::Table; use {MessageSender, Message, User}; @@ -25,12 +25,16 @@ impl MessageSender for StdinMessageSender { } impl StdinModule { - pub fn new (_: &Table, _: &Table) -> Box { - Box::new(StdinModule {}) + pub fn new (_: &Table, config: &Table) -> Module { + Module { + module_type: String::from("stdin"), + event_loop: Box::new(StdinModule {}), + config: config.clone() + } } } -impl Module for StdinModule { +impl EventLoop for StdinModule { fn run(&self, sender: Box>, _: Receiver>) { loop { let mut input = String::new();