1use std::future::Future;
2
3use crate::action::ChatActionGuard;
4use crate::context::Context;
5
6#[cfg(not(target_arch = "wasm32"))]
7pub trait FromContextBounds: Send {}
8#[cfg(not(target_arch = "wasm32"))]
9impl<T: Send> FromContextBounds for T {}
10
11#[cfg(target_arch = "wasm32")]
12pub trait FromContextBounds {}
13#[cfg(target_arch = "wasm32")]
14impl<T> FromContextBounds for T {}
15
16#[cfg(not(target_arch = "wasm32"))]
17pub trait ContextFutureBounds: Future + Send {}
18#[cfg(not(target_arch = "wasm32"))]
19impl<T: Future + Send + ?Sized> ContextFutureBounds for T {}
20
21#[cfg(target_arch = "wasm32")]
22pub trait ContextFutureBounds: Future {}
23#[cfg(target_arch = "wasm32")]
24impl<T: Future + ?Sized> ContextFutureBounds for T {}
25
26pub trait FromContext: Sized + FromContextBounds {
43 fn from_context(ctx: &Context) -> impl ContextFutureBounds<Output = Self>;
45}
46
47impl FromContext for Context {
49 async fn from_context(ctx: &Context) -> Self {
50 ctx.clone()
51 }
52}
53
54#[derive(Debug, Clone)]
56pub struct User {
57 pub id: String,
58 pub name: String,
59}
60
61impl FromContext for User {
62 async fn from_context(ctx: &Context) -> Self {
63 Self {
64 id: ctx.user_id().to_string(),
65 name: ctx.user_name().to_string(),
66 }
67 }
68}
69
70#[derive(Debug, Clone)]
72pub struct Channel {
73 pub id: String,
74}
75
76impl FromContext for Channel {
77 async fn from_context(ctx: &Context) -> Self {
78 Self {
79 id: ctx.channel_id().to_string(),
80 }
81 }
82}
83
84#[derive(Debug, Clone)]
86pub struct CommandName(pub String);
87
88impl FromContext for CommandName {
89 async fn from_context(ctx: &Context) -> Self {
90 Self(ctx.command_name().unwrap_or_default().to_string())
91 }
92}
93
94#[derive(Debug, Clone)]
96pub struct CommandArgs(pub String);
97
98impl FromContext for CommandArgs {
99 async fn from_context(ctx: &Context) -> Self {
100 Self(ctx.command_args().unwrap_or_default().to_string())
101 }
102}
103
104#[derive(Debug, Clone)]
106pub struct ButtonId(pub String);
107
108impl FromContext for ButtonId {
109 async fn from_context(ctx: &Context) -> Self {
110 Self(ctx.button_id().unwrap_or_default().to_string())
111 }
112}
113
114#[derive(Debug, Clone)]
116pub struct MessageContent(pub String);
117
118impl FromContext for MessageContent {
119 async fn from_context(ctx: &Context) -> Self {
120 Self(ctx.message_content().unwrap_or_default().to_string())
121 }
122}
123
124impl FromContext for () {
126 async fn from_context(_ctx: &Context) -> Self {}
127}
128
129impl<T1: FromContext> FromContext for (T1,) {
130 async fn from_context(ctx: &Context) -> Self {
131 (T1::from_context(ctx).await,)
132 }
133}
134
135impl<T1: FromContext, T2: FromContext> FromContext for (T1, T2) {
136 async fn from_context(ctx: &Context) -> Self {
137 let t1 = T1::from_context(ctx).await;
138 let t2 = T2::from_context(ctx).await;
139 (t1, t2)
140 }
141}
142
143impl<T1: FromContext, T2: FromContext, T3: FromContext> FromContext for (T1, T2, T3) {
144 async fn from_context(ctx: &Context) -> Self {
145 let t1 = T1::from_context(ctx).await;
146 let t2 = T2::from_context(ctx).await;
147 let t3 = T3::from_context(ctx).await;
148 (t1, t2, t3)
149 }
150}
151
152impl<T1: FromContext, T2: FromContext, T3: FromContext, T4: FromContext> FromContext
153 for (T1, T2, T3, T4)
154{
155 async fn from_context(ctx: &Context) -> Self {
156 let t1 = T1::from_context(ctx).await;
157 let t2 = T2::from_context(ctx).await;
158 let t3 = T3::from_context(ctx).await;
159 let t4 = T4::from_context(ctx).await;
160 (t1, t2, t3, t4)
161 }
162}
163
164pub struct Typing(pub Option<ChatActionGuard>);
177
178impl FromContext for Typing {
179 async fn from_context(ctx: &Context) -> Self {
180 Self(ctx.typing())
181 }
182}