//use app_auth::{UserCtx}; use kloud::{ defs::{ KloudQueryFilters, KloudQueryDefsFilters, KloudQueryLangFilters, // KloudReqData, KloudQueryConfigFilters, }, }; use crate::defs::DataDBs; use crate::handlers; use clds::clouds::defs::{Cloud}; use warp::{ filters::header::headers_cloned, filters::method::method, filters::BoxedFilter, Filter, }; /// The 4 ta filters combined. // #[must_use] // pub fn hello ( // //) -> impl Filter + Clone { // ) -> impl Filter + Clone { // warp::any().map(move|| "Hola, World!") // } /* let default_auth = warp::any().map(|| { // something default }); let auth = warp::header("authorization") .map(|token: String| { // something with token }) .or(default_auth) .unify(); let context_extractor = warp::any().and( warp::header::("authorization") .map(|token: String| -> Context { let token_data = match verify_jwt(token) { Ok(t) => t, Err(_) => return Context { user_id: 0 }, }; Context { user_id: token_data.claims.user_id, } }) .or(warp::any().map(|| Context { user_id: 0 })) .unify(), ); */ #[derive(Clone,Debug,Default)] pub struct CollFilters { pub prfx: String, // &'static str, } impl CollFilters { pub fn new(prfx: &str) -> Self { Self { prfx: String::from(prfx), } } pub fn filters_defs( &self, db: DataDBs, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let defs_path: &'static str = Box::leak(format!("{}defs",&self.prfx).into_boxed_str()); let lang_path: &'static str = Box::leak(format!("{}lang",&self.prfx).into_boxed_str()); self.list(db.clone(),defs_path,cors.clone()) .or(self.langs(db.clone(),lang_path,cors.clone())) .boxed() } pub fn filters_data( &self, db: DataDBs, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let list_path: &'static str = Box::leak(format!("{}data",&self.prfx).into_boxed_str()); // let table_path: &'static str = Box::leak(format!("{}table",&self.prfx).into_boxed_str()); let defs_path: &'static str = Box::leak(format!("{}defs",&self.prfx).into_boxed_str()); let lang_path: &'static str = Box::leak(format!("{}lang",&self.prfx).into_boxed_str()); let insert_path: &'static str = Box::leak(format!("{}insert",&self.prfx).into_boxed_str()); let delete_path: &'static str = Box::leak(format!("{}delete",&self.prfx).into_boxed_str()); self.list(db.clone(),list_path,cors.clone()) // .or(self.table(db.clone(),table_path,cors.clone())) .or(self.defs(db.clone(),defs_path,cors.clone())) .or(self.langs(db.clone(),lang_path,cors.clone())) // for others use "x" with path! macro .or(self.insert(db.clone(),insert_path,cors.clone())) // .or(self.update(db.clone())) .or(self.delete(db.clone(),delete_path,cors.clone())) .boxed() } pub fn filters_config( &self, db: DataDBs, cloud: Cloud, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let defs_path: &'static str = Box::leak(format!("{}defs",&self.prfx).into_boxed_str()); let lang_path: &'static str = Box::leak(format!("{}lang",&self.prfx).into_boxed_str()); let config_path: &'static str = Box::leak(format!("{}config",&self.prfx).into_boxed_str()); let provision_path: &'static str = Box::leak(format!("{}provision",&self.prfx).into_boxed_str()); let status_path: &'static str = Box::leak(format!("{}status",&self.prfx).into_boxed_str()); let liveness_path: &'static str = Box::leak(format!("{}liveness",&self.prfx).into_boxed_str()); self.config(db.clone(),cloud.clone(),config_path,cors.clone()) .or(self.defs(db.clone(),defs_path,cors.clone())) .or(self.langs(db.clone(),lang_path,cors.clone())) .or(self.provision(db.clone(),cloud.clone(),provision_path,cors.clone())) .or(self.status(db.clone(),cloud.clone(),status_path,cors.clone())) .or(self.liveness(db.clone(),cloud.clone(),liveness_path,cors.clone())) .boxed() } /// GET /ta?offset=3&limit=5 pub fn list( &self, db: DataDBs, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) .and(warp::query::()) .and(headers_cloned()) .and(method()) // .and_then(user_authentication) // .and(warp::header::optional::("authorization")) // .and(warp::header::optional::("accept-language")) .and(self.with_db(db)) .and(warp::any().map(move || prfx.to_owned())) // and(self.with_auth(db.app.clone(),db.auth.clone())) //.and(warp::any().map(move || &self.clone().db)) // .map(|method: warp::http::Method, path: warp::path::FullPath, headers: warp::http::HeaderMap, opts: TaQueryFilters, db: AppDB | { // dbg!(&headers); // dbg!(&path); // let mut req = warp::http::Request::builder() // .method(method) // .uri(path.as_str()) // ; // // // .body(body) // // .expect("request builder"); // // { *req.headers_mut() = headers; } // req // }) .and_then(handlers::h_data::list) .with(cors) .boxed() } /* /// GET /ta?offset=3&limit=5 pub fn table( &self, db: DataDBs, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) .and(warp::query::()) .and(headers_cloned()) .and(method()) .and(self.with_db(db)) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_data::table) .with(cors) .boxed() } */ /// GET /ta?offset=3&limit=5 pub fn defs( &self, db: DataDBs, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) .and(warp::query::()) .and(headers_cloned()) .and(method()) .and(self.with_db(db)) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_defs::defs) .with(cors) .boxed() } /// POST /ta with JSON body pub fn langs( &self, db: DataDBs, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { // warp::any().and( let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) // .and(warp::query::()) // .and(warp::filters::query::raw()) // .or(warp::any().map(|| String::default())) // .unify() .and(warp::query::()) .and(headers_cloned()) .and(method()) // .and(with_auth(db.app.clone(),db.auth.clone())) .and(self.with_db(db)) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_defs::langs) .with(cors) .boxed() } /// POST /ta with JSON body pub fn insert( &self, db: DataDBs, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::post()) .and(warp::body::json()) .and(headers_cloned()) .and(method()) .and(self.with_db(db)) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_data::insert) .with(cors) .boxed() } // /// PUT /ta/:id with JSON body // pub fn update( // &self, // db: DataDBs, // //) -> impl Filter + Clone { // ) -> BoxedFilter<(impl warp::Reply,)> { // let prfx = self.prfx.to_owned(); // warp::path(prfx.to_owned()) // , String) // .and(warp::path::param()) // .and(warp::put()) // .and(self.json_body()) // .and(self.with_db(db)) // .and(warp::any().map(move || prfx.to_owned())) // .and_then(handlers::h_data::update) // .boxed() // } /// DELETE /ta/:id pub fn delete( &self, db: DataDBs, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { // We'll make one of our endpoints admin-only to show how authentication filters are used // let admin_only = warp::header::exact("authorization", "Bearer admin"); let prfx = self.prfx.to_owned(); warp::path(path) // .and(warp::path::param()) // It is important to put the auth check _after_ the path filters. // If we put the auth check before, the request `PUT /ta/invalid-string` // would try this filter and reject because the authorization header doesn't match, // rather because the param is wrong for that other path. // .and(admin_only) // .and(warp::delete()) .and(warp::post()) .and(warp::body::json()) .and(headers_cloned()) .and(method()) .and(self.with_db(db)) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_data::delete) .with(cors) .boxed() } /// GET /config?offset=3&limit=5 pub fn config( &self, db: DataDBs, cloud: Cloud, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) .and(warp::query::()) .and(headers_cloned()) .and(method()) // .and_then(user_authentication) // .and(warp::header::optional::("authorization")) // .and(warp::header::optional::("accept-language")) .and(self.with_db(db)) .and(warp::any().map(move || cloud.to_owned())) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_config::config) .with(cors) .boxed() } /// GET /provision?offset=3&limit=5 pub fn provision( &self, db: DataDBs, cloud: Cloud, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) .and(warp::query::()) .and(headers_cloned()) .and(method()) // .and_then(user_authentication) // .and(warp::header::optional::("authorization")) // .and(warp::header::optional::("accept-language")) .and(self.with_db(db)) .and(warp::any().map(move || cloud.to_owned())) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_config::provision) .with(cors) .boxed() } /// GET /status?offset=3&limit=5 pub fn status( &self, db: DataDBs, cloud: Cloud, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) .and(warp::query::()) .and(headers_cloned()) .and(method()) // .and_then(user_authentication) // .and(warp::header::optional::("authorization")) // .and(warp::header::optional::("accept-language")) .and(self.with_db(db)) .and(warp::any().map(move || cloud.to_owned())) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_config::status) .with(cors) .boxed() } /// GET /status?offset=3&limit=5 pub fn liveness( &self, db: DataDBs, cloud: Cloud, path: &'static str, cors: warp::cors::Builder, //) -> impl Filter + Clone { ) -> BoxedFilter<(impl warp::Reply,)> { let prfx = self.prfx.to_owned(); warp::path(path) .and(warp::get()) .and(warp::query::()) .and(headers_cloned()) .and(method()) // .and_then(user_authentication) // .and(warp::header::optional::("authorization")) // .and(warp::header::optional::("accept-language")) .and(self.with_db(db)) .and(warp::any().map(move || cloud.to_owned())) .and(warp::any().map(move || prfx.to_owned())) .and_then(handlers::h_config::liveness) .with(cors) .boxed() } fn with_db(&self, db: DataDBs) -> impl Filter + Clone { warp::any().map(move || db.clone()) } // fn json_body(&self) -> impl Filter + Clone { // // When accepting a body, we want a JSON body // // (and to reject huge payloads)... // warp::body::content_length_limit(1024 * 16).and(warp::body::json()) // } }