Python for Entrepreneurs Transcripts
Chapter: Sending and receiving email
Lecture: Demo: Performing the reset

Login or purchase this course to watch this video and the rest of the course contents.
0:01 So recall from last time, that we has sent a password reset,
0:04 we generated and sent a password reset email to my test account.
0:08 And here you can see we have exactly what we are looking for,
0:12 an account/reset_password with some giant, hard to guess number
0:16 or alphanumeric thing here. So what's left to do?
0:20 Well, we need to actually perform the password reset and that involves adding validation,
0:26 make sure that this is real, active, not used with the right account sort of code here
0:32 and we are going to actually set the password and use up
0:36 and record that effect that password reset was used, let's start here.
0:42 So this is the reset password piece, now actually,
0:45 this even the GET requires a little bit of validation.
0:51 When we see this page, we would like to see a message that says
0:54 something to the effect of "sorry, this password reset code is invalid or expired"
1:00 or something like that, so let's go here and do vm.validate,
1:04 now we haven't done much of that method yet but we are about to,
1:08 and then we'll show this back,
1:11 now, in the GET, we are not going to redirect somewhere,
1:15 we are just going to show them a message,
1:17 this validate will generate a message which will get shown saying
1:19 "hey, this was already used", something like that.
1:22 So what is happening? Well, we are going to need to restore this from the dictionary,
1:27 so if we run it the way it is now, it's going to give us this message saying
1:31 "reset code not found" and it is going to hide the form to submit the password,
1:38 because we haven't called from dictionary,
1:41 now you might wonder where is the dictionary coming from,
1:44 it's coming from the route, not a form, so we'll come over here
1:47 and say vm.from_dict, remember,
1:50 we have this merge dictionary, it has the routes,
1:53 it has the query string, it has the forms, all that,
1:55 so if we rerun this, it should revalidate, OK, now it's found the code, that's good,
2:03 so next, now we have a code, let's try to get it from the database,
2:07 and that's going to come out of the account service,
2:09 I think it's probably the best place, so we'll say AccountService.find_reset_code
2:13 and we're just going to give it the code.
2:18 And let's store this, we'll say self.reset, I think it's what I called it up here,
2:22 let's look, yes, self.reset right there.
2:25 So that is going to set the code, and then validate,
2:28 we can come down here and we are already checking that
2:31 when they are setting the password, when they are actually doing the POST back,
2:34 we are checking for the password, we don't want to check for that on the GET only on the POST,
2:37 so we have this mechanism to indicate whether it's get or not,
2:41 you can see that happening here on the POST version, this is False
2:51 it defaults to True, OK so the last two things is to add validation around the reset code,
2:56 so we'll say this, actually let's go ahead and use this up here,
3:01 we'll just say if this query didn't actually set a reset thing,
3:06 we'll say the reset code is not found, OK, so that will do two in one,
3:10 and then down here we want to say "self.reset_was_used",
3:15 then we'll do a message like so, "This reset code has already been used."
3:24 Alright, that's good, and then if it's expired,
3:29 what does expired mean, expired means,
3:32 let's say 24 hours, 7 days, let's go 24 hours, huh?
3:37 So let's just compute the time from when the reset code was created,
3:41 that was automatically set, to now or reverse rather,
3:45 so now minus when this thing was created,
3:53 created_date we called it, so that is going to be the change,
3:58 and then let's move this down, right where we are using it,
4:03 let's say this, if dt.total_days, or total_seconds, so we got to turn that into days,
4:08 let's just do it like that, days=dt.total_seconds divided by 60 to get minutes,
4:14 divided by 60 to get hours, divided by 24.
4:19 we'll say days is greater than 1, then we are just going to say it's expired,
4:24 otherwise, if it makes it through all of this, we are going to be golden.
4:27 "This reset code has expired, generate a new one"
4:33 Let's try this again, OK, if I rerun this, how is everything looking?
4:38 Oh reset code not found. Why was it not found?
4:41 Because we have not implemented that query yet, let's go do that.
4:46 Which one am I talking about?
4:48 This one right here, find_reset_code, so let's go write that,
4:51 so we are going to do a session, right, this is going to be super easy
4:54 so we'll say "reset = session" remember how this goes, query of PasswordReset,
5:05 we'll do a filter, password_reset.id == code, and then what do we want next,
5:17 first like that, we are just going to return reset,
5:21 so either we are going to find one or not, now let's see if this works again.
5:25 Oh perfect, so it found it but this one is expired,
5:31 apparently it's been more than 24 hours since I've done that last segment,
5:37 let's just double check that here.
5:39 This was sent, yes, one day ago, beautiful, OK.
5:43 So it looks like it's working, I am going to send a new reset code.
5:48 Alright, it was sent, let me check the email,
5:53 OK we are in good shape, zero minutes ago, let's see if this one works.
5:57 Boom it passes all the validation, it's not been used, it's not expired, things like that,
6:02 OK, so the next step is actually going to perform the password reset,
6:08 we'll do that in the next video.