title
Python Django Tutorial: Full-Featured Web App Part 10 - Create, Update, and Delete Posts

description
In this Python Django Tutorial, we will be learning how to use class-based views in order to create, update, and delete posts. These class-based views are very convenient once we get used to using them properly. Let's get started... The code for this series can be found at: https://github.com/CoreyMSchafer/code_snippets/tree/master/Django_Blog ✅ Support My Channel Through Patreon: https://www.patreon.com/coreyms ✅ Become a Channel Member: https://www.youtube.com/channel/UCCezIgC97PvUuR4_gbFUs5g/join ✅ One-Time Contribution Through PayPal: https://goo.gl/649HFY ✅ Cryptocurrency Donations: Bitcoin Wallet - 3MPH8oY2EAgbLVy7RBMinwcBntggi7qeG3 Ethereum Wallet - 0x151649418616068fB46C3598083817101d3bCD33 Litecoin Wallet - MPvEBY5fxGkmPQgocfJbxP6EmTo5UUXMot ✅ Corey's Public Amazon Wishlist http://a.co/inIyro1 ✅ Equipment I Use and Books I Recommend: https://www.amazon.com/shop/coreyschafer ▶️ You Can Find Me On: My Website - http://coreyms.com/ My Second Channel - https://www.youtube.com/c/coreymschafer Facebook - https://www.facebook.com/CoreyMSchafer Twitter - https://twitter.com/CoreyMSchafer Instagram - https://www.instagram.com/coreymschafer/ #Python #Django

detail
{'title': 'Python Django Tutorial: Full-Featured Web App Part 10 - Create, Update, and Delete Posts', 'heatmap': [{'end': 483.815, 'start': 444.596, 'weight': 0.711}, {'end': 958.853, 'start': 862.273, 'weight': 0.839}, {'end': 1058.515, 'start': 989.976, 'weight': 0.767}, {'end': 1119.041, 'start': 1081.326, 'weight': 0.983}, {'end': 1377.195, 'start': 1342.121, 'weight': 0.852}, {'end': 1759.307, 'start': 1719.824, 'weight': 1}, {'end': 1861.205, 'start': 1786.134, 'weight': 0.746}, {'end': 2018.904, 'start': 1941.478, 'weight': 0.803}, {'end': 2524.168, 'start': 2489.256, 'weight': 0.823}], 'summary': 'This tutorial series on python django covers adding user posts to the homepage, implementing class-based views for the post model, debugging post creation, resolving integrity and redirect url errors, adding login functionality using a mixin, and securing and updating web application posts with a focus on security measures, author-specific access, and seamless user interface enhancements.', 'chapters': [{'end': 545.303, 'segs': [{'end': 31.482, 'src': 'embed', 'start': 0.229, 'weight': 0, 'content': [{'end': 6.451, 'text': "Hey there, how's it going everybody? In this video, we'll be adding the ability for users to add posts that will then show up on the homepage.", 'start': 0.229, 'duration': 6.222}, {'end': 12.853, 'text': "We'll also look at using class-based views in order to work with our post model and see how these class-based views can be useful.", 'start': 6.731, 'duration': 6.122}, {'end': 14.594, 'text': "So let's go ahead and get started.", 'start': 13.213, 'duration': 1.381}, {'end': 21.756, 'text': "So now that we'll be working with our blog post, we're going to be going back to our blog app that we created earlier in this series.", 'start': 15.094, 'duration': 6.662}, {'end': 22.736, 'text': 'So, first things.', 'start': 22.116, 'duration': 0.62}, {'end': 31.482, 'text': "first, I'm going to open up the blog views and we're going to look at using class-based views in order to display, update and delete new posts.", 'start': 22.736, 'duration': 8.746}], 'summary': 'Tutorial on adding user posts and using class-based views for blog app.', 'duration': 31.253, 'max_score': 0.229, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU229.jpg'}, {'end': 83.546, 'src': 'embed', 'start': 56.703, 'weight': 2, 'content': [{'end': 59.865, 'text': 'So now there are these things called class-based views.', 'start': 56.703, 'duration': 3.162}, {'end': 66.169, 'text': 'And those have a lot more built-in functionality that will try to handle a lot of the back-end logic for us.', 'start': 60.265, 'duration': 5.904}, {'end': 73.074, 'text': "So I'm going to create a class-based view for our homepage so that we can see what this looks like compared to a function view.", 'start': 66.549, 'duration': 6.525}, {'end': 76.358, 'text': 'So first of all, there are different kinds of class-based views.', 'start': 73.374, 'duration': 2.984}, {'end': 83.546, 'text': 'There are list views, detail views, create views, update views, and delete views, and a couple more.', 'start': 76.718, 'duration': 6.828}], 'summary': 'Introducing class-based views with various functionalities for handling back-end logic and different types including list, detail, create, update, and delete views.', 'duration': 26.843, 'max_score': 56.703, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU56703.jpg'}, {'end': 213.364, 'src': 'embed', 'start': 190.031, 'weight': 1, 'content': [{'end': 197.78, 'text': 'So I will call this class post list view and I will inherit from that list view.', 'start': 190.031, 'duration': 7.749}, {'end': 206.774, 'text': 'and within our list view we need to create a variable called model, and this will tell our list view what model to query in order to create the list,', 'start': 197.78, 'duration': 8.994}, {'end': 209.458, 'text': 'and in this case we want it to be all of our posts.', 'start': 206.774, 'duration': 2.684}, {'end': 213.364, 'text': "so we'll set that model equal to posts now.", 'start': 209.458, 'duration': 3.906}], 'summary': "Create a class 'post list view' inheriting from list view with model='posts'.", 'duration': 23.333, 'max_score': 190.031, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU190031.jpg'}, {'end': 280.606, 'src': 'embed', 'start': 229.253, 'weight': 3, 'content': [{'end': 237.018, 'text': 'we can open up our blog urls.py module and say that we want to use this post list view instead of our current home function.', 'start': 229.253, 'duration': 7.765}, {'end': 240.5, 'text': "So within our blog app, let's open up those URLs.", 'start': 237.478, 'duration': 3.022}, {'end': 246.604, 'text': "And instead of using this views.home, we're instead going to use our post list view.", 'start': 241.061, 'duration': 5.543}, {'end': 248.546, 'text': 'So let me actually import that directly.', 'start': 246.844, 'duration': 1.702}, {'end': 254.049, 'text': "So I'll keep the view import that we have now, but I'll also add a direct import.", 'start': 248.606, 'duration': 5.443}, {'end': 259.632, 'text': "So I'll say from.views import post list view.", 'start': 254.089, 'duration': 5.543}, {'end': 266.878, 'text': "And now instead of using our home view, I'm going to replace this here with this post list view.", 'start': 259.973, 'duration': 6.905}, {'end': 271.901, 'text': "Now when we use class face views, we can't just pass in the class like this.", 'start': 267.598, 'duration': 4.303}, {'end': 274.442, 'text': 'It has to be converted into an actual view.', 'start': 272.301, 'duration': 2.141}, {'end': 278.885, 'text': "And they have a method available that does this that's called as view.", 'start': 274.963, 'duration': 3.922}, {'end': 280.606, 'text': 'So we need to add that on.', 'start': 279.065, 'duration': 1.541}], 'summary': 'Replace views.home with post list view in blog urls.py module.', 'duration': 51.353, 'max_score': 229.253, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU229253.jpg'}, {'end': 335.883, 'src': 'embed', 'start': 303.375, 'weight': 4, 'content': [{'end': 308.096, 'text': 'So by default, class-based views look for templates of a certain naming pattern.', 'start': 303.375, 'duration': 4.721}, {'end': 315.579, 'text': 'So we can see here that it is looking for blog forward slash post underscore list dot HTML.', 'start': 308.477, 'duration': 7.102}, {'end': 321.225, 'text': 'So let me write this out so that you can see this a little bit better.', 'start': 316.44, 'duration': 4.785}, {'end': 335.883, 'text': 'So this is looking for a template with the naming convention of the app and then forward slash the model and then underscore and then the view type template.', 'start': 321.626, 'duration': 14.257}], 'summary': 'Class-based views default template naming convention: app/model_viewtype.html', 'duration': 32.508, 'max_score': 303.375, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU303375.jpg'}, {'end': 483.815, 'src': 'heatmap', 'start': 436.871, 'weight': 7, 'content': [{'end': 444.156, 'text': 'or we can set one more variable in our list view and let the class know that we want that variable to be called post instead.', 'start': 436.871, 'duration': 7.285}, {'end': 451.241, 'text': "So since we already have the template created, let's just go ahead and set this variable here within our list view.", 'start': 444.596, 'duration': 6.645}, {'end': 459.705, 'text': 'So to change that, we can set an attribute here and this will be called context underscore object underscore name.', 'start': 451.581, 'duration': 8.124}, {'end': 465.587, 'text': "And we will set that equal to post since that's what it is up here in our home template.", 'start': 460.086, 'duration': 5.501}, {'end': 467.967, 'text': 'And just setting those three attributes should do it.', 'start': 465.867, 'duration': 2.1}, {'end': 474.509, 'text': 'So now, if we save those changes and then reload this in our browser, so reload our homepage,', 'start': 468.267, 'duration': 6.242}, {'end': 478.77, 'text': 'then now we can see that we got the same thing as when we were using our function view.', 'start': 474.509, 'duration': 4.261}, {'end': 483.815, 'text': "Now one thing that isn't really right about our blog right now is the ordering of our posts.", 'start': 479.25, 'duration': 4.565}], 'summary': "Setting variable 'post' in list view to display blog posts, achieving same result as function view.", 'duration': 22.834, 'max_score': 436.871, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU436871.jpg'}, {'end': 545.303, 'src': 'embed', 'start': 525.005, 'weight': 8, 'content': [{'end': 534.994, 'text': 'so I will say I will create a new attribute here called ordering and set this equal to and we want to set this equal to date posted.', 'start': 525.005, 'duration': 9.989}, {'end': 540.058, 'text': "now this will order our post from oldest to newest, like it's doing right now.", 'start': 534.994, 'duration': 5.064}, {'end': 545.303, 'text': 'now, if we want to go from newest to oldest, then we can just put a minus sign here at the front.', 'start': 540.058, 'duration': 5.245}], 'summary': "Creating a new attribute 'ordering' to sort posts from oldest to newest, and using a minus sign for newest to oldest.", 'duration': 20.298, 'max_score': 525.005, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU525005.jpg'}], 'start': 0.229, 'title': 'Adding user posts & class-based views', 'summary': 'Covers adding user posts to the homepage, implementing class-based views for the post model, and the various types of class-based views available in django, including list, detail, create, update, and delete views.', 'chapters': [{'end': 229.253, 'start': 0.229, 'title': 'Adding user posts & class-based views', 'summary': 'Covers adding the ability for users to add posts to the homepage, implementing class-based views to work with the post model, and the different types of class-based views available in django, including list views, detail views, create views, update views, and delete views.', 'duration': 229.024, 'highlights': ['The chapter covers adding the ability for users to add posts to the homepage', 'Implementing class-based views to work with the post model', 'Different types of class-based views available in Django']}, {'end': 545.303, 'start': 229.253, 'title': 'Updating blog urls and views', 'summary': 'Discusses updating blog urls and views, including changing the view in the url module, converting class-based views, handling template naming conventions, setting template names, and altering the post order in the list view.', 'duration': 316.05, 'highlights': ['The chapter discusses updating blog URLs and views, including changing the view in the URL module, converting class-based views, handling template naming conventions, setting template names, and altering the post order in the list view.', "By using class-based views, we can convert a class to an actual view using the method 'as_view', and then execute it.", "Class-based views look for templates with a specific naming pattern, such as 'app/model_viewtype.html', and we can change the template that a view uses.", "The list view defaults to calling the variable 'object_list', but we can set it to a custom variable, such as 'post', by using the attribute 'context_object_name'.", "Changing the order of posts in the list view is achieved by adding an 'ordering' attribute with the desired field, such as 'date posted', and using a minus sign to reverse the order."]}], 'duration': 545.074, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU229.jpg', 'highlights': ['The chapter covers adding the ability for users to add posts to the homepage', 'Implementing class-based views to work with the post model', 'Different types of class-based views available in Django', 'Updating blog URLs and views, including changing the view in the URL module', 'Converting class-based views, handling template naming conventions, setting template names', "By using class-based views, we can convert a class to an actual view using the method 'as_view', and then execute it", "Class-based views look for templates with a specific naming pattern, such as 'app/model_viewtype.html', and we can change the template that a view uses", "The list view defaults to calling the variable 'object_list', but we can set it to a custom variable, such as 'post', by using the attribute 'context_object_name'", "Changing the order of posts in the list view is achieved by adding an 'ordering' attribute with the desired field, such as 'date posted', and using a minus sign to reverse the order"]}, {'end': 1155.235, 'segs': [{'end': 597.739, 'src': 'embed', 'start': 567.438, 'weight': 0, 'content': [{'end': 571.461, 'text': 'So here was our home function and here is our home list view.', 'start': 567.438, 'duration': 4.023}, {'end': 576.663, 'text': "So we can see that we're not really saving any lines of code in this example compared to the function view.", 'start': 571.821, 'duration': 4.842}, {'end': 581.184, 'text': 'But in our class based view, we are basically just setting some variables.', 'start': 577.043, 'duration': 4.141}, {'end': 587.066, 'text': 'And in our function view, we had to actually render a function and explicitly pass in that information.', 'start': 581.584, 'duration': 5.482}, {'end': 591.912, 'text': 'Now we could have saved some lines of code if we had used generic view defaults.', 'start': 587.546, 'duration': 4.366}, {'end': 597.739, 'text': 'So if I had created a template with the naming convention that our list view was looking for,', 'start': 592.232, 'duration': 5.507}], 'summary': 'Comparison of lines of code between class based view and function view.', 'duration': 30.301, 'max_score': 567.438, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU567438.jpg'}, {'end': 648.371, 'src': 'embed', 'start': 619.522, 'weight': 2, 'content': [{'end': 626.468, 'text': "So let's actually do this with our next class based view and stick to the conventions so that we can see how this cuts down on code.", 'start': 619.522, 'duration': 6.946}, {'end': 630.412, 'text': "Okay, so to do this, let's create a view for individual posts.", 'start': 626.769, 'duration': 3.643}, {'end': 639.041, 'text': "Now, when we look at an individual post, this is going to be a detail view since we're going to be looking at the details of a single post object.", 'start': 630.792, 'duration': 8.249}, {'end': 642.564, 'text': "So to create a detail view, let's first import it.", 'start': 639.361, 'duration': 3.203}, {'end': 648.371, 'text': "So up here at the top where we imported list view, let's also import detail view.", 'start': 642.705, 'duration': 5.666}], 'summary': 'Creating a detail view to display individual post objects, following conventions to reduce code.', 'duration': 28.849, 'max_score': 619.522, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU619522.jpg'}, {'end': 958.853, 'src': 'heatmap', 'start': 862.273, 'weight': 0.839, 'content': [{'end': 864.134, 'text': "so in this case it's going to be detail.", 'start': 862.273, 'duration': 1.861}, {'end': 871.219, 'text': 'so this is going to be looking for a template called blog forward slash post underscore detail dot HTML.', 'start': 864.134, 'duration': 7.085}, {'end': 878.504, 'text': "So let's create a template with that name so that it finds it automatically, without us needing to specify a template name,", 'start': 871.519, 'duration': 6.985}, {'end': 880.105, 'text': 'like we did in the post list view.', 'start': 878.504, 'duration': 1.601}, {'end': 885.209, 'text': "So within our templates, I'm going to open the subdirectory of blog.", 'start': 880.505, 'duration': 4.704}, {'end': 888.473, 'text': "And within blog, let's create a new template.", 'start': 885.59, 'duration': 2.883}, {'end': 892.698, 'text': 'And I will call this post underscore detail dot HTML.', 'start': 888.653, 'duration': 4.045}, {'end': 898.245, 'text': "And this is going to be very similar to home dot HTML, except we're just going to have a single post.", 'start': 893.119, 'duration': 5.126}, {'end': 901.489, 'text': 'So let me copy home dot HTML.', 'start': 898.585, 'duration': 2.904}, {'end': 904.872, 'text': 'paste this in to post detail.', 'start': 902.29, 'duration': 2.582}, {'end': 909.598, 'text': "but the difference here is that we don't need to loop over post, since there's only going to be one.", 'start': 904.872, 'duration': 4.726}, {'end': 919.549, 'text': "so I'm going to remove our for loop here and remember there is an end to the for loop down here and now I will unindent this and fix this.", 'start': 909.598, 'duration': 9.951}, {'end': 924.573, 'text': 'let me fix the indentation here and there are just a couple more changes here.', 'start': 919.549, 'duration': 5.024}, {'end': 934.297, 'text': "so, for example, we don't need the title of our post to be a link anymore, because that link on the home page is what takes us to the detailed view.", 'start': 924.573, 'duration': 9.724}, {'end': 936.938, 'text': 'so now we can just leave it as an h2 tag.', 'start': 934.297, 'duration': 2.641}, {'end': 939.9, 'text': 'but i still want this article title class here.', 'start': 936.938, 'duration': 2.962}, {'end': 942.501, 'text': "so i'm going to copy that article title class.", 'start': 939.9, 'duration': 2.601}, {'end': 945.383, 'text': 'but now we can just remove the anchor tag.', 'start': 943.041, 'duration': 2.342}, {'end': 951.447, 'text': "so i'm going to remove the closing anchor tag there and remove this whole opening anchor tag here,", 'start': 945.383, 'duration': 6.064}, {'end': 956.611, 'text': "and then i'm going to paste that class into our h2 tag there instead.", 'start': 951.447, 'duration': 5.164}, {'end': 958.853, 'text': 'okay, and just one more change that we need to make.', 'start': 956.611, 'duration': 2.242}], 'summary': 'Creating a new template for post detail without loop over post.', 'duration': 96.58, 'max_score': 862.273, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU862273.jpg'}, {'end': 1058.515, 'src': 'heatmap', 'start': 989.976, 'weight': 0.767, 'content': [{'end': 993.138, 'text': "And for the author, I'm going to say object.author.", 'start': 989.976, 'duration': 3.162}, {'end': 996.861, 'text': "For the date posted, we'll do object.datePosted.", 'start': 993.318, 'duration': 3.543}, {'end': 1000.322, 'text': 'For the title, we will say object.title.', 'start': 997.321, 'duration': 3.001}, {'end': 1003.263, 'text': 'And for the content, object.content.', 'start': 1000.822, 'duration': 2.441}, {'end': 1005.864, 'text': 'And I think that is the last one.', 'start': 1003.403, 'duration': 2.461}, {'end': 1010.925, 'text': "Okay, so now let's save this and open a post in our browser and see if this is working.", 'start': 1006.124, 'duration': 4.801}, {'end': 1015.667, 'text': 'So first I will check the dev server and that is running.', 'start': 1011.306, 'duration': 4.361}, {'end': 1020.53, 'text': "And now let's go to a URL for a specific post.", 'start': 1016.207, 'duration': 4.323}, {'end': 1024.252, 'text': 'So I will do forward slash post forward slash one.', 'start': 1020.87, 'duration': 3.382}, {'end': 1026.992, 'text': 'And we can see that that displays our blog one.', 'start': 1024.551, 'duration': 2.441}, {'end': 1031.836, 'text': "So now we can see that we've got pages specifically for these individual posts.", 'start': 1027.373, 'duration': 4.463}, {'end': 1037.398, 'text': 'Now remember in our views, all we needed was to specify that model on our detail view.', 'start': 1032.256, 'duration': 5.142}, {'end': 1040.161, 'text': 'and it handled the rest of that functionality for us.', 'start': 1037.919, 'duration': 2.242}, {'end': 1048.087, 'text': "Okay, so now that we actually have these individual pages, let's add links to these routes for the individual posts on our homepage.", 'start': 1040.521, 'duration': 7.566}, {'end': 1053.732, 'text': 'So right now, those are just dead links because I was waiting until we got the detail routes working.', 'start': 1048.367, 'duration': 5.365}, {'end': 1058.515, 'text': 'So if we go to the homepage right now, we can see that these actually go nowhere.', 'start': 1054.052, 'duration': 4.463}], 'summary': 'Configuring routes for individual posts, creating detail views, and adding links to homepage for improved navigation.', 'duration': 68.539, 'max_score': 989.976, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU989976.jpg'}, {'end': 1110.477, 'src': 'embed', 'start': 1081.326, 'weight': 3, 'content': [{'end': 1086.768, 'text': "So in order to link to that individual post, we can use the URL tag that we've seen before.", 'start': 1081.326, 'duration': 5.442}, {'end': 1096.671, 'text': "So I'll say URL and the name of that route was post detail and now we also had a parameter in that URL.", 'start': 1086.788, 'duration': 9.883}, {'end': 1100.833, 'text': "so remember it's the ID for the individual post.", 'start': 1096.671, 'duration': 4.162}, {'end': 1105.935, 'text': 'so we can pass that into the route just by adding this on to the URL tag here.', 'start': 1100.833, 'duration': 5.102}, {'end': 1110.477, 'text': "so I'll say post.id and that'll make sure that that gets passed in.", 'start': 1105.935, 'duration': 4.542}], 'summary': 'Using url tag to link to individual posts with post detail route and id parameter.', 'duration': 29.151, 'max_score': 1081.326, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1081326.jpg'}, {'end': 1119.041, 'src': 'heatmap', 'start': 1081.326, 'weight': 0.983, 'content': [{'end': 1086.768, 'text': "So in order to link to that individual post, we can use the URL tag that we've seen before.", 'start': 1081.326, 'duration': 5.442}, {'end': 1096.671, 'text': "So I'll say URL and the name of that route was post detail and now we also had a parameter in that URL.", 'start': 1086.788, 'duration': 9.883}, {'end': 1100.833, 'text': "so remember it's the ID for the individual post.", 'start': 1096.671, 'duration': 4.162}, {'end': 1105.935, 'text': 'so we can pass that into the route just by adding this on to the URL tag here.', 'start': 1100.833, 'duration': 5.102}, {'end': 1110.477, 'text': "so I'll say post.id and that'll make sure that that gets passed in.", 'start': 1105.935, 'duration': 4.542}, {'end': 1114.919, 'text': "if I go to our URLs, that'll get passed in as the primary key here in the URL.", 'start': 1110.477, 'duration': 4.442}, {'end': 1119.041, 'text': "So now let's go back to our browser and reload our homepage.", 'start': 1115.359, 'duration': 3.682}], 'summary': 'Using url tag to link to individual post with post id parameter.', 'duration': 37.715, 'max_score': 1081.326, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1081326.jpg'}, {'end': 1160.798, 'src': 'embed', 'start': 1130.547, 'weight': 4, 'content': [{'end': 1135.469, 'text': 'So if we test some of these, then we can see that those are now working.', 'start': 1130.547, 'duration': 4.922}, {'end': 1140.147, 'text': "Now if I try to go to a post that doesn't exist, then I should get a 404 error.", 'start': 1135.805, 'duration': 4.342}, {'end': 1143.449, 'text': "That means that the post with that ID doesn't exist.", 'start': 1140.447, 'duration': 3.002}, {'end': 1150.453, 'text': "So if I go up and try to go to, let's see, instead I'll go to post 10 instead of post 1.", 'start': 1143.809, 'duration': 6.644}, {'end': 1155.235, 'text': "Now we don't have a post 10, so we can see here that this says page not found 404.", 'start': 1150.453, 'duration': 4.782}, {'end': 1160.798, 'text': "And that's good that we get that error because that route wouldn't exist unless we had a post with that ID.", 'start': 1155.235, 'duration': 5.563}], 'summary': 'Testing shows 404 error for non-existent post id, confirming non-existence of post 10.', 'duration': 30.251, 'max_score': 1130.547, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1130547.jpg'}], 'start': 545.723, 'title': 'Class-based views vs function views', 'summary': 'Discusses the differences between class-based views and function views, highlighting the potential code reduction and simplification achievable through the use of generic view defaults, with an example demonstrating how a class-based view can be implemented with just a single line of code.', 'chapters': [{'end': 619.122, 'start': 545.723, 'title': 'Class-based views vs function views', 'summary': 'Discusses the differences between class-based views and function views, highlighting the potential code reduction and simplification achievable through the use of generic view defaults, with an example demonstrating how a class-based view can be implemented with just a single line of code.', 'duration': 73.399, 'highlights': ['The chapter compares class-based views and function views, emphasizing the minimal code reduction in the example provided (Relevance: 5)', 'It highlights the differences between the home function and home list view, showcasing that class-based views involve setting variables while function views require rendering functions and explicitly passing in information (Relevance: 4)', 'It explains the potential for code reduction by utilizing generic view defaults, illustrating that a working class-based view can be achieved with just a single line of code if conventions are followed (Relevance: 3)']}, {'end': 1155.235, 'start': 619.522, 'title': 'Creating detail view for individual posts', 'summary': 'Demonstrates the creation of a detail view for individual posts, including the process of importing, setting up url patterns, creating a template, and adding links to individual posts, resulting in efficient code organization and functionality.', 'duration': 535.713, 'highlights': ['The process of creating a detail view for individual posts is demonstrated, emphasizing the import of detail view, setting up URL patterns, and creating a template for efficient code organization.', 'The use of URL tags to add links to individual posts on the homepage is explained, showcasing the passing of parameters to the route for efficient functionality.', 'The functionality of the detail view for individual posts is tested, including handling non-existent post IDs and verifying the 404 error response for efficient error handling.']}], 'duration': 609.512, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU545723.jpg', 'highlights': ['The chapter compares class-based views and function views, emphasizing the minimal code reduction in the example provided (Relevance: 5)', 'The highlights the differences between the home function and home list view, showcasing that class-based views involve setting variables while function views require rendering functions and explicitly passing in information (Relevance: 4)', 'The process of creating a detail view for individual posts is demonstrated, emphasizing the import of detail view, setting up URL patterns, and creating a template for efficient code organization (Relevance: 3)', 'The use of URL tags to add links to individual posts on the homepage is explained, showcasing the passing of parameters to the route for efficient functionality (Relevance: 2)', 'The functionality of the detail view for individual posts is tested, including handling non-existent post IDs and verifying the 404 error response for efficient error handling (Relevance: 1)']}, {'end': 1592.365, 'segs': [{'end': 1211.93, 'src': 'embed', 'start': 1180.351, 'weight': 1, 'content': [{'end': 1182.912, 'text': "So let's open back up our views here.", 'start': 1180.351, 'duration': 2.561}, {'end': 1185.874, 'text': 'So I have the views open here.', 'start': 1183.252, 'duration': 2.622}, {'end': 1189.836, 'text': "I'll scroll up to the top because we need to import our create view.", 'start': 1186.094, 'duration': 3.742}, {'end': 1194.398, 'text': 'So right after detail view, I will import create view.', 'start': 1190.136, 'duration': 4.262}, {'end': 1197.9, 'text': 'Now we can see that our import line here is starting to get a little long.', 'start': 1194.898, 'duration': 3.002}, {'end': 1207.067, 'text': 'If you ever want to break up an import line, then you can just put these within parentheses here and put these on different lines.', 'start': 1198.24, 'duration': 8.827}, {'end': 1211.93, 'text': 'So I will move all of those and then end the parentheses.', 'start': 1207.347, 'duration': 4.583}], 'summary': 'Demonstrating how to manage import lines and views in code.', 'duration': 31.579, 'max_score': 1180.351, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1180351.jpg'}, {'end': 1314.969, 'src': 'embed', 'start': 1288.332, 'weight': 0, 'content': [{'end': 1294.456, 'text': "So I'm just going to copy this line here and then change this around a little bit.", 'start': 1288.332, 'duration': 6.124}, {'end': 1303.122, 'text': "So to create a new post, we'll go to post forward slash new and the view to handle that will be our post create view.", 'start': 1294.776, 'duration': 8.346}, {'end': 1308.325, 'text': 'and instead of post detail, we will call this post create.', 'start': 1303.862, 'duration': 4.463}, {'end': 1314.969, 'text': "okay, so at this point we know that we need a template for this view, but it might not be named what you think it's going to be named.", 'start': 1308.325, 'duration': 6.644}], 'summary': 'Creating a new post using post create view.', 'duration': 26.637, 'max_score': 1288.332, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1288332.jpg'}, {'end': 1377.195, 'src': 'heatmap', 'start': 1342.121, 'weight': 0.852, 'content': [{'end': 1349.704, 'text': "So up in my blog templates, I'm going to create a new file and let's create this called post underscore form dot HTML.", 'start': 1342.121, 'duration': 7.583}, {'end': 1356.725, 'text': "And this form template is going to be really similar to the other templates that contain forms that we've created in this series so far.", 'start': 1350.064, 'duration': 6.661}, {'end': 1364.669, 'text': 'So actually it would save us time just to grab our register template because there will only be a few changes that we need to make from that.', 'start': 1357.126, 'duration': 7.543}, {'end': 1367.07, 'text': 'Within our users app.', 'start': 1365.129, 'duration': 1.941}, {'end': 1377.195, 'text': "I'm going to go to those templates and I'm going to open the register template and copy that as a starting point and paste that into our post form template.", 'start': 1367.07, 'duration': 10.125}], 'summary': 'Creating a new post form template based on the register template with minimal changes.', 'duration': 35.074, 'max_score': 1342.121, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1342121.jpg'}, {'end': 1449.207, 'src': 'embed', 'start': 1424.188, 'weight': 3, 'content': [{'end': 1434.695, 'text': "so I will open this up and go back to our homepage, and now I'm going to go to the route of forward slash post, forward slash new,", 'start': 1424.188, 'duration': 10.507}, {'end': 1438.518, 'text': 'and we can see that it is a form to create a new blog post.', 'start': 1434.695, 'duration': 3.823}, {'end': 1440.42, 'text': 'okay, so this is looking really good.', 'start': 1438.518, 'duration': 1.902}, {'end': 1449.207, 'text': "so this is why class-based views are so powerful, because we didn't have to actually create a forms module to create this form or anything like that.", 'start': 1440.42, 'duration': 8.787}], 'summary': 'Demonstrating class-based views to create a new blog post without a separate forms module.', 'duration': 25.019, 'max_score': 1424.188, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1424188.jpg'}, {'end': 1512.113, 'src': 'embed', 'start': 1488.41, 'weight': 4, 'content': [{'end': 1496.638, 'text': "And the reason that we're getting an integrity error is because we're trying to create a post but it's saying that our author is null and that's not allowed.", 'start': 1488.41, 'duration': 8.228}, {'end': 1499.1, 'text': 'So every post needs to have an author.', 'start': 1496.978, 'duration': 2.122}, {'end': 1504.005, 'text': "Now we want the author of the post to be the current logged in user, but it doesn't know that.", 'start': 1499.46, 'duration': 4.545}, {'end': 1506.167, 'text': 'So we have to tell it in some way.', 'start': 1504.405, 'duration': 1.762}, {'end': 1512.113, 'text': 'So the way that we can do that is to override the form valid method for our create view.', 'start': 1506.648, 'duration': 5.465}], 'summary': 'Integrity error due to null author in post creation. need to override form valid method.', 'duration': 23.703, 'max_score': 1488.41, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1488410.jpg'}], 'start': 1155.235, 'title': 'Creating and using views for posts', 'summary': 'Covers creating, updating, and deleting views for posts, including importing and modifying views, updating urls, and creating a template. it also details the use of class-based views to create a form for new blog posts, addressing errors encountered during the process.', 'chapters': [{'end': 1424.188, 'start': 1155.235, 'title': 'Creating, updating, and deleting views for posts', 'summary': 'Covers the creation of a create, update, and delete view for posts, including importing and modifying views, updating urls, and creating a template for the new view.', 'duration': 268.953, 'highlights': ['Creating a create view for new posts', 'Importing and modifying views', 'Creating a template for the new view']}, {'end': 1592.365, 'start': 1424.188, 'title': 'Using class-based views to create a blog post form', 'summary': 'Details the use of class-based views to create a form for new blog posts, demonstrating the power of class-based views and addressing errors encountered during the process, such as the need to specify the author of the post.', 'duration': 168.177, 'highlights': ['The chapter details the use of class-based views to create a form for new blog posts', 'Addressing errors encountered, such as the need to specify the author of the post', 'Demonstrates the power of class-based views']}], 'duration': 437.13, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1155235.jpg', 'highlights': ['Creating a create view for new posts', 'Importing and modifying views', 'Creating a template for the new view', 'The chapter details the use of class-based views to create a form for new blog posts', 'Addressing errors encountered, such as the need to specify the author of the post', 'Demonstrates the power of class-based views']}, {'end': 1841.256, 'segs': [{'end': 1656.759, 'src': 'embed', 'start': 1592.365, 'weight': 0, 'content': [{'end': 1594.788, 'text': 'okay, so that should do it for setting the author.', 'start': 1592.365, 'duration': 2.423}, {'end': 1599.072, 'text': "so now let's try to create a new post in a browser and see what we get.", 'start': 1594.788, 'duration': 4.284}, {'end': 1604.498, 'text': "now i'm going to let you know that this still isn't going to work, but let's look at the error and see if it is helpful.", 'start': 1599.072, 'duration': 5.426}, {'end': 1611.166, 'text': "So we'll go back to the post forward, slash new and try to create another post.", 'start': 1604.878, 'duration': 6.288}, {'end': 1615.331, 'text': 'So fourth post and submit.', 'start': 1611.446, 'duration': 3.885}, {'end': 1619.056, 'text': "Okay, so we're no longer getting the integrity error about the author.", 'start': 1615.712, 'duration': 3.344}, {'end': 1619.697, 'text': "So that's good.", 'start': 1619.096, 'duration': 0.601}, {'end': 1623.862, 'text': "Now we're getting an error that says that we don't have a redirect URL.", 'start': 1620.157, 'duration': 3.705}, {'end': 1634.766, 'text': 'It says in the error message I know this is a little small here it says either provide a URL to redirect to or define a get absolute URL method on the model.', 'start': 1624.322, 'duration': 10.444}, {'end': 1641.488, 'text': "So basically it's telling us that it created the post successfully, but it doesn't know where we want to be redirected to now.", 'start': 1635.106, 'duration': 6.382}, {'end': 1647.993, 'text': 'So if we go back to the homepage, then we can see that our post was actually created here.', 'start': 1642.288, 'duration': 5.705}, {'end': 1648.953, 'text': "So that's good.", 'start': 1648.073, 'duration': 0.88}, {'end': 1656.759, 'text': "So now to get this working 100%, we just need to let the view know where we want to redirect once we've created the post.", 'start': 1649.394, 'duration': 7.365}], 'summary': 'Troubleshooting post creation, fixed author error, now addressing redirect url issue.', 'duration': 64.394, 'max_score': 1592.365, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1592365.jpg'}, {'end': 1768.074, 'src': 'heatmap', 'start': 1719.824, 'weight': 3, 'content': [{'end': 1729.008, 'text': 'so redirect will actually redirect you to a specific route, but reverse will simply return the full URL to that route as a string.', 'start': 1719.824, 'duration': 9.184}, {'end': 1737.653, 'text': 'so that is the difference between those, and in this case we simply want to return the URL as a string and let the view handle the redirect for us.', 'start': 1729.008, 'duration': 8.645}, {'end': 1741.155, 'text': 'So first we have to import the reverse function.', 'start': 1738.033, 'duration': 3.122}, {'end': 1748.72, 'text': "So up here at the top, I'm going to say from django.urls import reverse.", 'start': 1741.515, 'duration': 7.205}, {'end': 1759.307, 'text': "And now down in our post model, now we'll create that get absolute URL method to tell Django how to find the URL to any specific instance of a post.", 'start': 1749.601, 'duration': 9.706}, {'end': 1768.074, 'text': 'So to do this, we can say get absolute underscore URL, And this will take self as an argument.', 'start': 1759.687, 'duration': 8.387}], 'summary': 'Using reverse function to return the url as a string and defining get_absolute_url method for post model.', 'duration': 53.453, 'max_score': 1719.824, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1719824.jpg'}], 'start': 1592.365, 'title': 'Debugging post creation and django model object urls', 'summary': 'Discusses debugging the process of creating a new post and resolving integrity and redirect url errors, emphasizing the need to define a get absolute url method. it also demonstrates creating a get absolute url method within the django model to enable the framework to find the url of a specific instance and ensuring proper redirection.', 'chapters': [{'end': 1670.03, 'start': 1592.365, 'title': 'Debugging post creation and redirection', 'summary': 'Discusses debugging the process of creating a new post, resolving an integrity error, and addressing a redirect url error in a web browser, emphasizing the need to define a get absolute url method on the model for successful post creation and redirection.', 'duration': 77.665, 'highlights': ['The error message indicates the need to provide a URL to redirect to or define a get absolute URL method on the model for successful post creation and redirection.', 'It is important to let the view know where to redirect once a post is created, ideally to the detail page of the post that was just created.', 'The process involved debugging the errors related to author setting, integrity error, and redirect URL, ultimately leading to the successful creation of the post.']}, {'end': 1841.256, 'start': 1670.35, 'title': 'Django model object urls', 'summary': 'Demonstrates creating a get absolute url method within the django model to enable the framework to find the url of a specific instance, utilizing the reverse function to return the full url to a route and ensuring proper redirection.', 'duration': 170.906, 'highlights': ['Creating get absolute URL method in Django model', 'Utilizing the reverse function to return full URL to a route', 'Difference between redirect and reverse functions']}], 'duration': 248.891, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1592365.jpg', 'highlights': ['The error message indicates the need to provide a URL to redirect to or define a get absolute URL method on the model for successful post creation and redirection.', 'It is important to let the view know where to redirect once a post is created, ideally to the detail page of the post that was just created.', 'The process involved debugging the errors related to author setting, integrity error, and redirect URL, ultimately leading to the successful creation of the post.', 'Creating get absolute URL method in Django model', 'Utilizing the reverse function to return full URL to a route', 'Difference between redirect and reverse functions']}, {'end': 2097.748, 'segs': [{'end': 1889.187, 'src': 'embed', 'start': 1861.585, 'weight': 0, 'content': [{'end': 1866.67, 'text': "Now that would have also taken a lot more code if we'd done that with regular function views instead.", 'start': 1861.585, 'duration': 5.085}, {'end': 1873.235, 'text': 'So we would have needed to create forms and handle the post requests and save the information and all of that.', 'start': 1867.09, 'duration': 6.145}, {'end': 1880.402, 'text': 'But with these class-based views, we can do a lot of this just by knowing what attributes need to be set.', 'start': 1873.596, 'duration': 6.806}, {'end': 1885.246, 'text': 'So you can definitely save yourself a lot of lines of code once you get familiar with this kind of stuff.', 'start': 1880.742, 'duration': 4.504}, {'end': 1889.187, 'text': "okay. now there's actually one more thing that we need to do with this create view.", 'start': 1885.666, 'duration': 3.521}], 'summary': 'Class-based views can save a lot of code for forms and post requests.', 'duration': 27.602, 'max_score': 1861.585, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1861585.jpg'}, {'end': 2018.904, 'src': 'heatmap', 'start': 1893.448, 'weight': 2, 'content': [{'end': 1900.349, 'text': "so we need to make it so that if we try to access this route and we're not logged in, then we'll just be redirected to the login page.", 'start': 1893.448, 'duration': 6.901}, {'end': 1905.151, 'text': 'now we saw how to do this with function based views when we created our user profile page.', 'start': 1900.349, 'duration': 4.802}, {'end': 1908.891, 'text': 'so for function based views we use that login required decorator.', 'start': 1905.151, 'duration': 3.74}, {'end': 1911.272, 'text': "well, we can't use decorators on classes.", 'start': 1908.891, 'duration': 2.381}, {'end': 1918.336, 'text': "so what we are going to use here is something called a login mixin, And that's basically just a class that we inherit from.", 'start': 1911.272, 'duration': 7.064}, {'end': 1920.959, 'text': 'that will add that login functionality to the view.', 'start': 1918.336, 'duration': 2.623}, {'end': 1923.201, 'text': "So let's go ahead and add this in.", 'start': 1921.399, 'duration': 1.802}, {'end': 1929.788, 'text': "So I'm going to go back to our views here and go up to the top because we need to import this.", 'start': 1923.221, 'duration': 6.567}, {'end': 1938.477, 'text': 'And here at the top, I will import this by saying from Django dot contrib dot auth dot mixins dot.', 'start': 1930.208, 'duration': 8.269}, {'end': 1941.478, 'text': 'import and this is kind of long.', 'start': 1938.997, 'duration': 2.481}, {'end': 1951.74, 'text': "login required mixin and now we just want to add this to the classes that we are inheriting from and we'll want to add this to the very first one on the far left.", 'start': 1941.478, 'duration': 10.262}, {'end': 1955.641, 'text': "so I'm going to copy this and go down to our post create view.", 'start': 1951.74, 'duration': 3.901}, {'end': 1957.501, 'text': 'and we want to add this to the far left.', 'start': 1955.641, 'duration': 1.86}, {'end': 1962.922, 'text': 'so we want to inherit from the login required mixin and then the create view.', 'start': 1957.501, 'duration': 5.421}, {'end': 1972.907, 'text': "so now, if we save that and go back to our browser and log out and then try to add a new post, so I'll log out and then I will go to post forward,", 'start': 1962.922, 'duration': 9.985}, {'end': 1977.65, 'text': 'slash new and then you can see that we are redirected to the login page.', 'start': 1972.907, 'duration': 4.743}, {'end': 1979.531, 'text': "so that's good, okay.", 'start': 1977.65, 'duration': 1.881}, {'end': 1984.434, 'text': "so now let's create an update view so that we can update posts on the front end.", 'start': 1979.531, 'duration': 4.903}, {'end': 1986.675, 'text': 'so we should kind of be getting used to this by now.', 'start': 1984.434, 'duration': 2.241}, {'end': 1992.359, 'text': "so let's go back to the views here and at the top we will add to our list of imports.", 'start': 1986.675, 'duration': 5.684}, {'end': 1994.1, 'text': 'so I will import an update view.', 'start': 1992.359, 'duration': 1.741}, {'end': 2002.288, 'text': "And now down here under our create view, I'm just going to copy our create view because the update view is going to be very similar.", 'start': 1994.86, 'duration': 7.428}, {'end': 2009.274, 'text': "So I will paste that in and I will, let's see, call this post update view here.", 'start': 2002.708, 'duration': 6.566}, {'end': 2012.618, 'text': 'And we want to import from update view.', 'start': 2009.455, 'duration': 3.163}, {'end': 2018.904, 'text': 'And now we can actually leave this exactly the same in terms of the model and fields and the form save method.', 'start': 2012.898, 'duration': 6.006}], 'summary': 'Incorporated login functionality using a login mixin to redirect unauthorized access to the login page, and implemented an update view with similar structure to the create view.', 'duration': 108.84, 'max_score': 1893.448, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1893448.jpg'}, {'end': 2064.254, 'src': 'embed', 'start': 2033.578, 'weight': 8, 'content': [{'end': 2037.281, 'text': "And let's also not forget to import the view that we just created.", 'start': 2033.578, 'duration': 3.703}, {'end': 2040.184, 'text': 'So we created that post update view.', 'start': 2037.421, 'duration': 2.763}, {'end': 2043.485, 'text': "view. so now let's do the route for this.", 'start': 2040.564, 'duration': 2.921}, {'end': 2047.447, 'text': 'so i copied the post detail view and pasted that in here.', 'start': 2043.485, 'duration': 3.962}, {'end': 2052.768, 'text': "now, to update a post, we're going to need to include that primary key with that route as well,", 'start': 2047.447, 'duration': 5.321}, {'end': 2056.911, 'text': 'because we have to know what post that we are updating.', 'start': 2052.768, 'duration': 4.143}, {'end': 2064.254, 'text': 'so we will do post forward slash this primary key, and then after that we will do forward slash update.', 'start': 2056.911, 'duration': 7.343}], 'summary': 'Creating a route to update a post with primary key.', 'duration': 30.676, 'max_score': 2033.578, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2033578.jpg'}], 'start': 1841.256, 'title': 'Django class-based views and login functionality', 'summary': 'Explains the advantages of using class-based views in django, emphasizing reduced code and effort, and demonstrates adding login functionality using a mixin, leading to successful redirection to the login page when attempting to add a new post without being logged in.', 'chapters': [{'end': 1911.272, 'start': 1841.256, 'title': 'Class-based views in django', 'summary': 'Explains the advantages of using class-based views in django, highlighting how it reduces code and effort compared to regular function views, and demonstrates the need to enforce user authentication for a create view.', 'duration': 70.016, 'highlights': ['Using class-based views in Django reduces code and effort, providing a lot of functionality with just a few attributes, which would have required a lot more work in other frameworks.', 'Compared to regular function views, class-based views save a lot of lines of code by simplifying tasks like creating forms, handling post requests, and saving information.', 'Enforcing user authentication for a create view is necessary, redirecting users to the login page if they are not logged in, a concept previously implemented with the login required decorator in function-based views.']}, {'end': 1979.531, 'start': 1911.272, 'title': 'Adding login functionality with django mixin', 'summary': 'Demonstrates the process of adding a login functionality to a view using a login mixin, resulting in successful redirection to the login page when attempting to add a new post without being logged in.', 'duration': 68.259, 'highlights': ['The chapter demonstrates the process of adding a login functionality to a view using a login mixin, resulting in successful redirection to the login page when attempting to add a new post without being logged in.', 'Importing the login required mixin from Django dot contrib dot auth dot mixins and adding it to the classes being inherited from in order to incorporate the login functionality.', 'Inheriting from the login required mixin and the create view, ensuring that the login functionality is added to the view by adding it to the classes being inherited from.', 'Successfully redirected to the login page when attempting to add a new post without being logged in, indicating the successful incorporation of the login functionality.']}, {'end': 2097.748, 'start': 1979.531, 'title': 'Creating post update view', 'summary': 'Demonstrates the process of creating an update view to update posts on the front end, including importing the update view, defining the route, and handling the primary key for post updates.', 'duration': 118.217, 'highlights': ['The process of creating an update view for updating posts on the front end is explained.', 'Importing the update view and adding it to the list of imports.', 'Defining the route for updating a post and handling the primary key.']}], 'duration': 256.492, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU1841256.jpg', 'highlights': ['Using class-based views in Django reduces code and effort, providing a lot of functionality with just a few attributes, which would have required a lot more work in other frameworks.', 'Compared to regular function views, class-based views save a lot of lines of code by simplifying tasks like creating forms, handling post requests, and saving information.', 'The chapter demonstrates the process of adding a login functionality to a view using a login mixin, resulting in successful redirection to the login page when attempting to add a new post without being logged in.', 'Enforcing user authentication for a create view is necessary, redirecting users to the login page if they are not logged in, a concept previously implemented with the login required decorator in function-based views.', 'Inheriting from the login required mixin and the create view, ensuring that the login functionality is added to the view by adding it to the classes being inherited from.', 'Successfully redirected to the login page when attempting to add a new post without being logged in, indicating the successful incorporation of the login functionality.', 'The process of creating an update view for updating posts on the front end is explained.', 'Importing the update view and adding it to the list of imports.', 'Defining the route for updating a post and handling the primary key.', 'Importing the login required mixin from Django dot contrib dot auth dot mixins and adding it to the classes being inherited from in order to incorporate the login functionality.']}, {'end': 3181.962, 'segs': [{'end': 2163.21, 'src': 'embed', 'start': 2123.951, 'weight': 0, 'content': [{'end': 2129.473, 'text': "So I'll say blog five updated, my fifth updated post and submit that.", 'start': 2123.951, 'duration': 5.522}, {'end': 2131.714, 'text': 'So we can see that that updates our post.', 'start': 2129.833, 'duration': 1.881}, {'end': 2134.134, 'text': 'So that was pretty easy to put together.', 'start': 2132.214, 'duration': 1.92}, {'end': 2136.775, 'text': "Now, when you're building an application like this,", 'start': 2134.535, 'duration': 2.24}, {'end': 2143.998, 'text': 'you kind of need to be thinking about the different ways that people could use your app or try to abuse it and always try to plan for that.', 'start': 2136.775, 'duration': 7.223}, {'end': 2151.381, 'text': 'So for example, right now we have a login check on being able to update a post and to be able to create a post.', 'start': 2144.338, 'duration': 7.043}, {'end': 2158.226, 'text': 'but we are checking if the author of the post is the person trying to access this update page,', 'start': 2151.781, 'duration': 6.445}, {'end': 2163.21, 'text': "and that's important because we only want the people who wrote the post to be able to edit it.", 'start': 2158.226, 'duration': 4.984}], 'summary': 'Updated blog post submitted, emphasizing user access control and security measures.', 'duration': 39.259, 'max_score': 2123.951, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2123951.jpg'}, {'end': 2358.997, 'src': 'embed', 'start': 2332.994, 'weight': 8, 'content': [{'end': 2339.96, 'text': 'So if I reload this, Then we can see that we get a 404 or 403 response that says that this is forbidden.', 'start': 2332.994, 'duration': 6.966}, {'end': 2342.263, 'text': 'And that is the exact response that we want.', 'start': 2340.201, 'duration': 2.062}, {'end': 2343.705, 'text': 'So that is good.', 'start': 2342.604, 'duration': 1.101}, {'end': 2347.129, 'text': 'Okay, so that does it for the update view.', 'start': 2344.526, 'duration': 2.603}, {'end': 2352.095, 'text': "So lastly, we're also going to want to create a delete view for deleting posts.", 'start': 2347.549, 'duration': 4.546}, {'end': 2355.376, 'text': 'And the delete view is very similar to our detail view.', 'start': 2352.515, 'duration': 2.861}, {'end': 2358.997, 'text': "So I'm going to go back to our views and import our delete view.", 'start': 2355.396, 'duration': 3.601}], 'summary': 'Developed update and delete views for posts, ensuring 404 or 403 forbidden response.', 'duration': 26.003, 'max_score': 2332.994, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2332994.jpg'}, {'end': 2524.168, 'src': 'heatmap', 'start': 2489.256, 'weight': 0.823, 'content': [{'end': 2494.857, 'text': 'And this is called post underscore confirm underscore delete dot HTML.', 'start': 2489.256, 'duration': 5.601}, {'end': 2502.14, 'text': "and i'm just going to copy from our post form template that was used for our create and update templates.", 'start': 2495.857, 'duration': 6.283}, {'end': 2509.203, 'text': 'so i am going to copy from here and paste that into our post confirm, delete template.', 'start': 2502.14, 'duration': 7.063}, {'end': 2511.064, 'text': "and now i'll make a couple of changes here.", 'start': 2509.203, 'duration': 1.861}, {'end': 2517.647, 'text': "so the legend instead of this being blog post, i'm going to change this to delete post as the legend.", 'start': 2511.064, 'duration': 6.583}, {'end': 2520.368, 'text': "Now this doesn't actually pass in a form for us.", 'start': 2517.947, 'duration': 2.421}, {'end': 2524.168, 'text': 'So we can actually remove the crispy forms and the form line here.', 'start': 2520.508, 'duration': 3.66}], 'summary': 'Creating post_confirm_delete template with changes to the legend and removing crispy forms and form line.', 'duration': 34.912, 'max_score': 2489.256, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2489256.jpg'}, {'end': 2760.477, 'src': 'embed', 'start': 2730.102, 'weight': 9, 'content': [{'end': 2733.983, 'text': 'Now, if we read the error, then it actually tells us exactly what we need to do.', 'start': 2730.102, 'duration': 3.881}, {'end': 2737.365, 'text': 'It says that we need to provide a success URL.', 'start': 2734.364, 'duration': 3.001}, {'end': 2738.906, 'text': "So we'll go do that.", 'start': 2737.765, 'duration': 1.141}, {'end': 2743.768, 'text': "Now, when we get a failure on deletion, it actually doesn't do the deletion just in case.", 'start': 2739.306, 'duration': 4.462}, {'end': 2745.749, 'text': 'So that post will still be there.', 'start': 2744.068, 'duration': 1.681}, {'end': 2751.932, 'text': 'So if I go back to the homepage, then we can see that that post still exists.', 'start': 2746.369, 'duration': 5.563}, {'end': 2760.477, 'text': "So now I'm going to go back to our delete view and add a success URL so that our deletion knows where to redirect us if that works.", 'start': 2752.432, 'duration': 8.045}], 'summary': 'Error message prompts addition of success url for deletion view.', 'duration': 30.375, 'max_score': 2730.102, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2730102.jpg'}, {'end': 2825.741, 'src': 'embed', 'start': 2801.208, 'weight': 1, 'content': [{'end': 2807.694, 'text': "Let's click on blog five and I will go to blog five forward slash delete.", 'start': 2801.208, 'duration': 6.486}, {'end': 2810.957, 'text': "And it says, are you sure you want to delete this post? We'll click yes.", 'start': 2808.174, 'duration': 2.783}, {'end': 2813.658, 'text': 'and we can see that that post was now deleted.', 'start': 2811.597, 'duration': 2.061}, {'end': 2814.818, 'text': 'Okay, so that works.', 'start': 2813.938, 'duration': 0.88}, {'end': 2816.058, 'text': 'So that is great.', 'start': 2814.898, 'duration': 1.16}, {'end': 2825.741, 'text': "So in this one video, we've added the ability to list, view, create, update, and delete posts using these new class-based views.", 'start': 2816.398, 'duration': 9.343}], 'summary': 'Added ability to list, view, create, update, and delete posts using new class-based views.', 'duration': 24.533, 'max_score': 2801.208, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2801208.jpg'}, {'end': 2939.8, 'src': 'embed', 'start': 2913.502, 'weight': 4, 'content': [{'end': 2921.568, 'text': "so within our blog templates let's open up the post detail template and let's just put these buttons right after the author and the date.", 'start': 2913.502, 'duration': 8.066}, {'end': 2926.652, 'text': 'so right after the author and date here we can put in a conditional.', 'start': 2921.568, 'duration': 5.084}, {'end': 2935.218, 'text': 'so we will say if object dot author is equal to user, which is the current logged in user,', 'start': 2926.652, 'duration': 8.566}, {'end': 2939.8, 'text': 'then we can add in the buttons for the update and delete links.', 'start': 2935.878, 'duration': 3.922}], 'summary': 'Update and delete buttons added after author and date based on user status', 'duration': 26.298, 'max_score': 2913.502, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2913502.jpg'}, {'end': 3072.555, 'src': 'embed', 'start': 3043.106, 'weight': 3, 'content': [{'end': 3047.767, 'text': 'Okay, so with those changes in place, we should have links to all of the routes that we created in the video.', 'start': 3043.106, 'duration': 4.661}, {'end': 3050.548, 'text': "So let's give this one last look in the browser.", 'start': 3048.107, 'duration': 2.441}, {'end': 3055.35, 'text': 'So we will save all of those and open this up in the browser.', 'start': 3050.888, 'duration': 4.462}, {'end': 3058.831, 'text': "So we can see that since I'm logged in, we now have a new post link up here.", 'start': 3055.63, 'duration': 3.201}, {'end': 3063.352, 'text': 'So if I click on that, then it takes us to the route where we can create a new post.', 'start': 3058.971, 'duration': 4.381}, {'end': 3072.555, 'text': 'So if I go back to the homepage and click on a post that I have created, then we can see that we have an update and delete link here.', 'start': 3064.252, 'duration': 8.303}], 'summary': 'Implemented changes to create links for all routes, enabling easy navigation and access to new post creation and editing.', 'duration': 29.449, 'max_score': 3043.106, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU3043106.jpg'}, {'end': 3163.217, 'src': 'embed', 'start': 3137.486, 'weight': 7, 'content': [{'end': 3145.628, 'text': 'Hopefully now you have a pretty good idea for how you can use class-based views to list out different objects from our database and also how to view,', 'start': 3137.486, 'duration': 8.142}, {'end': 3148.488, 'text': 'update and delete those objects using these views.', 'start': 3145.628, 'duration': 2.86}, {'end': 3154.511, 'text': "Now in the next video, we'll learn how to paginate our site, so that our posts are broken up into different pages.", 'start': 3148.848, 'duration': 5.663}, {'end': 3158.594, 'text': "And we'll also see how to create a page for specific users' posts.", 'start': 3154.871, 'duration': 3.723}, {'end': 3163.217, 'text': 'But if you have any questions about what we covered in this video, then feel free to ask in the comment section below,', 'start': 3158.914, 'duration': 4.303}], 'summary': 'Learned to use class-based views for database operations, next: pagination and user-specific posts.', 'duration': 25.731, 'max_score': 3137.486, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU3137486.jpg'}], 'start': 2097.848, 'title': 'Securing web application posts', 'summary': 'Covers securing and updating web application posts, emphasizing the ease of updates, potential abuse considerations, and addressing vulnerabilities. it also discusses implementing security measures, author-specific access, and seamless user interface enhancements, enabling complete post functionality.', 'chapters': [{'end': 2187.004, 'start': 2097.848, 'title': 'Building secure web applications', 'summary': 'Demonstrates how to update and secure posts in a web application, highlighting the ease of updating posts, the importance of considering potential abuse, and the current vulnerability in the system that allows unauthorized users to update posts.', 'duration': 89.156, 'highlights': ['The system allows easy post updates, demonstrated by updating blog five with new content.', 'It is important to consider potential abuse when building an application, as demonstrated by the need to plan for unauthorized access to post updates.', 'The current system vulnerability allows unauthorized users to update posts, exemplified by the ability to update a post authored by another user.']}, {'end': 2825.741, 'start': 2187.004, 'title': 'Post update and delete security', 'summary': 'Discusses implementing security measures in the update and delete views, including allowing only the author of the post to update or delete it, resulting in a 404 or 403 response for unauthorized attempts and the addition of a success url for post deletion, ultimately enabling the functionality to list, view, create, update, and delete posts using class-based views.', 'duration': 638.737, 'highlights': ['Implemented security measures to allow only the author of the post to update or delete it', "Resulted in a 404 or 403 response for unauthorized attempts to update another user's post", 'Added a success URL for post deletion to redirect users after successful deletion', 'Enabled functionality to list, view, create, update, and delete posts using class-based views']}, {'end': 3181.962, 'start': 2826.141, 'title': 'Adding navigation links and conditional buttons', 'summary': 'Demonstrates adding navigation links to create, update, and delete posts, and conditional buttons based on user authentication, achieving a seamless user interface. it also hints at upcoming topics such as pagination and user-specific pages.', 'duration': 355.821, 'highlights': ['The video demonstrates adding navigation links to create, update, and delete posts, enhancing user interaction.', 'Conditional buttons are added based on user authentication, ensuring that only the post author can see the update and delete links.', 'Upcoming topics such as pagination and user-specific pages are hinted at, offering a glimpse of future learning.']}], 'duration': 1084.114, 'thumbnail': 'https://coursnap.oss-ap-southeast-1.aliyuncs.com/video-capture/-s7e_Fy6NRU/pics/-s7e_Fy6NRU2097848.jpg', 'highlights': ['Implemented security measures to allow only the author of the post to update or delete it', 'Enabled functionality to list, view, create, update, and delete posts using class-based views', 'The system allows easy post updates, demonstrated by updating blog five with new content', 'The video demonstrates adding navigation links to create, update, and delete posts, enhancing user interaction', 'Conditional buttons are added based on user authentication, ensuring that only the post author can see the update and delete links', 'It is important to consider potential abuse when building an application, as demonstrated by the need to plan for unauthorized access to post updates', 'The current system vulnerability allows unauthorized users to update posts, exemplified by the ability to update a post authored by another user', 'Upcoming topics such as pagination and user-specific pages are hinted at, offering a glimpse of future learning', "Resulted in a 404 or 403 response for unauthorized attempts to update another user's post", 'Added a success URL for post deletion to redirect users after successful deletion']}], 'highlights': ['Implemented security measures to allow only the author of the post to update or delete it', 'Using class-based views in Django reduces code and effort, providing a lot of functionality with just a few attributes, which would have required a lot more work in other frameworks', 'The chapter demonstrates the process of adding a login functionality to a view using a login mixin, resulting in successful redirection to the login page when attempting to add a new post without being logged in', 'The chapter covers adding the ability for users to add posts to the homepage', 'The process involved debugging the errors related to author setting, integrity error, and redirect URL, ultimately leading to the successful creation of the post', 'The process of creating an update view for updating posts on the front end is explained', 'The chapter details the use of class-based views to create a form for new blog posts', 'Enforcing user authentication for a create view is necessary, redirecting users to the login page if they are not logged in, a concept previously implemented with the login required decorator in function-based views', 'The functionality of the detail view for individual posts is tested, including handling non-existent post IDs and verifying the 404 error response for efficient error handling', 'The error message indicates the need to provide a URL to redirect to or define a get absolute URL method on the model for successful post creation and redirection']}