adding url_extract to servme
This commit is contained in:
		@@ -3,7 +3,9 @@ mod config;
 | 
			
		||||
mod requester;
 | 
			
		||||
mod responder;
 | 
			
		||||
mod server;
 | 
			
		||||
mod url_extract;
 | 
			
		||||
 | 
			
		||||
pub use requester::Requester;
 | 
			
		||||
pub use responder::Responder;
 | 
			
		||||
pub use server::Server;
 | 
			
		||||
pub use url_extract::UrlExtract;
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										61
									
								
								src/url_extract.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										61
									
								
								src/url_extract.rs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,61 @@
 | 
			
		||||
use http::Uri;
 | 
			
		||||
use std::collections::HashMap;
 | 
			
		||||
 | 
			
		||||
pub struct UrlExtract {
 | 
			
		||||
    params: HashMap<String, String>,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
impl UrlExtract {
 | 
			
		||||
    pub fn new(uri: &Uri) -> Self {
 | 
			
		||||
        Self {
 | 
			
		||||
            params: extract_params(uri),
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pub fn param_str(&self, param: &str) -> Option<String> {
 | 
			
		||||
        self.params.get(param).map(|param| Self::parse_param(param))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pub fn param_i64(&self, param: &str) -> Option<i64> {
 | 
			
		||||
        self.params.get(param)?.parse().ok()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pub fn param_f64(&self, param: &str) -> Option<f64> {
 | 
			
		||||
        self.params.get(param)?.parse().ok()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pub fn url_i64(uri: &Uri, match_path: &str) -> Option<i64> {
 | 
			
		||||
        Self::extract_url(uri, match_path).first()?.parse().ok()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pub fn url_str(uri: &Uri, match_path: &str) -> Option<String> {
 | 
			
		||||
        Self::extract_url(uri, match_path).first()?.parse().ok()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fn extract_url(uri: &Uri, r#match: &str) -> Vec<String> {
 | 
			
		||||
        uri.path()
 | 
			
		||||
            .trim_start_matches(r#match)
 | 
			
		||||
            .split('/')
 | 
			
		||||
            .map(|s| s.to_string())
 | 
			
		||||
            .collect()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fn parse_param(param: &str) -> String {
 | 
			
		||||
        param.replace("%20", " ")
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
pub fn extract_params(uri: &Uri) -> HashMap<String, String> {
 | 
			
		||||
    uri.query()
 | 
			
		||||
        .map(|q| {
 | 
			
		||||
            q.split('&')
 | 
			
		||||
                .map(|pair| {
 | 
			
		||||
                    let mut split = pair.splitn(2, '=');
 | 
			
		||||
                    let key = split.next().unwrap_or_default().to_string();
 | 
			
		||||
                    let value = split.next().unwrap_or_default().to_string();
 | 
			
		||||
                    (key, value)
 | 
			
		||||
                })
 | 
			
		||||
                .collect()
 | 
			
		||||
        })
 | 
			
		||||
        .unwrap_or_default()
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										47
									
								
								tests/url_extract.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										47
									
								
								tests/url_extract.rs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,47 @@
 | 
			
		||||
use servme::UrlExtract;
 | 
			
		||||
 | 
			
		||||
#[test]
 | 
			
		||||
fn param_str() {
 | 
			
		||||
    let uri = "https://example.com/path?param1=value1¶m2=value2¶m3=value%203"
 | 
			
		||||
        .parse()
 | 
			
		||||
        .unwrap();
 | 
			
		||||
    let extractor = UrlExtract::new(&uri);
 | 
			
		||||
 | 
			
		||||
    assert_eq!(extractor.param_str("param1"), Some("value1".to_string()));
 | 
			
		||||
    assert_eq!(extractor.param_str("param2"), Some("value2".to_string()));
 | 
			
		||||
    assert_eq!(extractor.param_str("param3"), Some("value 3".to_string()));
 | 
			
		||||
    assert_eq!(extractor.param_str("nonexistent"), None);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#[test]
 | 
			
		||||
fn param_i64() {
 | 
			
		||||
    let uri = "https://example.com/path?param1=42¶m2=invalid"
 | 
			
		||||
        .parse()
 | 
			
		||||
        .unwrap();
 | 
			
		||||
    let extractor = UrlExtract::new(&uri);
 | 
			
		||||
 | 
			
		||||
    assert_eq!(extractor.param_i64("param1"), Some(42));
 | 
			
		||||
    assert_eq!(extractor.param_i64("param2"), None);
 | 
			
		||||
    assert_eq!(extractor.param_i64("nonexistent"), None);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#[test]
 | 
			
		||||
fn param_f64() {
 | 
			
		||||
    let uri = "https://example.com/path?param1=3.14¶m2=invalid"
 | 
			
		||||
        .parse()
 | 
			
		||||
        .unwrap();
 | 
			
		||||
    let extractor = UrlExtract::new(&uri);
 | 
			
		||||
 | 
			
		||||
    assert_eq!(extractor.param_f64("param1"), Some(3.14));
 | 
			
		||||
    assert_eq!(extractor.param_f64("param2"), None);
 | 
			
		||||
    assert_eq!(extractor.param_f64("nonexistent"), None);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#[test]
 | 
			
		||||
fn url_i64() {
 | 
			
		||||
    let uri = "https://example.com/path/42/rest".parse().unwrap();
 | 
			
		||||
    assert_eq!(UrlExtract::url_i64(&uri, "/path/"), Some(42));
 | 
			
		||||
 | 
			
		||||
    let uri_without_match = "https://example.com/otherpath/42/rest".parse().unwrap();
 | 
			
		||||
    assert_eq!(UrlExtract::url_i64(&uri_without_match, "/path/"), None);
 | 
			
		||||
}
 | 
			
		||||
		Reference in New Issue
	
	Block a user