16 releases
0.0.26 | Aug 24, 2020 |
---|---|
0.0.25 | Aug 22, 2020 |
0.0.19 | Feb 18, 2020 |
#796 in HTTP server
51 downloads per month
135KB
3.5K
SLoC
Post Office
this is a light weight tcp connection manager, including client and server side functions to communicate at high speed long living stable connctions with message que written in Rust.
Installation
put carte name and version in your cargo.toml file under dependencies.
postoffice = "*"
Api layers
- TCP connection - Module : client,server
- Json Request Result handler - Module : resp
- Json Scheme Validation on server Side for request handling - Module : check
Tcp Connection
base tcp connection use custom utf string as request seprated by \r\n and transferred as bytes
client Requests
simple request
SMPL sdf67sf678sd6f sdf78sd6f78sdfsdfsdf+=\r\n
here first term is the request identifier then followed by the request id and the base64 encoded string
encrypted request
SMPL sdf67sf678sd6f sdf87sd89fsd987f789sd7f8sd97f+:sdf78sd6f78sdfsdfsdf+=\r\n
here first term is the request identifier then followed by the request id and the base64 encoded nonce and cipher text seprated by ':'
Server Responses
these responses are returned by the handler function as Response Struct and parsed as given below.
Ok Response
//encrypted
match Response::new(req,"secure message".to_string(),true) {
Ok(res)=>{
return Ok(res);
},
Err()=>{
return Resp::error(req,"parser failed".to_string());
}
}
//simple
match Response::new(req,"unsecure message".to_string(),false) {
Ok(res)=>{
return Ok(res);
},
Err()=>{
return Resp::error(req,"parser failed".to_string());
}
}
OK sdf67sf678sd6f sdf87sd89fsd987f789sd7f8sd97f+:sdf78sd6f78sdfsdfsdf+=\r\n
here first term is the result identifier then followed by the request id and the base64 encoded nonce and cipher text seprated by ':' for encrypted messages and simple base64 encoded string on normal response;
BAD Response
bad response are what they sound like they may carry errors and request identifier but if parsing fails then bad request dont identify the request by given id.
BAD parser-failed\r\n
this response occurs when parse fails to process the request data.
custom error by hanlder
return Ok(resp::error(req,"hanlder ran out of mem".to_string()));
BAD sdf67sf678sd6f "hanlder ran out of mem"\r\n
undefined error by hanlder
return Ok(resp::bad(req));
BAD sdf67sf678sd6f undefined\r\n
Server Usage
use postoffice::{server,resp,common};
use postoffice::check::{Field,Format};
use json::JsonValue;
fn handler(req: Request) -> Result<Response,String> {
let mut new_format = Format::new();
new_format.field_builder(vec![
Field::new("string",false,"type",vec!["write","read","collection_check","collection_insert"],Field::no_format(),0,0,false),
Field::new("object",false,"data",Field::no_options(),Field::no_format(),0,0,false)
]);
let body:JsonValue;
match check::check_request(req.clone(),new_format) {
Ok(parsed)=>{
body = parsed;
},
Err(e)=>{
let error = format!("check request failed error : {:?}",e);
return Ok(resp::error(req,error));
}
}
let child_format = Format::builder(vec![
Field::new("string",false,"id",Field::no_options(),Field::no_format(),0,0,false),
Field::new("string",false,"path",Field::no_options(),Field::no_format(),0,0,false),
Field::new("array",false,"users",Field::no_options(),Field::no_format(),0,100,true)
]);
match check::check_children(&body["data"], "object".to_string(), Field::no_options(), child_format, false, true) {
Ok(_)=>{},
Err(e)=>{
let error = format!("check children failed error : {:?}",e);
return Ok(resp::error(req,error));
}
}
let mut user_format = Format::new();
user_format.field_builder(vec![
Field::new("string",false,"name",Field::no_options(),Field::no_format(),0,0,false),
Field::new("string",false,"email",Field::no_options(),Field::no_format(),0,0,false),
Field::new("string",false,"company",Field::no_options(),Field::no_format(),2,50,true)
]);
for entry in body["data"].entries() {
let data = entry.1;
let users = &data["users"];
match check::check_array(&users, "object".to_string(), Field::no_options(), &user_format) {
Ok(_)=>{},
Err(e)=>{
let error = format!("check array failed error : {:?}",e);
return Ok(resp::error(req,error));
}
}
}
return Ok(resp::ok(req));
}
fn auth(token:server::auth::Token) -> bool {
println!("token : {:?}",token);
return true;
}
fn main(){
let key = "8cfb30b34977529853bbe46afdbbd5ae".to_string();
let address = String::from("127.0.0.1:5200");
server::init(address,key,handler,auth);
}
Client Usage
use postoffice::client::{get_random_connection_id,start_connection,send_message};
use postoffice::resp;
fn main(){
let key = "8cfb30b34977529853bbe46afdbbd5ae".to_string();
let connection_id = client::get_random_connection_id();
let addr = "127.0.0.1:5200".to_string();
match start_connection(&connection_id,addr,key) {
Ok(_)=>{
//println!("connection establishged");
},
Err(_)=>{
common::error("failed start connection");
}
}
let mut user = JsonValue::new_object();
user.insert("name","akku").unwrap();
user.insert("email","gzbakku@gmail.com").unwrap();
user.insert("company","daachi.in").unwrap();
let mut users = JsonValue::new_array();
users.push(user);
let mut request = JsonValue::new_object();
request.insert("collection","1a62c37cf70a74cfeb69aba742643613").unwrap();
request.insert("path","/users/");
request.insert("users",users);
send(connection_id,request);
}
fn send(connection_id:String,data:json::JsonValue){
let mut request_object = json::JsonValue::new_object();
match request_object.insert("type","write") {
Ok(_)=>{},
Err(_)=>{}
}
match request_object.insert("data",data) {
Ok(_)=>{},
Err(_)=>{}
}
let request_string = request_object.dump();
match client::send_message(&connection_id,request_string,false) {
Ok(response)=>{
match resp::parse_response(response) {
Ok(result)=>{
println!("result : {:?}",result);
},
Err(e)=>{
println!("error parse response strucft : {:?}",e);
}
}
},
Err(_)=>{
println!("request failed");
}
}
}
Please make sure to update tests as appropriate.
License
MIT
Dependencies
~7MB
~122K SLoC