Add IP and Username to failed login attempts

Resolves #119
This commit is contained in:
Baelyk 2018-08-25 17:07:59 -05:00
parent 8d1ee859f2
commit c386b3bcf7

View File

@ -1,4 +1,5 @@
use std::collections::HashMap; use std::collections::HashMap;
use std::net::{IpAddr, Ipv4Addr, SocketAddr};
use rocket::request::{self, Form, FormItems, FromForm, FromRequest, Request}; use rocket::request::{self, Form, FormItems, FromForm, FromRequest, Request};
use rocket::{Outcome, Route}; use rocket::{Outcome, Route};
@ -21,12 +22,12 @@ pub fn routes() -> Vec<Route> {
} }
#[post("/connect/token", data = "<connect_data>")] #[post("/connect/token", data = "<connect_data>")]
fn login(connect_data: Form<ConnectData>, device_type: DeviceType, conn: DbConn) -> JsonResult { fn login(connect_data: Form<ConnectData>, device_type: DeviceType, conn: DbConn, socket: Option<SocketAddr>) -> JsonResult {
let data = connect_data.get(); let data = connect_data.get();
match data.grant_type { match data.grant_type {
GrantType::RefreshToken => _refresh_login(data, device_type, conn), GrantType::RefreshToken => _refresh_login(data, device_type, conn),
GrantType::Password => _password_login(data, device_type, conn), GrantType::Password => _password_login(data, device_type, conn, socket),
} }
} }
@ -57,7 +58,13 @@ fn _refresh_login(data: &ConnectData, _device_type: DeviceType, conn: DbConn) ->
}))) })))
} }
fn _password_login(data: &ConnectData, device_type: DeviceType, conn: DbConn) -> JsonResult { fn _password_login(data: &ConnectData, device_type: DeviceType, conn: DbConn, remote: Option<SocketAddr>) -> JsonResult {
// Get the ip for error reporting
let ip = match remote {
Some(ip) => ip.ip(),
None => IpAddr::V4(Ipv4Addr::new(0, 0, 0, 0)),
};
// Validate scope // Validate scope
let scope = data.get("scope"); let scope = data.get("scope");
if scope != "api offline_access" { if scope != "api offline_access" {
@ -68,13 +75,19 @@ fn _password_login(data: &ConnectData, device_type: DeviceType, conn: DbConn) ->
let username = data.get("username"); let username = data.get("username");
let user = match User::find_by_mail(username, &conn) { let user = match User::find_by_mail(username, &conn) {
Some(user) => user, Some(user) => user,
None => err!("Username or password is incorrect. Try again."), None => err!(format!(
"Username or password is incorrect. Try again. IP: {}. Username: {}.",
ip, username
)),
}; };
// Check password // Check password
let password = data.get("password"); let password = data.get("password");
if !user.check_valid_password(password) { if !user.check_valid_password(password) {
err!("Username or password is incorrect. Try again.") err!(format!(
"Username or password is incorrect. Try again. IP: {}. Username: {}.",
ip, username
))
} }
// Let's only use the header and ignore the 'devicetype' parameter // Let's only use the header and ignore the 'devicetype' parameter