Skip to content

Commit

Permalink
Added Regex: Capture Group service.
Browse files Browse the repository at this point in the history
  • Loading branch information
DK26 committed Jun 16, 2021
1 parent b22995f commit 5c68780
Show file tree
Hide file tree
Showing 6 changed files with 117 additions and 3 deletions.
4 changes: 3 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,6 @@ actix-web = "3"
encoding = "0.2"
# unescape = "0.1"
lazy_static = "1.4"
base64 = "0.13"
base64 = "0.13"
regex = "1.5"
parking_lot = "0.11"
3 changes: 3 additions & 0 deletions cfg.toml
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,6 @@ alt_encoding = "windows-1255" # If decoding to UTF-8 fails, this will be attemp

[service]
listen = "127.0.0.1:8080"

[cache]
regex_patterns_limit = 10000
8 changes: 7 additions & 1 deletion src/cfglib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,8 @@ use std::env::current_exe;
#[derive(Deserialize)]
pub struct Config {
pub common: CommonConfig,
pub service: ServiceConfig
pub service: ServiceConfig,
pub cache: CacheConfig,
}

#[derive(Deserialize)]
Expand All @@ -21,6 +22,11 @@ pub struct ServiceConfig {
pub listen: String
}

#[derive(Deserialize)]
pub struct CacheConfig {
pub regex_patterns_limit: usize,
}

pub fn init_cfg() -> Config {

// TODO: Verify the existence of a `cfg.toml` file.
Expand Down
11 changes: 11 additions & 0 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,25 @@ extern crate lazy_static;
mod cfglib;
mod services;
mod utils;
use parking_lot::RwLock;

use cfglib::*;
use utils::PatternsCache;
use actix_web::{
HttpServer,
App
};

lazy_static! {

static ref CFG: Config = init_cfg();

static ref PATTERNS_CACHE: RwLock<PatternsCache> = {
let cache = PatternsCache::new()
.limit(CFG.cache.regex_patterns_limit);
RwLock::new(cache)
};

}

pub const DEFAULT_ENCODING : &'static str = "utf-8";
Expand All @@ -36,6 +46,7 @@ async fn main() -> std::io::Result<()> {
.service(services::decode_base64)
.service(services::decode_base64_encoding)
.service(services::decode_mime_subject)
.service(services::regex_capture_group)
})
.bind(&CFG.service.listen)?
.run()
Expand Down
22 changes: 21 additions & 1 deletion src/services.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// use serde::Deserialize;
use serde::Deserialize;
use actix_web::{
get,
post,
Expand All @@ -9,6 +9,14 @@ use actix_web::{

use crate::utils;
use crate::DEFAULT_ENCODING;
use crate::PATTERNS_CACHE;

#[derive(Deserialize, Debug)]
pub struct RegexData {
payload: String,
pattern: String,
// join: String,
}

#[get("/welcome")]
pub async fn welcome() -> impl Responder {
Expand Down Expand Up @@ -74,7 +82,19 @@ pub async fn decode_mime_subject(req_body: String) -> impl Responder {

}

#[post("/regex_capture_group")]
pub async fn regex_capture_group(request: web::Json<RegexData>) -> impl Responder {

let mut patterns = PATTERNS_CACHE.write();

let re = patterns.get(&request.pattern);

let caps = re.captures(&request.payload).unwrap();

let response = caps.get(1).unwrap().as_str().to_owned();

HttpResponse::Ok().body(response)
}

// #[derive(Deserialize, Debug)]
// pub struct TestData {
Expand Down
72 changes: 72 additions & 0 deletions src/utils.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
#![allow(dead_code)]
use std::collections::HashMap;
use std::borrow::Cow;
use std::collections::VecDeque;
use std::char;
use regex::Regex;

// use std::string::FromUtf8Error;
use encoding::{
DecoderTrap,
Expand Down Expand Up @@ -450,4 +453,73 @@ pub fn decode_mime_subject(src: &str) -> DecodingResult {
} // for src.chars()

attempt_decode(&decoded_payload, &encoding)
}

pub struct PatternsCache {
map: HashMap<String, Regex>,
limit: usize,
size: usize
}

#[allow(dead_code)]
impl<'a> PatternsCache {

pub fn new() -> Self {
Self {
map: HashMap::new(),
limit: 0,
size: 0,
}
}

pub fn limit(mut self, value: usize) -> Self {
self.limit = value;
self
}

pub fn get<'b, 'c>(&'a mut self, pattern: &'c str) -> &'b Regex
where 'a: 'b {

let mut current_size = self.map.len();


if self.limit > 0 && current_size == self.limit {
self.map.clear();
current_size = 0;
}

let result = self.map.entry(pattern.to_owned()).or_insert_with(|| {
current_size += 1;
Regex::new(&pattern).unwrap()
});

self.size = current_size;

result
}

pub fn len(&self) -> usize {
self.size
}

pub fn get_limit(&self) -> usize {
self.limit
}

pub fn is_limited(&self) -> bool {
self.limit > 0
}

pub fn reached_limit(&self) -> bool {
self.size >= self.limit
}

pub fn clear(&mut self) {

{
self.map.clear();
}
self.size = 0;
}

}

0 comments on commit 5c68780

Please sign in to comment.