impl new Save for hashcache
This commit is contained in:
parent
b597c0b965
commit
9f4429aee9
2 changed files with 164 additions and 17 deletions
146
src/cache/hashcache.rs
vendored
146
src/cache/hashcache.rs
vendored
|
@ -33,15 +33,15 @@ pub struct HashCache {
|
|||
|
||||
impl HashCache {
|
||||
// save [PoWConfig] to cache
|
||||
fn save(&mut self, config: CachePoW) -> CaptchaResult<()> {
|
||||
fn save_pow_config(&mut self, config: CachePoW) -> CaptchaResult<()> {
|
||||
self.difficulty_map
|
||||
.insert(config.string, config.difficulty_factor);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
// retrive [PoWConfig] from cache. Deletes config post retrival
|
||||
fn retrive(&mut self, string: String) -> CaptchaResult<Option<u32>> {
|
||||
if let Some(difficulty_factor) = self.remove(&string) {
|
||||
fn retrive_pow_config(&mut self, string: String) -> CaptchaResult<Option<u32>> {
|
||||
if let Some(difficulty_factor) = self.remove_pow_config(&string) {
|
||||
Ok(Some(difficulty_factor.to_owned()))
|
||||
} else {
|
||||
Ok(None)
|
||||
|
@ -49,9 +49,33 @@ impl HashCache {
|
|||
}
|
||||
|
||||
// delete [PoWConfig] from cache
|
||||
fn remove(&mut self, string: &str) -> Option<u32> {
|
||||
fn remove_pow_config(&mut self, string: &str) -> Option<u32> {
|
||||
self.difficulty_map.remove(string)
|
||||
}
|
||||
|
||||
// save captcha result
|
||||
fn save_captcha_result(&mut self, res: CacheResult) -> CaptchaResult<()> {
|
||||
self.result_map.insert(res.result, res.key);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
// verify captcha result
|
||||
fn verify_captcha_result(&mut self, challenge: VerifyCaptchaResult) -> CaptchaResult<bool> {
|
||||
if let Some(captcha_id) = self.remove_cache_result(&challenge.result) {
|
||||
if captcha_id == challenge.key {
|
||||
return Ok(true);
|
||||
} else {
|
||||
return Ok(false);
|
||||
}
|
||||
} else {
|
||||
Ok(false)
|
||||
}
|
||||
}
|
||||
|
||||
// delete cache result
|
||||
fn remove_cache_result(&mut self, string: &str) -> Option<String> {
|
||||
self.result_map.remove(string)
|
||||
}
|
||||
}
|
||||
|
||||
impl Save for HashCache {}
|
||||
|
@ -80,7 +104,7 @@ impl Handler<CachePoW> for HashCache {
|
|||
.into_actor(self);
|
||||
ctx.spawn(wait_for);
|
||||
|
||||
MessageResult(self.save(msg))
|
||||
MessageResult(self.save_pow_config(msg))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -88,7 +112,7 @@ impl Handler<CachePoW> for HashCache {
|
|||
impl Handler<DeletePoW> for HashCache {
|
||||
type Result = MessageResult<DeletePoW>;
|
||||
fn handle(&mut self, msg: DeletePoW, _ctx: &mut Self::Context) -> Self::Result {
|
||||
self.remove(&msg.0);
|
||||
self.remove_pow_config(&msg.0);
|
||||
MessageResult(Ok(()))
|
||||
}
|
||||
}
|
||||
|
@ -97,7 +121,51 @@ impl Handler<DeletePoW> for HashCache {
|
|||
impl Handler<RetrivePoW> for HashCache {
|
||||
type Result = MessageResult<RetrivePoW>;
|
||||
fn handle(&mut self, msg: RetrivePoW, _ctx: &mut Self::Context) -> Self::Result {
|
||||
MessageResult(self.retrive(msg.0))
|
||||
MessageResult(self.retrive_pow_config(msg.0))
|
||||
}
|
||||
}
|
||||
|
||||
/// cache PoW result
|
||||
impl Handler<CacheResult> for HashCache {
|
||||
type Result = MessageResult<CacheResult>;
|
||||
fn handle(&mut self, msg: CacheResult, ctx: &mut Self::Context) -> Self::Result {
|
||||
//use actix::clock::sleep;
|
||||
use actix::clock::delay_for;
|
||||
use std::time::Duration;
|
||||
|
||||
let addr = ctx.address();
|
||||
let del_msg = DeleteCaptchaResult {
|
||||
result: msg.result.clone(),
|
||||
};
|
||||
|
||||
let duration: Duration = Duration::new(msg.duration.clone(), 0);
|
||||
let wait_for = async move {
|
||||
//sleep(duration).await;
|
||||
delay_for(duration).await;
|
||||
addr.send(del_msg).await.unwrap().unwrap();
|
||||
}
|
||||
.into_actor(self);
|
||||
ctx.spawn(wait_for);
|
||||
|
||||
MessageResult(self.save_captcha_result(msg))
|
||||
}
|
||||
}
|
||||
|
||||
/// Delte a PoWConfig
|
||||
impl Handler<DeleteCaptchaResult> for HashCache {
|
||||
type Result = MessageResult<DeleteCaptchaResult>;
|
||||
fn handle(&mut self, msg: DeleteCaptchaResult, _ctx: &mut Self::Context) -> Self::Result {
|
||||
self.remove_cache_result(&msg.result);
|
||||
MessageResult(Ok(()))
|
||||
}
|
||||
}
|
||||
|
||||
/// Retrive PoW difficulty_factor for a PoW string
|
||||
impl Handler<VerifyCaptchaResult> for HashCache {
|
||||
type Result = MessageResult<VerifyCaptchaResult>;
|
||||
fn handle(&mut self, msg: VerifyCaptchaResult, _ctx: &mut Self::Context) -> Self::Result {
|
||||
// MessageResult(self.retrive(msg.0))
|
||||
MessageResult(self.verify_captcha_result(msg))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -107,18 +175,18 @@ mod tests {
|
|||
use crate::mcaptcha::AddVisitorResult;
|
||||
use crate::pow::PoWConfig;
|
||||
|
||||
async fn sleep(time: u64) {
|
||||
//use actix::clock::sleep;
|
||||
use actix::clock::delay_for;
|
||||
use std::time::Duration;
|
||||
// async fn sleep(time: u64) {
|
||||
// //use actix::clock::sleep;
|
||||
// use actix::clock::delay_for;
|
||||
// use std::time::Duration;
|
||||
|
||||
let duration: Duration = Duration::new(time, 0);
|
||||
//sleep(duration).await;
|
||||
delay_for(duration).await;
|
||||
}
|
||||
// let duration: Duration = Duration::new(time, 0);
|
||||
// //sleep(duration).await;
|
||||
// delay_for(duration).await;
|
||||
// }
|
||||
|
||||
#[actix_rt::test]
|
||||
async fn hashcache_works() {
|
||||
async fn hashcache_pow_cache_works() {
|
||||
use actix::clock::delay_for;
|
||||
use actix::clock::Duration;
|
||||
|
||||
|
@ -149,4 +217,50 @@ mod tests {
|
|||
let expired_string = addr.send(RetrivePoW(string)).await.unwrap().unwrap();
|
||||
assert_eq!(None, expired_string);
|
||||
}
|
||||
|
||||
#[actix_rt::test]
|
||||
async fn hashcache_result_cache_works() {
|
||||
use actix::clock::delay_for;
|
||||
use actix::clock::Duration;
|
||||
|
||||
const DURATION: u64 = 5;
|
||||
const KEY: &str = "a";
|
||||
const RES: &str = "b";
|
||||
let addr = HashCache::default().start();
|
||||
// send value to cache
|
||||
// send another value to cache for auto delete
|
||||
// verify_captcha_result
|
||||
// delete
|
||||
// wait for timeout and verify_captcha_result against second value
|
||||
|
||||
let add_cache = CacheResult {
|
||||
key: KEY.into(),
|
||||
result: RES.into(),
|
||||
duration: DURATION,
|
||||
};
|
||||
|
||||
addr.send(add_cache).await.unwrap().unwrap();
|
||||
|
||||
let verify_msg = VerifyCaptchaResult {
|
||||
key: KEY.into(),
|
||||
result: RES.into(),
|
||||
};
|
||||
|
||||
assert!(addr.send(verify_msg).await.unwrap().unwrap());
|
||||
|
||||
let verify_msg = VerifyCaptchaResult {
|
||||
key: "cz".into(),
|
||||
result: RES.into(),
|
||||
};
|
||||
assert!(!addr.send(verify_msg).await.unwrap().unwrap());
|
||||
|
||||
let duration: Duration = Duration::new(5, 0);
|
||||
delay_for(duration + duration).await;
|
||||
|
||||
let verify_msg = VerifyCaptchaResult {
|
||||
key: KEY.into(),
|
||||
result: RES.into(),
|
||||
};
|
||||
assert!(!addr.send(verify_msg).await.unwrap().unwrap());
|
||||
}
|
||||
}
|
||||
|
|
35
src/cache/mod.rs
vendored
35
src/cache/mod.rs
vendored
|
@ -24,7 +24,13 @@ pub mod hashcache;
|
|||
|
||||
/// Describes actor handler trait impls that are required by a cache implementation
|
||||
pub trait Save:
|
||||
actix::Actor + actix::Handler<RetrivePoW> + actix::Handler<CachePoW> + actix::Handler<DeletePoW>
|
||||
actix::Actor
|
||||
+ actix::Handler<RetrivePoW>
|
||||
+ actix::Handler<CachePoW>
|
||||
+ actix::Handler<DeletePoW>
|
||||
+ actix::Handler<CacheResult>
|
||||
+ actix::Handler<VerifyCaptchaResult>
|
||||
+ actix::Handler<DeleteCaptchaResult>
|
||||
{
|
||||
}
|
||||
pub mod messages {
|
||||
|
@ -68,4 +74,31 @@ pub mod messages {
|
|||
#[derive(Message)]
|
||||
#[rtype(result = "CaptchaResult<()>")]
|
||||
pub struct DeletePoW(pub String);
|
||||
|
||||
/// Message to cache captcha result and the captcha key for which
|
||||
/// it was generated
|
||||
#[derive(Message, Serialize, Deserialize, Builder)]
|
||||
#[rtype(result = "CaptchaResult<()>")]
|
||||
pub struct CacheResult {
|
||||
pub result: String,
|
||||
// key is Captcha identifier
|
||||
pub key: String,
|
||||
pub duration: u64,
|
||||
}
|
||||
|
||||
/// Message to verify captcha result against
|
||||
/// the stored captcha key
|
||||
#[derive(Message)]
|
||||
#[rtype(result = "CaptchaResult<bool>")]
|
||||
pub struct VerifyCaptchaResult {
|
||||
pub result: String,
|
||||
pub key: String,
|
||||
}
|
||||
|
||||
/// Message to delete cached capthca result when it expires
|
||||
#[derive(Message)]
|
||||
#[rtype(result = "CaptchaResult<()>")]
|
||||
pub struct DeleteCaptchaResult {
|
||||
pub result: String,
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue