@@ -51,7 +51,7 @@ impl<W: std::io::Write> HeaderContext<W> {
51
51
Some ( "redirect" ) => self . redirect ( & data) . map ( PageContext :: Close ) ,
52
52
Some ( "json" ) => self . json ( & data) . map ( PageContext :: Close ) ,
53
53
Some ( "cookie" ) => self . add_cookie ( & data) . map ( PageContext :: Header ) ,
54
- Some ( "authentication" ) => self . authentication ( & data) . await ,
54
+ Some ( "authentication" ) => self . authentication ( data) . await ,
55
55
_ => self . start_body ( data) . await ,
56
56
}
57
57
}
@@ -167,27 +167,19 @@ impl<W: std::io::Write> HeaderContext<W> {
167
167
Ok ( self . response . body ( json_response) )
168
168
}
169
169
170
- async fn authentication ( mut self , data : & JsonValue ) -> anyhow:: Result < PageContext < W > > {
171
- let password_hash = get_object_str ( data, "password_hash" ) ;
172
- let password = get_object_str ( data, "password" ) ;
170
+ async fn authentication ( mut self , mut data : JsonValue ) -> anyhow:: Result < PageContext < W > > {
171
+ let password_hash = take_object_str ( & mut data, "password_hash" ) ;
172
+ let password = take_object_str ( & mut data, "password" ) ;
173
173
if let ( Some ( password) , Some ( password_hash) ) = ( password, password_hash) {
174
- log:: debug!(
175
- "Authenticating user with password_hash = {:?}" ,
176
- password_hash
177
- ) ;
178
- let verif_result =
179
- tokio:: task:: block_in_place ( move || verify_password_sync ( password_hash, password) ) ?;
180
- match verif_result {
174
+ log:: debug!( "Authentication with password_hash = {:?}" , password_hash) ;
175
+ match verify_password_async ( password_hash, password) . await ? {
181
176
Ok ( ( ) ) => return Ok ( PageContext :: Header ( self ) ) ,
182
- Err ( e) => log:: info!( "User authentication failed : {}" , e) ,
177
+ Err ( e) => log:: info!( "Password didn't match : {}" , e) ,
183
178
}
184
179
}
185
- log:: debug!(
186
- "Authentication failed with password_hash = {:?}" ,
187
- password_hash
188
- ) ;
180
+ log:: debug!( "Authentication failed" ) ;
189
181
// The authentication failed
190
- if let Some ( link) = get_object_str ( data, "link" ) {
182
+ if let Some ( link) = get_object_str ( & data, "link" ) {
191
183
self . response . status ( StatusCode :: FOUND ) ;
192
184
self . response . insert_header ( ( header:: LOCATION , link) ) ;
193
185
self . has_status = true ;
@@ -218,14 +210,17 @@ impl<W: std::io::Write> HeaderContext<W> {
218
210
}
219
211
}
220
212
221
- fn verify_password_sync (
222
- password_hash : & str ,
223
- password : & str ,
213
+ async fn verify_password_async (
214
+ password_hash : String ,
215
+ password : String ,
224
216
) -> Result < Result < ( ) , password_hash:: Error > , anyhow:: Error > {
225
- let hash = password_hash:: PasswordHash :: new ( password_hash)
226
- . map_err ( |e| anyhow:: anyhow!( "invalid value for the password_hash property: {}" , e) ) ?;
227
- let phfs = & [ & argon2:: Argon2 :: default ( ) as & dyn password_hash:: PasswordVerifier ] ;
228
- Ok ( hash. verify_password ( phfs, password) )
217
+ tokio:: task:: spawn_blocking ( move || {
218
+ let hash = password_hash:: PasswordHash :: new ( & password_hash)
219
+ . map_err ( |e| anyhow:: anyhow!( "invalid value for the password_hash property: {}" , e) ) ?;
220
+ let phfs = & [ & argon2:: Argon2 :: default ( ) as & dyn password_hash:: PasswordVerifier ] ;
221
+ Ok ( hash. verify_password ( phfs, password) )
222
+ } )
223
+ . await ?
229
224
}
230
225
231
226
fn get_backtrace ( error : & anyhow:: Error ) -> Vec < String > {
@@ -244,6 +239,13 @@ fn get_object_str<'a>(json: &'a JsonValue, key: &str) -> Option<&'a str> {
244
239
. and_then ( JsonValue :: as_str)
245
240
}
246
241
242
+ fn take_object_str ( json : & mut JsonValue , key : & str ) -> Option < String > {
243
+ match json. get_mut ( key) ?. take ( ) {
244
+ JsonValue :: String ( s) => Some ( s) ,
245
+ _ => None ,
246
+ }
247
+ }
248
+
247
249
#[ allow( clippy:: module_name_repetitions) ]
248
250
pub struct RenderContext < W : std:: io:: Write > {
249
251
app_state : Arc < AppState > ,
0 commit comments