1use serde::de::DeserializeOwned;
4use serde::Serialize;
5use std::{
6 any::Any,
7 fmt,
8 future::Future,
9 ops::Deref,
10 pin::Pin,
11 sync::Arc,
12};
13
14pub trait IntoHandlerResult: Send {
23 fn into_handler_result(self) -> Result<String, String>;
25}
26
27impl IntoHandlerResult for String {
29 fn into_handler_result(self) -> Result<String, String> {
30 Ok(self)
31 }
32}
33
34pub struct Json<T>(pub T);
39
40impl<T: Serialize + Send> IntoHandlerResult for Json<T> {
41 fn into_handler_result(self) -> Result<String, String> {
42 serde_json::to_string(&self.0)
43 .map_err(|e| format!("Failed to serialize response: {e}"))
44 }
45}
46
47impl<T: Serialize + Send, E: fmt::Display + Send> IntoHandlerResult for Result<T, E> {
49 fn into_handler_result(self) -> Result<String, String> {
50 match self {
51 Ok(value) => serde_json::to_string(&value)
52 .map_err(|e| format!("Failed to serialize response: {e}")),
53 Err(e) => Err(e.to_string()),
54 }
55 }
56}
57
58pub trait Handler: Send + Sync {
65 fn call(&self, args: &str) -> Pin<Box<dyn Future<Output = Result<String, String>> + Send + '_>>;
67}
68
69#[derive(Debug, Clone)]
75pub struct State<S>(pub S);
76
77impl<S> Deref for State<S> {
78 type Target = S;
79
80 fn deref(&self) -> &Self::Target {
81 &self.0
82 }
83}
84
85pub struct HandlerFn<F, Fut, R>
89where
90 F: Fn() -> Fut + Send + Sync,
91 Fut: Future<Output = R> + Send,
92 R: IntoHandlerResult,
93{
94 func: F,
95 _marker: std::marker::PhantomData<fn() -> R>,
96}
97
98impl<F, Fut, R> HandlerFn<F, Fut, R>
99where
100 F: Fn() -> Fut + Send + Sync,
101 Fut: Future<Output = R> + Send,
102 R: IntoHandlerResult,
103{
104 pub fn new(func: F) -> Self {
106 Self {
107 func,
108 _marker: std::marker::PhantomData,
109 }
110 }
111}
112
113impl<F, Fut, R> Handler for HandlerFn<F, Fut, R>
114where
115 F: Fn() -> Fut + Send + Sync + 'static,
116 Fut: Future<Output = R> + Send + 'static,
117 R: IntoHandlerResult + 'static,
118{
119 fn call(&self, _args: &str) -> Pin<Box<dyn Future<Output = Result<String, String>> + Send + '_>> {
120 let fut = (self.func)();
121 Box::pin(async move { fut.await.into_handler_result() })
122 }
123}
124
125pub struct HandlerWithArgs<F, T, Fut, R>
127where
128 F: Fn(T) -> Fut + Send + Sync,
129 T: DeserializeOwned + Send,
130 Fut: Future<Output = R> + Send,
131 R: IntoHandlerResult,
132{
133 func: F,
134 _marker: std::marker::PhantomData<(fn() -> T, fn() -> R)>,
137}
138
139impl<F, T, Fut, R> HandlerWithArgs<F, T, Fut, R>
140where
141 F: Fn(T) -> Fut + Send + Sync,
142 T: DeserializeOwned + Send,
143 Fut: Future<Output = R> + Send,
144 R: IntoHandlerResult,
145{
146 pub fn new(func: F) -> Self {
148 Self {
149 func,
150 _marker: std::marker::PhantomData,
151 }
152 }
153}
154
155impl<F, T, Fut, R> Handler for HandlerWithArgs<F, T, Fut, R>
156where
157 F: Fn(T) -> Fut + Send + Sync + 'static,
158 T: DeserializeOwned + Send + 'static,
159 Fut: Future<Output = R> + Send + 'static,
160 R: IntoHandlerResult + 'static,
161{
162 fn call(&self, args: &str) -> Pin<Box<dyn Future<Output = Result<String, String>> + Send + '_>> {
163 let parsed: Result<T, _> = serde_json::from_str(args);
164 match parsed {
165 Ok(value) => {
166 let fut = (self.func)(value);
167 Box::pin(async move { fut.await.into_handler_result() })
168 }
169 Err(e) => Box::pin(async move {
170 Err(format!("Failed to deserialize args: {e}"))
171 }),
172 }
173 }
174}
175
176pub struct HandlerWithState<F, S, T, Fut, R>
178where
179 F: Fn(State<Arc<S>>, T) -> Fut + Send + Sync,
180 S: Send + Sync + 'static,
181 T: DeserializeOwned + Send,
182 Fut: Future<Output = R> + Send,
183 R: IntoHandlerResult,
184{
185 func: F,
186 state: Arc<dyn Any + Send + Sync>,
187 _marker: std::marker::PhantomData<(fn() -> S, fn() -> T, fn() -> R)>,
188}
189
190impl<F, S, T, Fut, R> HandlerWithState<F, S, T, Fut, R>
191where
192 F: Fn(State<Arc<S>>, T) -> Fut + Send + Sync,
193 S: Send + Sync + 'static,
194 T: DeserializeOwned + Send,
195 Fut: Future<Output = R> + Send,
196 R: IntoHandlerResult,
197{
198 pub fn new(func: F, state: Arc<dyn Any + Send + Sync>) -> Self {
200 Self {
201 func,
202 state,
203 _marker: std::marker::PhantomData,
204 }
205 }
206}
207
208impl<F, S, T, Fut, R> Handler for HandlerWithState<F, S, T, Fut, R>
209where
210 F: Fn(State<Arc<S>>, T) -> Fut + Send + Sync + 'static,
211 S: Send + Sync + 'static,
212 T: DeserializeOwned + Send + 'static,
213 Fut: Future<Output = R> + Send + 'static,
214 R: IntoHandlerResult + 'static,
215{
216 fn call(&self, args: &str) -> Pin<Box<dyn Future<Output = Result<String, String>> + Send + '_>> {
217 let state_arc = match self.state.clone().downcast::<S>() {
218 Ok(s) => s,
219 Err(_) => {
220 let msg = format!(
221 "State type mismatch: expected {}",
222 std::any::type_name::<S>()
223 );
224 return Box::pin(async move { Err(msg) });
225 }
226 };
227
228 let parsed: Result<T, _> = serde_json::from_str(args);
229 match parsed {
230 Ok(value) => {
231 let fut = (self.func)(State(state_arc), value);
232 Box::pin(async move { fut.await.into_handler_result() })
233 }
234 Err(e) => Box::pin(async move {
235 Err(format!("Failed to deserialize args: {e}"))
236 }),
237 }
238 }
239}
240
241pub struct HandlerWithStateOnly<F, S, Fut, R>
243where
244 F: Fn(State<Arc<S>>) -> Fut + Send + Sync,
245 S: Send + Sync + 'static,
246 Fut: Future<Output = R> + Send,
247 R: IntoHandlerResult,
248{
249 func: F,
250 state: Arc<dyn Any + Send + Sync>,
251 _marker: std::marker::PhantomData<(fn() -> S, fn() -> R)>,
252}
253
254impl<F, S, Fut, R> HandlerWithStateOnly<F, S, Fut, R>
255where
256 F: Fn(State<Arc<S>>) -> Fut + Send + Sync,
257 S: Send + Sync + 'static,
258 Fut: Future<Output = R> + Send,
259 R: IntoHandlerResult,
260{
261 pub fn new(func: F, state: Arc<dyn Any + Send + Sync>) -> Self {
263 Self {
264 func,
265 state,
266 _marker: std::marker::PhantomData,
267 }
268 }
269}
270
271impl<F, S, Fut, R> Handler for HandlerWithStateOnly<F, S, Fut, R>
272where
273 F: Fn(State<Arc<S>>) -> Fut + Send + Sync + 'static,
274 S: Send + Sync + 'static,
275 Fut: Future<Output = R> + Send + 'static,
276 R: IntoHandlerResult + 'static,
277{
278 fn call(&self, _args: &str) -> Pin<Box<dyn Future<Output = Result<String, String>> + Send + '_>> {
279 let state_arc = match self.state.clone().downcast::<S>() {
280 Ok(s) => s,
281 Err(_) => {
282 let msg = format!(
283 "State type mismatch: expected {}",
284 std::any::type_name::<S>()
285 );
286 return Box::pin(async move { Err(msg) });
287 }
288 };
289
290 let fut = (self.func)(State(state_arc));
291 Box::pin(async move { fut.await.into_handler_result() })
292 }
293}
294
295#[cfg(test)]
296mod tests {
297 use super::*;
298
299 #[tokio::test]
302 async fn test_handler_fn() {
303 let handler = HandlerFn::new(|| async { "test".to_string() });
304 let result = handler.call("{}").await;
305 assert_eq!(result, Ok("test".to_string()));
306 }
307
308 #[tokio::test]
309 async fn test_handler_fn_ignores_args() {
310 let handler = HandlerFn::new(|| async { "no-args".to_string() });
311 let result = handler.call(r#"{"unexpected": true}"#).await;
312 assert_eq!(result, Ok("no-args".to_string()));
313 }
314
315 #[tokio::test]
316 async fn test_handler_with_args() {
317 #[derive(serde::Deserialize)]
318 struct Input {
319 name: String,
320 }
321
322 let handler = HandlerWithArgs::new(|args: Input| async move {
323 format!("hello {}", args.name)
324 });
325
326 let result = handler.call(r#"{"name":"Alice"}"#).await;
327 assert_eq!(result, Ok("hello Alice".to_string()));
328 }
329
330 #[tokio::test]
331 async fn test_handler_with_args_bad_json() {
332 #[derive(serde::Deserialize)]
333 struct Input {
334 _name: String,
335 }
336
337 let handler = HandlerWithArgs::new(|_args: Input| async move {
338 "unreachable".to_string()
339 });
340
341 let result = handler.call("not-json").await;
342 assert!(result.is_err());
343 assert!(result.unwrap_err().contains("Failed to deserialize args"));
344 }
345
346 #[tokio::test]
347 async fn test_handler_with_args_missing_field() {
348 #[derive(serde::Deserialize)]
349 struct Input {
350 _name: String,
351 }
352
353 let handler = HandlerWithArgs::new(|_args: Input| async move {
354 "unreachable".to_string()
355 });
356
357 let result = handler.call(r#"{"age": 30}"#).await;
358 assert!(result.is_err());
359 assert!(result.unwrap_err().contains("Failed to deserialize args"));
360 }
361
362 #[tokio::test]
363 async fn test_handler_with_state() {
364 struct AppState {
365 greeting: String,
366 }
367
368 #[derive(serde::Deserialize)]
369 struct Input {
370 name: String,
371 }
372
373 let state: Arc<dyn Any + Send + Sync> = Arc::new(AppState {
374 greeting: "Hi".to_string(),
375 });
376
377 let handler = HandlerWithState::new(
378 |state: State<Arc<AppState>>, args: Input| async move {
379 format!("{} {}", state.greeting, args.name)
380 },
381 state,
382 );
383
384 let result = handler.call(r#"{"name":"Bob"}"#).await;
385 assert_eq!(result, Ok("Hi Bob".to_string()));
386 }
387
388 #[tokio::test]
389 async fn test_handler_with_state_only() {
390 struct AppState {
391 value: i32,
392 }
393
394 let state: Arc<dyn Any + Send + Sync> = Arc::new(AppState { value: 42 });
395
396 let handler = HandlerWithStateOnly::new(
397 |state: State<Arc<AppState>>| async move {
398 format!("value={}", state.value)
399 },
400 state,
401 );
402
403 let result = handler.call("{}").await;
404 assert_eq!(result, Ok("value=42".to_string()));
405 }
406
407 #[tokio::test]
408 async fn test_handler_with_state_deser_error() {
409 struct AppState;
410
411 #[derive(serde::Deserialize)]
412 struct Input {
413 _x: i32,
414 }
415
416 let state: Arc<dyn Any + Send + Sync> = Arc::new(AppState);
417
418 let handler = HandlerWithState::new(
419 |_state: State<Arc<AppState>>, _args: Input| async move {
420 "unreachable".to_string()
421 },
422 state,
423 );
424
425 let result = handler.call("bad").await;
426 assert!(result.is_err());
427 assert!(result.unwrap_err().contains("Failed to deserialize args"));
428 }
429
430 #[tokio::test]
433 async fn test_json_handler_fn_struct() {
434 #[derive(serde::Serialize)]
435 struct User {
436 id: u32,
437 name: String,
438 }
439
440 let handler = HandlerFn::new(|| async {
441 Json(User {
442 id: 1,
443 name: "Alice".to_string(),
444 })
445 });
446
447 let result = handler.call("{}").await;
448 assert_eq!(result, Ok(r#"{"id":1,"name":"Alice"}"#.to_string()));
449 }
450
451 #[tokio::test]
452 async fn test_json_handler_fn_vec() {
453 let handler = HandlerFn::new(|| async { Json(vec![1, 2, 3]) });
454 let result = handler.call("{}").await;
455 assert_eq!(result, Ok("[1,2,3]".to_string()));
456 }
457
458 #[tokio::test]
459 async fn test_json_handler_with_args() {
460 #[derive(serde::Deserialize)]
461 struct Input {
462 name: String,
463 }
464
465 #[derive(serde::Serialize)]
466 struct Output {
467 greeting: String,
468 }
469
470 let handler = HandlerWithArgs::new(|args: Input| async move {
471 Json(Output {
472 greeting: format!("Hello {}", args.name),
473 })
474 });
475
476 let result = handler.call(r#"{"name":"Bob"}"#).await;
477 assert_eq!(result, Ok(r#"{"greeting":"Hello Bob"}"#.to_string()));
478 }
479
480 #[tokio::test]
481 async fn test_json_handler_with_args_bad_json() {
482 #[derive(serde::Deserialize)]
483 struct Input {
484 _x: i32,
485 }
486
487 let handler = HandlerWithArgs::new(|_: Input| async move { Json(42) });
488 let result = handler.call("bad").await;
489 assert!(result.is_err());
490 assert!(result.unwrap_err().contains("Failed to deserialize args"));
491 }
492
493 #[tokio::test]
494 async fn test_json_handler_with_state() {
495 struct AppState {
496 prefix: String,
497 }
498
499 #[derive(serde::Deserialize)]
500 struct Input {
501 name: String,
502 }
503
504 #[derive(serde::Serialize)]
505 struct Output {
506 message: String,
507 }
508
509 let state: Arc<dyn Any + Send + Sync> = Arc::new(AppState {
510 prefix: "Hi".to_string(),
511 });
512
513 let handler = HandlerWithState::new(
514 |state: State<Arc<AppState>>, args: Input| async move {
515 Json(Output {
516 message: format!("{} {}", state.prefix, args.name),
517 })
518 },
519 state,
520 );
521
522 let result = handler.call(r#"{"name":"Charlie"}"#).await;
523 assert_eq!(result, Ok(r#"{"message":"Hi Charlie"}"#.to_string()));
524 }
525
526 #[tokio::test]
527 async fn test_json_handler_with_state_only() {
528 struct AppState {
529 version: String,
530 }
531
532 #[derive(serde::Serialize)]
533 struct Info {
534 version: String,
535 }
536
537 let state: Arc<dyn Any + Send + Sync> = Arc::new(AppState {
538 version: "1.0".to_string(),
539 });
540
541 let handler = HandlerWithStateOnly::new(
542 |state: State<Arc<AppState>>| async move {
543 Json(Info {
544 version: state.version.clone(),
545 })
546 },
547 state,
548 );
549
550 let result = handler.call("{}").await;
551 assert_eq!(result, Ok(r#"{"version":"1.0"}"#.to_string()));
552 }
553
554 #[tokio::test]
557 async fn test_result_handler_fn_ok() {
558 #[derive(serde::Serialize)]
559 struct Data {
560 value: i32,
561 }
562
563 let handler = HandlerFn::new(|| async {
564 Ok::<_, String>(Data { value: 42 })
565 });
566
567 let result = handler.call("{}").await;
568 assert_eq!(result, Ok(r#"{"value":42}"#.to_string()));
569 }
570
571 #[tokio::test]
572 async fn test_result_handler_fn_err() {
573 #[derive(serde::Serialize)]
574 struct Data {
575 value: i32,
576 }
577
578 let handler = HandlerFn::new(|| async {
579 Err::<Data, String>("something went wrong".to_string())
580 });
581
582 let result = handler.call("{}").await;
583 assert_eq!(result, Err("something went wrong".to_string()));
584 }
585
586 #[tokio::test]
587 async fn test_result_handler_with_args_ok() {
588 #[derive(serde::Deserialize)]
589 struct Input {
590 x: i32,
591 }
592
593 #[derive(serde::Serialize)]
594 struct Output {
595 doubled: i32,
596 }
597
598 let handler = HandlerWithArgs::new(|args: Input| async move {
599 Ok::<_, String>(Output { doubled: args.x * 2 })
600 });
601
602 let result = handler.call(r#"{"x":21}"#).await;
603 assert_eq!(result, Ok(r#"{"doubled":42}"#.to_string()));
604 }
605
606 #[tokio::test]
607 async fn test_result_handler_with_args_err() {
608 #[derive(serde::Deserialize)]
609 struct Input {
610 x: i32,
611 }
612
613 let handler = HandlerWithArgs::new(|args: Input| async move {
614 if args.x < 0 {
615 Err::<i32, String>("negative".to_string())
616 } else {
617 Ok(args.x)
618 }
619 });
620
621 let result = handler.call(r#"{"x":-1}"#).await;
622 assert_eq!(result, Err("negative".to_string()));
623 }
624
625 #[tokio::test]
626 async fn test_result_handler_with_state() {
627 struct AppState {
628 threshold: i32,
629 }
630
631 #[derive(serde::Deserialize)]
632 struct Input {
633 value: i32,
634 }
635
636 #[derive(serde::Serialize)]
637 struct Output {
638 accepted: bool,
639 }
640
641 let state: Arc<dyn Any + Send + Sync> = Arc::new(AppState { threshold: 10 });
642
643 let handler = HandlerWithState::new(
644 |state: State<Arc<AppState>>, args: Input| async move {
645 if args.value >= state.threshold {
646 Ok::<_, String>(Output { accepted: true })
647 } else {
648 Err("below threshold".to_string())
649 }
650 },
651 state,
652 );
653
654 let ok_result = handler.call(r#"{"value":15}"#).await;
655 assert_eq!(ok_result, Ok(r#"{"accepted":true}"#.to_string()));
656
657 let err_result = handler.call(r#"{"value":5}"#).await;
658 assert_eq!(err_result, Err("below threshold".to_string()));
659 }
660
661 #[tokio::test]
662 async fn test_result_handler_with_state_only() {
663 struct AppState {
664 ready: bool,
665 }
666
667 #[derive(serde::Serialize)]
668 struct Status {
669 ok: bool,
670 }
671
672 let state: Arc<dyn Any + Send + Sync> = Arc::new(AppState { ready: true });
673
674 let handler = HandlerWithStateOnly::new(
675 |state: State<Arc<AppState>>| async move {
676 if state.ready {
677 Ok::<_, String>(Status { ok: true })
678 } else {
679 Err("not ready".to_string())
680 }
681 },
682 state,
683 );
684
685 let result = handler.call("{}").await;
686 assert_eq!(result, Ok(r#"{"ok":true}"#.to_string()));
687 }
688}