Skip to content

Commit c798166

Browse files
committed
make the event handler an async fn
This works so long as the handler's future does not capture the shard.
1 parent bc25f2a commit c798166

File tree

2 files changed

+20
-31
lines changed

2 files changed

+20
-31
lines changed

src/dispatch.rs

Lines changed: 8 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ pub enum ShardRestartResult {
1111
}
1212

1313
impl ShardRestartResult {
14-
pub fn is_forced(&self) -> bool {
14+
pub fn is_forced(self) -> bool {
1515
matches!(self, Self::ForcedRestart)
1616
}
1717
}
@@ -90,24 +90,12 @@ impl State {
9090
}
9191
}
9292

93-
pub struct Dispatcher<'a> {
94-
#[allow(dead_code)]
95-
pub shard: &'a mut Shard,
96-
tracker: &'a TaskTracker,
97-
}
98-
99-
impl<'a> Dispatcher<'a> {
100-
fn new(shard: &'a mut Shard, tracker: &'a TaskTracker) -> Self {
101-
Self { shard, tracker }
102-
}
103-
104-
pub fn dispatch(self, future: impl Future<Output = ()> + Send + 'static) {
105-
self.tracker.spawn(future);
106-
}
107-
}
108-
10993
#[tracing::instrument(name = "dispatcher", fields(shard.id = shard.id().number()), skip_all)]
110-
pub async fn run(mut shard: Shard, mut event_handler: impl FnMut(Dispatcher, Event)) -> ResumeInfo {
94+
pub async fn run<H, Fut>(mut shard: Shard, mut event_handler: H) -> ResumeInfo
95+
where
96+
H: FnMut(Event, &mut Shard) -> Fut,
97+
Fut: Future<Output = ()> + Send + 'static,
98+
{
11199
let mut receiver = ShardHandle::insert(shard.id());
112100
let mut shutdown = pin!(signal::ctrl_c());
113101
let tracker = TaskTracker::new();
@@ -132,11 +120,8 @@ pub async fn run(mut shard: Shard, mut event_handler: impl FnMut(Dispatcher, Eve
132120
event = shard.next_event(EVENT_TYPES) => {
133121
match event {
134122
Some(Ok(Event::GatewayClose(_))) if !state.is_active() => break,
135-
Some(Ok(event)) => event_handler(Dispatcher::new(&mut shard, &tracker), event),
136-
Some(Err(error)) => {
137-
tracing::warn!(error = &error as &dyn Error, "shard failed to receive an event");
138-
continue;
139-
}
123+
Some(Ok(event)) => _ = tracker.spawn(event_handler(event, &mut shard)),
124+
Some(Err(error)) => tracing::warn!(error = &error as &dyn Error, "shard failed to receive an event"),
140125
None => break,
141126
}
142127
}

src/main.rs

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,9 @@ use dashmap::DashMap;
1414
use std::{env, pin::pin, time::Duration};
1515
use tokio::signal;
1616
use tracing::{Instrument as _, instrument::Instrumented};
17-
use twilight_gateway::{ConfigBuilder, Event, EventTypeFlags, Intents, queue::InMemoryQueue};
17+
use twilight_gateway::{
18+
ConfigBuilder, Event, EventTypeFlags, Intents, Shard, queue::InMemoryQueue,
19+
};
1820
use twilight_http::Client;
1921
use twilight_model::id::{
2022
Id,
@@ -92,7 +94,7 @@ async fn main() -> anyhow::Result<()> {
9294
Ok(())
9395
}
9496

95-
fn event_handler(dispatcher: dispatch::Dispatcher, event: Event) {
97+
fn event_handler(event: Event, _shard: &mut Shard) -> impl Future<Output = ()> + use<> {
9698
async fn log_err(future: Instrumented<impl Future<Output = anyhow::Result<()>>>) {
9799
let mut future = pin!(future);
98100
if let Err(error) = future.as_mut().await {
@@ -101,12 +103,14 @@ fn event_handler(dispatcher: dispatch::Dispatcher, event: Event) {
101103
}
102104
}
103105

104-
#[allow(clippy::single_match)]
105-
match event {
106-
Event::InteractionCreate(event) => {
107-
let span = tracing::info_span!(parent: None, "interaction", id = %event.id);
108-
dispatcher.dispatch(log_err(command::interaction(event).instrument(span)))
106+
async {
107+
#[allow(clippy::single_match)]
108+
match event {
109+
Event::InteractionCreate(event) => {
110+
let span = tracing::info_span!("interaction", id = %event.id);
111+
log_err(command::interaction(event).instrument(span)).await;
112+
}
113+
_ => {}
109114
}
110-
_ => {}
111115
}
112116
}

0 commit comments

Comments
 (0)