1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132
use std::fmt; use std::pin::Pin; use async_trait::async_trait; use futures::Future; use tc_error::*; use tcgeneric::{Map, PathSegment, TCPath}; use crate::scalar::{OpRefType as ORT, Value}; use crate::state::State; use crate::txn::Txn; mod chain; mod cluster; mod collection; mod generic; mod object; mod scalar; mod state; pub type GetFuture<'a> = Pin<Box<dyn Future<Output = TCResult<State>> + Send + 'a>>; pub type GetHandler<'a> = Box<dyn FnOnce(Txn, Value) -> GetFuture<'a> + Send + 'a>; pub type PutFuture<'a> = Pin<Box<dyn Future<Output = TCResult<()>> + Send + 'a>>; pub type PutHandler<'a> = Box<dyn FnOnce(Txn, Value, State) -> PutFuture<'a> + Send + 'a>; pub type PostFuture<'a> = Pin<Box<dyn Future<Output = TCResult<State>> + Send + 'a>>; pub type PostHandler<'a> = Box<dyn FnOnce(Txn, Map<State>) -> PostFuture<'a> + Send + 'a>; pub type DeleteFuture<'a> = Pin<Box<dyn Future<Output = TCResult<()>> + Send + 'a>>; pub type DeleteHandler<'a> = Box<dyn FnOnce(Txn, Value) -> DeleteFuture<'a> + Send + 'a>; pub trait Handler<'a>: Send { fn get(self: Box<Self>) -> Option<GetHandler<'a>> { None } fn put(self: Box<Self>) -> Option<PutHandler<'a>> { None } fn post(self: Box<Self>) -> Option<PostHandler<'a>> { None } fn delete(self: Box<Self>) -> Option<DeleteHandler<'a>> { None } } pub trait Route: Send + Sync { fn route<'a>(&'a self, path: &'a [PathSegment]) -> Option<Box<dyn Handler<'a> + 'a>>; } #[async_trait] pub trait Public { async fn get(&self, txn: &Txn, path: &[PathSegment], key: Value) -> TCResult<State>; async fn put(&self, txn: &Txn, path: &[PathSegment], key: Value, value: State) -> TCResult<()>; async fn post(&self, txn: &Txn, path: &[PathSegment], params: Map<State>) -> TCResult<State>; async fn delete(&self, txn: &Txn, path: &[PathSegment], key: Value) -> TCResult<()>; } #[async_trait] impl<T: Route + fmt::Display> Public for T { async fn get(&self, txn: &Txn, path: &[PathSegment], key: Value) -> TCResult<State> { let handler = self .route(path) .ok_or_else(|| TCError::not_found(TCPath::from(path)))?; if let Some(get_handler) = handler.get() { get_handler(txn.clone(), key).await } else { Err(TCError::method_not_allowed( ORT::Get, self, TCPath::from(path), )) } } async fn put(&self, txn: &Txn, path: &[PathSegment], key: Value, value: State) -> TCResult<()> { let handler = self .route(path) .ok_or_else(|| TCError::not_found(TCPath::from(path)))?; if let Some(put_handler) = handler.put() { put_handler(txn.clone(), key, value).await } else { Err(TCError::method_not_allowed( ORT::Put, self, TCPath::from(path), )) } } async fn post(&self, txn: &Txn, path: &[PathSegment], params: Map<State>) -> TCResult<State> { let handler = self .route(path) .ok_or_else(|| TCError::not_found(TCPath::from(path)))?; if let Some(post_handler) = handler.post() { post_handler(txn.clone(), params).await } else { Err(TCError::method_not_allowed( ORT::Post, self, TCPath::from(path), )) } } async fn delete(&self, txn: &Txn, path: &[PathSegment], key: Value) -> TCResult<()> { let handler = self .route(path) .ok_or_else(|| TCError::not_found(TCPath::from(path)))?; if let Some(delete_handler) = handler.delete() { delete_handler(txn.clone(), key).await } else { Err(TCError::method_not_allowed( ORT::Delete, self, TCPath::from(path), )) } } }