diff options
Diffstat (limited to 'src/slack.rs')
| -rw-r--r-- | src/slack.rs | 139 |
1 files changed, 139 insertions, 0 deletions
diff --git a/src/slack.rs b/src/slack.rs new file mode 100644 index 0000000..1c272cf --- /dev/null +++ b/src/slack.rs @@ -0,0 +1,139 @@ +use crate::agenda::{ + parse_message, + AgendaPoint +}; + +use futures::join; +use slack::{ + Event, + Message, +}; +use tokio::{ + sync::mpsc, + task::{ + spawn, + spawn_blocking, + }, +}; + +const TOKEN: Option<&str> = None; +const CHANNEL: Option<&str> = None; + +struct Handler { + sender: mpsc::UnboundedSender<AgendaPoint>, + slack_sender: slack::Sender, + slack_channel: Option<String>, + print_channels: bool, +} + +impl Handler { + fn new( + sender: mpsc::UnboundedSender<AgendaPoint>, + slack_sender: slack::Sender, + slack_channel: Option<String>, + ) -> Self { + Self { + sender, + slack_sender, + slack_channel: slack_channel.clone(), + print_channels: slack_channel.is_none() + } + } +} + +impl slack::EventHandler for Handler { + fn on_event(&mut self, cli: &slack::RtmClient, event: slack::Event) { + match event { + Event::Hello => { + if self.print_channels { + println!("Slack channels found: {:#?}", + cli + .start_response() + .channels + .as_ref() + .and_then(|channels| { + Some(channels + .iter() + .map(|channel| format!("{}: {}", + channel.name.as_ref().unwrap_or(&"??".to_string()), //TODO &"".to_string() ? + channel.id.as_ref().unwrap_or(&"??".to_string()))) //TODO + .collect::<Vec<_>>()) + })); + } + } + Event::Message(msg) => { + if let Some(channel) = &self.slack_channel { + match *msg { + Message::Standard(msg) => { + if msg.channel.is_some() && *channel == msg.channel.unwrap() { //TODO + if let Ok(Some(s)) = parse_message( + &msg.text.unwrap_or("".to_string()), + &msg.user.unwrap_or("??".to_string()), + &self.sender, + ) { + self.slack_sender.send_message(channel.as_str(), &s).unwrap(); + } + } + } + _ => {} // message type + } + } + } + _ => {} // event type + } + } + + fn on_close(&mut self, _cli: &slack::RtmClient) {} + + fn on_connect(&mut self, _cli: &slack::RtmClient) {} +} + +pub async fn handle( + sender: mpsc::UnboundedSender<AgendaPoint>, + receiver: mpsc::UnboundedReceiver<AgendaPoint>, +) { + println!("Setting up Slack"); + + let token = std::env::var("SLACK_API_TOKEN").unwrap_or_else(|_| TOKEN.expect("Missing slack token").to_string()); + let channel = match std::env::var("SLACK_CHANNEL") { + Ok(channel) => Some(channel), + Err(_) => match CHANNEL { + Some(channel) => Some(channel.to_string()), + None => None + } + }; + let client = spawn_blocking(move || { + slack::RtmClient::login(&token).unwrap() + }).await.unwrap(); + + let mut handler = Handler::new(sender, client.sender().clone(), channel.clone()); + let slack_sender = client.sender().clone(); + + let (_, _) = join!( + spawn_blocking(move || { + match client.run(&mut handler) { + Ok(_) => {} + Err(e) => { + println!("Error: {}", e) + } + } + }), + spawn(receive_from_discord(receiver, slack_sender, channel)) + ); +} + +async fn receive_from_discord( + mut receiver: mpsc::UnboundedReceiver<AgendaPoint>, + sender: slack::Sender, + channel: Option<String>, +) { + if let Some(channel) = channel { + while let Some(point) = receiver.recv().await { + //TODO Sending messages is very slow sometimes. Have seen delays + // from 5 up to 20(!) seconds. + sender.send_typing(&channel).unwrap(); + sender.send_message(&channel, &point.to_add_message()).unwrap(); + println!("Slack message sent"); + } + } +} |
