-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add examples, tests, improve documentation, move to stable
- Loading branch information
1 parent
9edca01
commit de54163
Showing
17 changed files
with
274 additions
and
30 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,6 @@ | ||
[package] | ||
name = "actix-permissions" | ||
version = "0.1.0-beta.1" | ||
version = "0.1.0" | ||
edition = "2018" | ||
authors = ["Ana Bujan <[email protected]>"] | ||
readme = "README.md" | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
[package] | ||
name = "hello-world-example" | ||
publish = false | ||
version = "0.1.0-SNAPSHOT" | ||
edition = "2018" | ||
|
||
[dependencies] | ||
actix-permissions = { path = "../.." } | ||
actix-web = { version = "4.0.1" } | ||
thiserror = "1.0" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
# Hello World Example | ||
|
||
In this example showing how you can compose a list of permissions, | ||
access service request, payload and injected services. | ||
|
||
# Running the App | ||
```cargo run``` and go to <http://localhost:8080/>, then try <http://localhost:8080/?q>. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
[package] | ||
name = "role-based-authorization-example" | ||
publish = false | ||
version = "0.1.0-SNAPSHOT" | ||
edition = "2018" | ||
|
||
[dependencies] | ||
actix-permissions = { path = "../.." } | ||
actix-web = { version = "4.0.1" } | ||
actix-web-httpauth = "0.6.0" | ||
thiserror = "1.0" | ||
|
||
[lib] | ||
path = "src/lib.rs" | ||
|
||
[[bin]] | ||
path = "src/bin/main.rs" | ||
name = "ums-server" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
# Role Base Authorization Example | ||
|
||
In this example for role based permission check, basic authentication is used with 3 users. | ||
Each user has a different role - *Administrator, Moderator and User*. | ||
|
||
There are 3 pages served: | ||
- Only for Administrators `admin:1` <http://localhost:8080/admin> | ||
- For Moderators and higher `moderator:2` <http://localhost:8080/mod> | ||
- For Logged in users `user:3` <http://localhost:8080/> | ||
|
||
# Running the App | ||
```cargo run``` and go to <http://localhost:8080/> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
use std::fmt::Debug; | ||
use actix_web::{App, HttpServer, ResponseError, HttpMessage}; | ||
use actix_web::web; | ||
use actix_web::http::StatusCode; | ||
use actix_web::dev::ServiceRequest; | ||
use actix_web_httpauth::extractors::basic::BasicAuth; | ||
use actix_web_httpauth::middleware::HttpAuthentication; | ||
|
||
use role_based_authorization_example::routes::routes; | ||
use thiserror::Error; | ||
use role_based_authorization_example::models::User; | ||
|
||
#[derive(Debug, Error)] | ||
pub enum ValidatorError { | ||
#[error("Forbidden")] | ||
Forbidden | ||
} | ||
|
||
impl ResponseError for ValidatorError { | ||
fn status_code(&self) -> StatusCode { | ||
match self { | ||
Self::Forbidden => StatusCode::FORBIDDEN, | ||
} | ||
} | ||
} | ||
|
||
async fn validator(req: ServiceRequest, credentials: BasicAuth) -> Result<ServiceRequest, actix_web::Error> { | ||
let users = User::list(); | ||
let user = users.iter().find(|it| | ||
credentials.user_id().eq(&it.username) && | ||
credentials.password().is_some() && | ||
credentials.password().unwrap().eq(&it.password)); | ||
if let Some(user) = user { | ||
req.extensions_mut().insert(user.role); | ||
return Ok(req); | ||
} | ||
|
||
Err(ValidatorError::Forbidden.into()) | ||
} | ||
|
||
#[actix_web::main] | ||
async fn main() -> std::io::Result<()> { | ||
HttpServer::new(|| { | ||
let auth = HttpAuthentication::basic(validator); | ||
App::new() | ||
.wrap(auth) | ||
.service(web::scope("").configure(routes)) | ||
}).bind("127.0.0.1:8888")?.run().await | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
pub mod permissions; | ||
pub mod models; | ||
pub mod routes; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
#[derive(Clone, PartialOrd, PartialEq, Copy)] | ||
pub enum Role { | ||
Administrator, Moderator, User | ||
} | ||
|
||
pub struct User { | ||
pub username: String, | ||
pub role: Role, | ||
pub password: String | ||
} | ||
|
||
impl User { | ||
pub fn new(username: &str, role: Role, password: &str) -> Self { | ||
Self { | ||
username: username.to_string(), | ||
role, | ||
password: password.to_string() | ||
} | ||
} | ||
|
||
pub fn list()->Vec<User>{ | ||
vec![ | ||
User::new("admin", Role::Administrator, "1"), | ||
User::new("moderator", Role::Moderator, "2"), | ||
User::new("user", Role::User, "3"), | ||
] | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
use actix_permissions::permission::Permission; | ||
use actix_web::dev::Payload; | ||
use actix_web::{HttpMessage, HttpRequest}; | ||
use std::future::{ready, Ready}; | ||
use crate::models::Role; | ||
|
||
#[derive(Clone)] | ||
pub struct RolePermissionCheck { | ||
role: Role, | ||
} | ||
|
||
impl Permission for RolePermissionCheck { | ||
fn call(&self, req: &HttpRequest, _payload: &mut Payload) -> Ready<actix_web::Result<bool>> { | ||
let is_allowed = req.extensions().get::<Role>().map(|user_role| self.role >= *user_role).unwrap_or(false); | ||
let res: actix_web::Result<bool, actix_web::Error> = Ok(is_allowed); | ||
ready(res) | ||
} | ||
} | ||
|
||
/// Returns true if logged in user's role is equal or higher than role | ||
pub fn has_min_role(role: Role) -> RolePermissionCheck { | ||
RolePermissionCheck { role } | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
use actix_permissions::{check, with}; | ||
use actix_web::*; | ||
use actix_web::web::ServiceConfig; | ||
|
||
use crate::models::Role; | ||
use crate::permissions::*; | ||
|
||
async fn administrators_index() -> Result<String, Error> { | ||
Ok("Only for administrators!".to_string()) | ||
} | ||
|
||
async fn moderators_index() -> Result<String, Error> { | ||
Ok("Only for administrators and moderators!".to_string()) | ||
} | ||
|
||
async fn index() -> Result<String, Error> { | ||
Ok("For logged in users!".to_string()) | ||
} | ||
|
||
pub fn routes(cfg: &mut ServiceConfig) { | ||
cfg.route( | ||
"/", | ||
check(web::get(), with(has_min_role(Role::User)), index, ), | ||
).route( | ||
"/admin", | ||
check(web::get(), with(has_min_role(Role::Administrator)), administrators_index, ), | ||
) | ||
.route( | ||
"/mod", | ||
check(web::get(), with(has_min_role(Role::Moderator)), moderators_index, ), | ||
); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
mod test_service; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
#[cfg(test)] | ||
mod tests { | ||
use std::future::{ready, Ready}; | ||
use std::sync::Arc; | ||
use actix_web::{Error, HttpRequest, test}; | ||
use actix_web::dev::{Payload, Service}; | ||
use crate::PermissionService; | ||
|
||
async fn index() -> Result<String, Error> { | ||
Ok("Welcome!".to_string()) | ||
} | ||
|
||
|
||
#[actix_web::test] | ||
async fn test_no_permission_checks_set() { | ||
let service_req = test::TestRequest::with_uri("/").to_srv_request(); | ||
let service = PermissionService::new(Arc::new(vec![]), index); | ||
|
||
let result = service.call(service_req).await; | ||
|
||
assert!(result.is_ok()) | ||
} | ||
|
||
|
||
fn deny_all( | ||
_req: &HttpRequest, | ||
_payload: &mut Payload, | ||
) -> Ready<actix_web::Result<bool, actix_web::Error>> { | ||
ready(Ok(false)) | ||
} | ||
|
||
#[actix_web::test] | ||
async fn test_deny_all() { | ||
let service_req = test::TestRequest::with_uri("/").to_srv_request(); | ||
let service = PermissionService::new(Arc::new(vec![Box::new(deny_all)]), index); | ||
|
||
let result = service.call(service_req).await; | ||
|
||
assert!(result.is_ok()) | ||
} | ||
} |
This file was deleted.
Oops, something went wrong.