Properly extract all extractable methods from GatewayHandle into Trait

This commit is contained in:
bitfl0wer 2023-11-15 20:18:50 +01:00
parent 5af6d1ce4b
commit 20c9066e6f
6 changed files with 122 additions and 100 deletions

View File

@ -1,5 +1,5 @@
use async_trait::async_trait; use async_trait::async_trait;
use chorus::gateway::GatewayCapable; use chorus::gateway::{GatewayCapable, GatewayHandleCapable};
use chorus::{ use chorus::{
self, self,
gateway::{Gateway, Observer}, gateway::{Gateway, Observer},

View File

@ -1,6 +1,6 @@
use std::time::Duration; use std::time::Duration;
use chorus::gateway::GatewayCapable; use chorus::gateway::{GatewayCapable, GatewayHandleCapable};
use chorus::{self, gateway::Gateway, types::GatewayIdentifyPayload}; use chorus::{self, gateway::Gateway, types::GatewayIdentifyPayload};
use tokio::time::sleep; use tokio::time::sleep;

View File

@ -4,7 +4,7 @@ use reqwest::Client;
use serde_json::to_string; use serde_json::to_string;
use crate::errors::ChorusResult; use crate::errors::ChorusResult;
use crate::gateway::{Gateway, GatewayCapable}; use crate::gateway::{Gateway, GatewayCapable, GatewayHandleCapable};
use crate::instance::{ChorusUser, Instance}; use crate::instance::{ChorusUser, Instance};
use crate::ratelimiter::ChorusRequest; use crate::ratelimiter::ChorusRequest;
use crate::types::{GatewayIdentifyPayload, LimitType, LoginResult, LoginSchema}; use crate::types::{GatewayIdentifyPayload, LimitType, LoginResult, LoginSchema};

View File

@ -3,7 +3,7 @@ use std::sync::{Arc, RwLock};
pub use login::*; pub use login::*;
pub use register::*; pub use register::*;
use crate::gateway::GatewayCapable; use crate::gateway::{GatewayCapable, GatewayHandleCapable};
use crate::{ use crate::{
errors::ChorusResult, errors::ChorusResult,
gateway::Gateway, gateway::Gateway,

View File

@ -3,7 +3,7 @@ use std::sync::{Arc, RwLock};
use reqwest::Client; use reqwest::Client;
use serde_json::to_string; use serde_json::to_string;
use crate::gateway::{Gateway, GatewayCapable, GatewayHandle}; use crate::gateway::{Gateway, GatewayCapable, GatewayHandle, GatewayHandleCapable};
use crate::types::GatewayIdentifyPayload; use crate::types::GatewayIdentifyPayload;
use crate::{ use crate::{
errors::ChorusResult, errors::ChorusResult,

View File

@ -1,11 +1,128 @@
use super::{event::Events, *}; use super::{event::Events, *};
use crate::types::{self, Composite}; use crate::types::{self, Composite};
#[async_trait(?Send)]
pub trait GatewayHandleCapable<R, S> pub trait GatewayHandleCapable<R, S>
where where
R: Stream, R: Stream,
S: Sink<Message>, S: Sink<Message>,
{ {
/// Sends json to the gateway with an opcode
async fn send_json_event(&self, op_code: u8, to_send: serde_json::Value);
/// Observes an Item `<T: Updateable>`, which will update itself, if new information about this
/// item arrives on the corresponding Gateway Thread
async fn observe<T: Updateable + Clone + Debug + Composite<T> + Send + Sync>(
&self,
object: Arc<RwLock<T>>,
) -> Arc<RwLock<T>>;
/// Recursively observes and updates all updateable fields on the struct T. Returns an object `T`
/// with all of its observable fields being observed.
async fn observe_and_into_inner<T: Updateable + Clone + Debug + Composite<T>>(
&self,
object: Arc<RwLock<T>>,
) -> T {
let channel = self.observe(object.clone()).await;
let object = channel.read().unwrap().clone();
object
}
/// Sends an identify event to the gateway
async fn send_identify(&self, to_send: types::GatewayIdentifyPayload) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Identify..");
self.send_json_event(GATEWAY_IDENTIFY, to_send_value).await;
}
/// Sends an update presence event to the gateway
async fn send_update_presence(&self, to_send: types::UpdatePresence) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Update Presence..");
self.send_json_event(GATEWAY_UPDATE_PRESENCE, to_send_value)
.await;
}
/// Sends a resume event to the gateway
async fn send_resume(&self, to_send: types::GatewayResume) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Resume..");
self.send_json_event(GATEWAY_RESUME, to_send_value).await;
}
/// Sends a request guild members to the server
async fn send_request_guild_members(&self, to_send: types::GatewayRequestGuildMembers) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Request Guild Members..");
self.send_json_event(GATEWAY_REQUEST_GUILD_MEMBERS, to_send_value)
.await;
}
/// Sends an update voice state to the server
async fn send_update_voice_state(&self, to_send: types::UpdateVoiceState) {
let to_send_value = serde_json::to_value(to_send).unwrap();
trace!("GW: Sending Update Voice State..");
self.send_json_event(GATEWAY_UPDATE_VOICE_STATE, to_send_value)
.await;
}
/// Sends a call sync to the server
async fn send_call_sync(&self, to_send: types::CallSync) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Call Sync..");
self.send_json_event(GATEWAY_CALL_SYNC, to_send_value).await;
}
/// Sends a Lazy Request
async fn send_lazy_request(&self, to_send: types::LazyRequest) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Lazy Request..");
self.send_json_event(GATEWAY_LAZY_REQUEST, to_send_value)
.await;
}
/// Closes the websocket connection and stops all gateway tasks;
///
/// Esentially pulls the plug on the gateway, leaving it possible to resume;
async fn close(&self);
}
#[async_trait(?Send)]
impl
GatewayHandleCapable<
WebSocketStream<MaybeTlsStream<TcpStream>>,
WebSocketStream<MaybeTlsStream<TcpStream>>,
> for GatewayHandle
{
async fn send_json_event(&self, op_code: u8, to_send: serde_json::Value) {
self.send_json_event(op_code, to_send).await
}
async fn observe<T: Updateable + Clone + Debug + Composite<T>>(
&self,
object: Arc<RwLock<T>>,
) -> Arc<RwLock<T>> {
self.observe(object).await
}
async fn close(&self) {
self.kill_send.send(()).unwrap();
self.websocket_send.lock().await.close().await.unwrap();
}
} }
/// Represents a handle to a Gateway connection. A Gateway connection will create observable /// Represents a handle to a Gateway connection. A Gateway connection will create observable
@ -30,7 +147,6 @@ pub struct GatewayHandle {
} }
impl GatewayHandle { impl GatewayHandle {
/// Sends json to the gateway with an opcode
async fn send_json_event(&self, op_code: u8, to_send: serde_json::Value) { async fn send_json_event(&self, op_code: u8, to_send: serde_json::Value) {
let gateway_payload = types::GatewaySendPayload { let gateway_payload = types::GatewaySendPayload {
op_code, op_code,
@ -89,98 +205,4 @@ impl GatewayHandle {
wrapped wrapped
} }
} }
/// Recursively observes and updates all updateable fields on the struct T. Returns an object `T`
/// with all of its observable fields being observed.
pub async fn observe_and_into_inner<T: Updateable + Clone + Debug + Composite<T>>(
&self,
object: Arc<RwLock<T>>,
) -> T {
let channel = self.observe(object.clone()).await;
let object = channel.read().unwrap().clone();
object
}
/// Sends an identify event to the gateway
pub async fn send_identify(&self, to_send: types::GatewayIdentifyPayload) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Identify..");
self.send_json_event(GATEWAY_IDENTIFY, to_send_value).await;
}
/// Sends a resume event to the gateway
pub async fn send_resume(&self, to_send: types::GatewayResume) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Resume..");
self.send_json_event(GATEWAY_RESUME, to_send_value).await;
}
/// Sends an update presence event to the gateway
pub async fn send_update_presence(&self, to_send: types::UpdatePresence) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Update Presence..");
self.send_json_event(GATEWAY_UPDATE_PRESENCE, to_send_value)
.await;
}
/// Sends a request guild members to the server
pub async fn send_request_guild_members(&self, to_send: types::GatewayRequestGuildMembers) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Request Guild Members..");
self.send_json_event(GATEWAY_REQUEST_GUILD_MEMBERS, to_send_value)
.await;
}
/// Sends an update voice state to the server
pub async fn send_update_voice_state(&self, to_send: types::UpdateVoiceState) {
let to_send_value = serde_json::to_value(to_send).unwrap();
trace!("GW: Sending Update Voice State..");
self.send_json_event(GATEWAY_UPDATE_VOICE_STATE, to_send_value)
.await;
}
/// Sends a call sync to the server
pub async fn send_call_sync(&self, to_send: types::CallSync) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Call Sync..");
self.send_json_event(GATEWAY_CALL_SYNC, to_send_value).await;
}
/// Sends a Lazy Request
pub async fn send_lazy_request(&self, to_send: types::LazyRequest) {
let to_send_value = serde_json::to_value(&to_send).unwrap();
trace!("GW: Sending Lazy Request..");
self.send_json_event(GATEWAY_LAZY_REQUEST, to_send_value)
.await;
}
/// Closes the websocket connection and stops all gateway tasks;
///
/// Esentially pulls the plug on the gateway, leaving it possible to resume;
pub async fn close(&self) {
self.kill_send.send(()).unwrap();
self.websocket_send.lock().await.close().await.unwrap();
}
}
impl
GatewayHandleCapable<
WebSocketStream<MaybeTlsStream<TcpStream>>,
WebSocketStream<MaybeTlsStream<TcpStream>>,
> for GatewayHandle
{
} }