107 lines
2.8 KiB
Rust
107 lines
2.8 KiB
Rust
use phoebe::{
|
|
mid_chat::{self, ChatMessage, ChatMessageEdit, ChatMessageReference, ChatReference},
|
|
prelude::*,
|
|
DynServiceLookup,
|
|
};
|
|
use serenity::{client::Context, Client};
|
|
use tracing::{debug, info};
|
|
|
|
mod chat_conv;
|
|
mod handler;
|
|
mod lookup;
|
|
mod sender;
|
|
|
|
pub fn discord_reference(id: impl ToString) -> mid_chat::ChatReference {
|
|
mid_chat::ChatReference {
|
|
service: "discord",
|
|
id: id.to_string(),
|
|
}
|
|
}
|
|
|
|
pub struct DiscordService {
|
|
pub core_db: SqlitePool,
|
|
pub discord_media_db: SqlitePool,
|
|
pub ctx: Context,
|
|
pub dyn_service: DynServiceLookup,
|
|
}
|
|
|
|
pub async fn setup(
|
|
core_db: SqlitePool,
|
|
tx: ChatEventSender,
|
|
dyn_service: DynServiceLookup,
|
|
) -> Result<DiscordService> {
|
|
info!("Setting up Discord service…");
|
|
|
|
let discord_media_db = phoebe::db::open("discord_media").await?;
|
|
sqlx::migrate!().run(&discord_media_db).await?;
|
|
|
|
let (ctx_tx, mut ctx_rx) = tokio::sync::mpsc::unbounded_channel::<Context>();
|
|
|
|
let discord_handler = handler::DiscordHandler {
|
|
core_db: core_db.clone(),
|
|
discord_media_db: discord_media_db.clone(),
|
|
chat_event_tx: tx,
|
|
ctx_tx,
|
|
};
|
|
|
|
debug!("Logging in…");
|
|
let discord_token = std::env::var("PHOEBE_DISCORD_TOKEN")
|
|
.expect("PHOEBE_DISCORD_TOKEN environment variable was not set!");
|
|
|
|
let mut client = Client::builder(&discord_token)
|
|
.event_handler(discord_handler)
|
|
.await?;
|
|
|
|
tokio::spawn(async move {
|
|
client
|
|
.start()
|
|
.await
|
|
.expect("Failed to start Discord client")
|
|
});
|
|
|
|
let discord_ctx = ctx_rx.recv().await.expect("Couldn't get Discord context");
|
|
debug!("Logged in!");
|
|
|
|
Ok(DiscordService {
|
|
core_db,
|
|
discord_media_db,
|
|
ctx: discord_ctx,
|
|
dyn_service,
|
|
})
|
|
}
|
|
|
|
#[async_trait]
|
|
impl Service for DiscordService {
|
|
fn tag(&self) -> &'static str {
|
|
"discord"
|
|
}
|
|
|
|
async fn send_chat_message(
|
|
&mut self,
|
|
source: &ChatMessage,
|
|
destination_channel: ChatReference,
|
|
) -> Vec<ChatMessageReference> {
|
|
assert_eq!(destination_channel.service, "discord");
|
|
sender::send_discord_message(self, source, destination_channel)
|
|
.await
|
|
.ok()
|
|
.into_iter()
|
|
.collect()
|
|
}
|
|
|
|
async fn delete_message(&mut self, message: &ChatMessageReference) -> bool {
|
|
assert_eq!(message.channel.service, "discord");
|
|
sender::delete_discord_message(self, message).await.is_ok()
|
|
}
|
|
|
|
async fn edit_message(
|
|
&mut self,
|
|
prev_origin: &ChatMessageReference,
|
|
new_message: &ChatMessageEdit,
|
|
) -> Vec<ChatMessageReference> {
|
|
assert_eq!(prev_origin.channel.service, "discord");
|
|
let _ = sender::edit_discord_message(self, prev_origin, new_message).await;
|
|
vec![]
|
|
}
|
|
}
|