use ruma::{
api::client::{account::request_openid_token, delayed_events},
events::{AnyStateEvent, AnyTimelineEvent, AnyToDeviceEvent},
serde::Raw,
};
use serde::{Deserialize, Deserializer, de};
use serde_json::value::RawValue as RawJsonValue;
use uuid::Uuid;
#[cfg(doc)]
use super::MatrixDriverRequestData;
use super::{
SendToDeviceEventResponse,
from_widget::{FromWidgetRequest, SendEventResponse},
to_widget::ToWidgetResponse,
};
use crate::widget::Capabilities;
pub(crate) enum IncomingMessage {
WidgetMessage(String),
MatrixDriverResponse {
request_id: Uuid,
response: Result<MatrixDriverResponse, crate::Error>,
},
MatrixEventReceived(Raw<AnyTimelineEvent>),
StateUpdateReceived(Vec<Raw<AnyStateEvent>>),
ToDeviceReceived(Raw<AnyToDeviceEvent>),
}
pub(crate) enum MatrixDriverResponse {
CapabilitiesAcquired(Capabilities),
OpenIdReceived(request_openid_token::v3::Response),
EventsRead(Vec<Raw<AnyTimelineEvent>>),
StateRead(Vec<Raw<AnyStateEvent>>),
EventSent(SendEventResponse),
ToDeviceSent(SendToDeviceEventResponse),
DelayedEventUpdated(delayed_events::update_delayed_event::unstable::Response),
}
pub(super) struct IncomingWidgetMessage {
pub(super) widget_id: String,
pub(super) request_id: String,
pub(super) kind: IncomingWidgetMessageKind,
}
#[derive(Debug)]
pub(super) enum IncomingWidgetMessageKind {
Request(Raw<FromWidgetRequest>),
Response(ToWidgetResponse),
}
impl<'de> Deserialize<'de> for IncomingWidgetMessage {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: Deserializer<'de>,
{
let raw: Box<RawJsonValue> = Box::deserialize(deserializer)?;
#[derive(Deserialize)]
#[serde(rename_all = "camelCase")]
enum ApiTag {
FromWidget,
ToWidget,
}
#[derive(Deserialize)]
#[serde(rename_all = "camelCase")]
struct ExtractHeader {
api: ApiTag,
widget_id: String,
request_id: String,
}
let ExtractHeader { api, widget_id, request_id } =
serde_json::from_str(raw.get()).map_err(de::Error::custom)?;
let kind = match api {
ApiTag::FromWidget => IncomingWidgetMessageKind::Request(Raw::from_json(raw)),
ApiTag::ToWidget => serde_json::from_str(raw.get())
.map(IncomingWidgetMessageKind::Response)
.map_err(de::Error::custom)?,
};
Ok(Self { widget_id, request_id, kind })
}
}