Add extra guards, begin working on channels.

This commit is contained in:
Paul Makles
2020-01-26 15:20:32 +00:00
parent 0e5211e705
commit 955e482dae
8 changed files with 118 additions and 4 deletions

67
src/guards/auth.rs Normal file
View File

@@ -0,0 +1,67 @@
use rocket::Outcome;
use rocket::http::{ Status, RawStr };
use rocket::request::{ self, Request, FromRequest, FromParam };
use bson::{ bson, doc, ordered::OrderedDocument };
use ulid::Ulid;
use crate::database;
pub struct User(
pub Ulid,
pub String,
pub OrderedDocument,
);
#[derive(Debug)]
pub enum AuthError {
BadCount,
Missing,
Invalid,
}
impl<'a, 'r> FromRequest<'a, 'r> for User {
type Error = AuthError;
fn from_request(request: &'a Request<'r>) -> request::Outcome<Self, Self::Error> {
let keys: Vec<_> = request.headers().get("x-auth-token").collect();
match keys.len() {
0 => Outcome::Failure((Status::Forbidden, AuthError::Missing)),
1 => {
let key = keys[0];
let col = database::get_db().collection("users");
let result = col.find_one(doc! { "access_token": key }, None).unwrap();
if let Some(user) = result {
Outcome::Success(User (
Ulid::from_string(user.get_str("_id").unwrap()).unwrap(),
user.get_str("username").unwrap().to_string(),
user
))
} else {
Outcome::Failure((Status::Forbidden, AuthError::Invalid))
}
},
_ => Outcome::Failure((Status::BadRequest, AuthError::BadCount)),
}
}
}
impl<'r> FromParam<'r> for User {
type Error = &'r RawStr;
fn from_param(param: &'r RawStr) -> Result<Self, Self::Error> {
let col = database::get_db().collection("users");
let result = col.find_one(doc! { "_id": param.to_string() }, None).unwrap();
if let Some(user) = result {
Ok(User (
Ulid::from_string(user.get_str("_id").unwrap()).unwrap(),
user.get_str("username").unwrap().to_string(),
user
))
} else {
Err(param)
}
}
}

58
src/guards/channel.rs Normal file
View File

@@ -0,0 +1,58 @@
use rocket::Outcome;
use rocket::http::{ Status, RawStr };
use rocket::request::{ self, Request, FromRequest, FromParam };
use bson::{ bson, doc, ordered::OrderedDocument };
use std::convert::TryFrom;
use ulid::Ulid;
use crate::database;
use crate::routes::channel::ChannelType;
pub struct Channel (
pub Ulid,
pub ChannelType,
pub OrderedDocument,
);
pub struct Message (
pub Ulid,
pub OrderedDocument,
);
impl<'r> FromParam<'r> for Channel {
type Error = &'r RawStr;
fn from_param(param: &'r RawStr) -> Result<Self, Self::Error> {
let col = database::get_db().collection("channels");
let result = col.find_one(doc! { "_id": param.to_string() }, None).unwrap();
if let Some(channel) = result {
Ok(Channel (
Ulid::from_string(channel.get_str("_id").unwrap()).unwrap(),
ChannelType::try_from(channel.get_i32("username").unwrap() as usize).unwrap(),
channel
))
} else {
Err(param)
}
}
}
impl<'r> FromParam<'r> for Message {
type Error = &'r RawStr;
fn from_param(param: &'r RawStr) -> Result<Self, Self::Error> {
let col = database::get_db().collection("messages");
let result = col.find_one(doc! { "_id": param.to_string() }, None).unwrap();
if let Some(message) = result {
Ok(Message (
Ulid::from_string(message.get_str("_id").unwrap()).unwrap(),
message
))
} else {
Err(param)
}
}
}

2
src/guards/mod.rs Normal file
View File

@@ -0,0 +1,2 @@
pub mod auth;
pub mod channel;