peach-workspace/peach-web/src/routes/authentication/change.rs

102 lines
4.2 KiB
Rust

use log::info;
use maud::{html, PreEscaped};
use peach_lib::password_utils;
use rouille::{post_input, try_or_400, Request, Response};
use crate::{error::PeachWebError, templates};
// HELPER AND ROUTES FOR /auth/change (GET and POST)
/// Password change form template builder.
pub fn build_template() -> PreEscaped<String> {
let form_template = html! {
(PreEscaped("<!-- CHANGE PASSWORD FORM -->"))
div class="card center" {
form id="changePassword" class="center" action="/auth/change" method="post" {
div style="display: flex; flex-direction: column; margin-bottom: 1rem;" {
(PreEscaped("<!-- input for current password -->"))
label for="currentPassword" class="center label-small font-gray" style="width: 80%;" { "CURRENT PASSWORD" }
input id="currentPassword" class="center input" name="current_password" type="password" title="Current password" autofocus;
(PreEscaped("<!-- input for new password -->"))
label for="newPassword" class="center label-small font-gray" style="width: 80%;" { "NEW PASSWORD" }
input id="newPassword" class="center input" name="new_password1" type="password" title="New password";
(PreEscaped("<!-- input for duplicate new password -->"))
label for="newPasswordDuplicate" class="center label-small font-gray" style="width: 80%;" { "RE-ENTER NEW PASSWORD" }
input id="newPasswordDuplicate" class="center input" name="new_password2" type="password" title="New password duplicate";
(PreEscaped("<!-- save (form submission) button -->"))
input id="savePassword" class="button button-primary center" title="Add" type="submit" value="Save";
a class="button button-secondary center" href="/settings/admin" title="Cancel"{ "Cancel" }
}
}
(PreEscaped("<!-- FLASH MESSAGE -->"))
// TODO: render flash message
//{% include "snippets/flash_message" %}
}
};
// wrap the nav bars around the settings menu template content
// parameters are template, title and back url
let body =
templates::nav::build_template(form_template, "Change Password", Some("/settings/admin"));
// render the base template with the provided body
templates::base::build_template(body)
}
/// Verify, validate and set a new password, overwriting the current password.
pub fn save_password(
current_password: &str,
new_password1: &str,
new_password2: &str,
) -> Result<(), PeachWebError> {
info!(
"Attempting password change: {} {} {}",
current_password, new_password1, new_password2
);
// check that the supplied value matches the actual current password
password_utils::verify_password(current_password)?;
// ensure that both new_password values match
password_utils::validate_new_passwords(new_password1, new_password2)?;
// hash the password and save the hash to file
password_utils::set_new_password(new_password1)?;
Ok(())
}
/// Parse current and new passwords from the submitted form, save the new
/// password hash to file (`/var/lib/peachcloud/config.yml`) and redirect
/// to the change password form URL.
pub fn handle_form(request: &Request) -> Response {
// query the request body for form data
// return a 400 error if the admin_id field is missing
let data = try_or_400!(post_input!(request, {
current_password: String,
new_password1: String,
new_password2: String,
}));
// save submitted admin id to file
let _result = save_password(
&data.current_password,
&data.new_password1,
&data.new_password2,
);
// TODO: match on result and define flash message accordingly
// then send the redirect response
// redirect to the configure admin page
// TODO: add flash message
Response::redirect_303("/auth/change")
}
/*
match result {
Ok(_) => Flash::success(Redirect::to(url), "Added SSB administrator"),
Err(e) => Flash::error(Redirect::to(url), format!("Failed to add new admin: {}", e)),
}
*/