LoginView12:41 with Kenneth Love
Now that some of our views require users to be logged in, we should provide them a way of authenticating themselves.
Like I've said many times before, Django loves us and 0:00 wants to save us time and trouble, so it's made it easy to log users in. 0:03 You've logged in to your Django admin panel before but that only works for 0:06 users that are marked as being staff members. 0:10 You don't want to make every user of your web app a staff user though. 0:12 And you don't want them all to log in to your admin panel either, but 0:15 all of that functionality exists, so you can probably use it. 0:19 There's obviously some code somewhere for 0:22 logging users in because the admin doesn't. 0:24 Let me show you how to use that log-in function and 0:27 a few other tools to make your very own log-in view for your users. 0:29 Django actually has a few different ways of handling log-in forms, 0:33 views, the whole log-in process. 0:38 So needless to say there's, you know, been a lot of approaches to this. 0:42 The approach that I actually always used is this one that's here in the docs you 0:47 would call authenticate and then you would call this login method to log the user in, 0:52 or this login function rather. 0:57 You don't have to do all that anymore. 0:59 You still have to call log in. 1:01 Well sorta. 1:03 We don't have to do authenticate and so 1:04 like that Django provides some tools for that. 1:06 So that's pretty cool. 1:09 So let me use Django's provided goodies to save myself some work. 1:11 So before I do that though, I'm going to create a new app 1:18 named accounts, and this app is going to hold just 1:24 any sort of stuff I'm doing that's dealing with accounts. 1:28 So if I made a user model or just whatever. 1:32 So I'm gonna create that and then I'm going to add that to my installed apps. 1:36 And I'm gonna add it above communities just in case 1:41 communities need to rely on accounts. 1:45 And then here inside of url.pie I'm gonna add a new URL for accounts. 1:48 I'm gonna include accounts.urls, 1:58 namespace=accounts. 2:02 All right, cool. 2:07 So there's that. 2:09 So now if I refresh my tree over here then I should see accounts and 2:10 I'm gonna go ahead and create the templates folder and 2:16 inside of there I'm gonna go ahead and 2:20 create accounts cuz I better have some templates. 2:24 And then I'm also going to create the urls.py file because and 2:28 we gonna have some urls and in fact I'm gonna go ahead and 2:34 get that started so from django.com.url from .url 2:39 import view and then urlpatterns is an empty list. 2:45 All right cool. 2:50 I mean it's just it's just a blank shell for now. 2:52 Okay so I think I'm ready to start creating my view. 2:55 Now this view is going to be a form view it's not a creative you or 3:00 an update view but they're very similar. 3:04 So I'm gonna go ahead and do from django.views import generic so 3:06 that I can use form view I have a couple of other imports I need to do, though. 3:13 So I need to do from django.contrib.auth.forms 3:19 import AuthenticationForm, and 3:24 this very appropriately named form is the form that handles authenticating the user. 3:28 So authenticating means Is there an account that has this username and 3:34 this password? 3:39 It's not actually logging the user in, 3:40 it's just making sure they are an authentic user. 3:42 I'm going to need to do a redirect when the form view is complete, so 3:46 I'm going to do an import for 3:51 reverse lazy, so that I can get that URL without having to have like a method 3:57 that does that, and then like I said I still need to use the login function. 4:03 So I'm going to do from Django.contrib.log and forward login. 4:08 Okay, pretty sure I'm all ready to do this view. 4:13 Now this isn't the simplest view ever, so stick with me to get through this one. 4:17 So LoginView(generic.FormView) and 4:23 then the form_class is going to be AuthenticationForm. 4:28 The success URL is going to be 4:35 reverse lazy post going all. 4:40 Because I want to go to all the posts once you're logged in and 4:45 the template name is going to be accountslogin.html. 4:50 So far, pretty basic. 4:55 But now I need to override get_form, 4:57 and it takes two arguments which is self and form_class. 5:01 Form_class by default is none. 5:05 You should be used to this kind of thing with our mix-ins. 5:09 We set something to none and then we check to see if it's none. 5:12 So if one class is none, then the form 5:15 class is equal to self-Git form class. 5:20 And then we're gonna to return the form class. 5:25 Now the default view just or 5:29 the default class rather just does this get form cards and that's it. 5:32 But the authentication form of the first argument to it has to be the request. 5:37 So I need to send back self.request and then **self.get_form_kwargs. 5:42 And then, if the form is valid, so they've successfully submitted and 5:50 the user is a real user then I'm gonna call log in, and 5:57 I'm gonna pass it self.request, because that's where it creates the session and 6:01 all the data that actually validates the request as being from the user. 6:06 and then I'm going to call form.get_user, and this is a method provided by 6:10 the authentication form for getting the user that's been authenticated. 6:15 Then all return super( )_form_valid(form). 6:20 All right, so not the easiest, simplest view ever but it's not terrible either. 6:26 Okay, so 6:32 I do need a template though cuz I said I was gonna have this login.html template. 6:33 So I'm gonna need that. 6:38 And this is going to extend the layout.html template 6:41 which is my template that just kind of covers everything. 6:46 And then I'm gonna load the bootstrap3 library. 6:49 So bootstrap3 is a library that lets you automatically create some bootstrap3 6:53 things in your templates and 6:58 the template that I'm using the, 7:02 the design to build that I got uses bootstrap3. 7:07 So that's why I'm using the bootstrap3 library here. 7:12 So inside of here I'm going to make a div which is a container. 7:19 Apparently it automatically creates an extra div for me, thanks. 7:27 And then I'm going to try on that just as log in. 7:30 I make a form where the method is post. 7:33 I'm going to enter the CSRF token, or print that out at least. 7:37 And then I'm gonna use the bootstrap form template tag to render my form. 7:44 And then I'm gonna do an input type = "submit" value = 7:53 "Login" class = "btn btn-default". 7:57 Alright. 8:04 So that should handle all the template work that I need to do. 8:05 Basically I'm just printing out a form, right? 8:09 This is equivalent to doing like form.asp, 8:12 but the fields will get some special CSS, and or 8:17 some special html wrapped around them so they take advantage of the bootstrap3 CSS. 8:21 Okay, last thing I should have to do is to make a URL for this. 8:26 So url and 8:31 I'm just gonna say login and 8:34 views.LoginView.as_view() and name='login'. 8:39 All right, so now you will to go and test this out. 8:46 So, if I go to accounts login. 8:48 And restart my server here. 8:57 And there we go, okay? 9:02 And I should have to log in with my usual username and 9:03 password, and if this worked, this menu should change. 9:09 Yep, there we go so now I have post communities. 9:13 I can see the thing, where I can make new communities. 9:15 And, I can delete my post. 9:17 So, that's pretty cool, it works. 9:19 Now, I told you earlier though, that there were multiple approaches. 9:21 And, there just happens to be an easier way. 9:25 Honestly, I think this one's pretty easy. 9:29 It's not that bad, but what if you could do all of this, and 9:31 even a little bit more in a single line of code? 9:35 Well, a single line of code and a copy of the template that I just made. 9:38 Yeah? Okay. 9:42 So back over here in my MSD urls.py, I'm going to add a new line Of URL's. 9:43 Now I'm gonna put it below this one because django looks from top to bottom. 9:52 I have a feeling I'm wanna override some accounts URL's later. 9:57 So that way I can kind of put one here, take one out whatever. 10:01 So we're gonna accounts again, and 10:05 I'm going to include django.contrib.auth.urls. 10:11 Now I'm not going to give this one a namespace, 10:14 because these are Django's URLs. 10:18 I don't want to, I just don't want to namespace them. 10:19 And then I'm going to go over here and 10:22 I'm going to comment out this one, because I don't want to use it anymore. 10:24 All right, I want the Django provided one for login to work. 10:28 If I refresh this URL accounts log in, I get a template doesn't exist. 10:31 And it's looking for a registration login.html. 10:40 And that's true. 10:43 That template does not exist. 10:44 So I'm gonna come down here to my global templates directory. 10:46 I want to make a new folder called registration and then inside there. 10:50 I'm gonna make a new file. 10:55 That's called login.html cuz that's what it's looking for and 10:57 then I'm gonna to take this login, copy, paste, save, refresh. 11:01 Hey look it's the same form. 11:09 It looks exactly the same. 11:11 All right. So now I should be able to log in 11:13 here as well. 11:15 So if I do kennethlove, test password. 11:16 Then I should still see but I got a 404 something's not found what's not found? 11:21 It's trying to go to accounts profile, why is it? 11:26 Why is trying to go there? 11:30 Well I don't have that view and I don't want. 11:31 I'm not going to make that right now. 11:34 So I need to deal with this and the way that I deal with this is 11:37 by changing it inside of msg's settings.py. 11:41 Then at the bottom, I'm gonna add a new setting and 11:45 the setting is named log-in redirect URL. 11:50 And so this can actually be a URL like /hello. 11:54 Or this can be a URL name. 11:58 I want this to be the name posts all, so I'm going to redirect to there. 12:00 So now if I go back and 12:06 I log in. 12:12 Then I should, now I get taken to the Post page. 12:15 Cool, there it is. 12:20 Thanks to code already provided by Django, 12:22 you didn't have to write a lot of new code. 12:24 That's exactly how Frameworks was supposed to work. 12:26 You'll see that as a common pattern throughout this course. 12:28 I'll be using Django's tools as often as possible. 12:31 Now though, users can log in, but then they're trapped and can't log out. 12:34 Take care of that with me in the next video. 12:38
You need to sign up for Treehouse in order to download course files.Sign up