Distinguish between authenticated and non-authenticated HTTP requests

I have an update password endpoint in my actix-web application and I want to check if the client performs a request as authenticated and non-authenticated. How can I do this?

#[put("/update")]
#[protect(any("TEACHER", "STUDENT", "ADMIN", "MAKERSPACE"), error = "access_denied")]
pub async fn update_user(
    claims: Option<web::ReqData<Claims>>, 
    update_user: web::Json<ChangeUser>
) -> impl Responder {

    if let Some(claims) = claims {
            user_service::update_user(
                claims.sub.clone(),
                update_user.old_pass.clone(),
                update_user.new_pass.clone()
            ).await.unwrap();
        HttpResponse::Ok().json("Ok")
    } else {
        HttpError::not_found("User does not exist").error_response()
    }
}

I didn't entirely understand what you mean, but you probably are looking for an authentication middleware.

My goal is to do a password reset and an password update using the same PUT endpoint. If the request comes as an unauthenticated request then the endpoint should perform a password reset and if the request comes from an authenticated client then it should do a update password with the old password and a new password.

Then you need to search for how authentication works and how to implement it with i.e. a session cookie.

Btw, your description of the problem sounds extremely unsafe (Giving anyone the ability to reset a password).

Yes, I know. This is just the first step. I think about adding security questions or something similar.

Then you need to search for how authentication works and how to implement it with i.e. a session cookie.

I'm using JWT and working with permission roles. Maybe it could be useful to add a GUEST role?

Are you using a library for authentication? I see that you added a macro for the protected route.

Yes, actix_web_grants

On the documentation it shows a way to perform manual checks:

use actix_web_grants::authorities::{AuthDetails, AuthoritiesCheck};

async fn manual_secure(details: AuthDetails) -> HttpResponse {
    if details.has_authority(ROLE_ADMIN) {
        return HttpResponse::Ok().body("ADMIN_RESPONSE");
    }
    HttpResponse::Ok().body("OTHER_RESPONSE")
}

You could use that together with the has_any_authority method: AuthoritiesCheck in actix_web_grants::authorities - Rust

1 Like