Jack Linke - Server-Side is Dead! Long Live Server-Side (+ HTMX)

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
[Music] welcome and thank you for joining me hopefully next time we'll get to do this in person my name is jack linke i've been a django developer since 2018 so not that long but really dove in head first i am a psf contributing member and i'm also the lead developer for a web op application for utilities districts that helps them manage their resources i got involved with htmx late last year really kind of at the beginning of its uh development and increasing popularity so i was very fortunate to be involved my talk today is entitled server side is dead along the server side plus hdmx and thank you again for joining me so i started web programming at the turn of the millennium back in the early days of web 2.0 javascript was still very young ajax which is the ability to asynchronously do things like form submissions or updating parts of the page without needing a full refresh it really wasn't even a thing yet css still felt really experimental if you'd even heard of it but interactivity and dynamic content were the new thing and in those days everything was done server-side often in perl or php we were creating really cool database backed web applications that felt powerful it was you know it was something really new a website wasn't just a static page of text and images it could now respond to your inquiries and return customized content sadly while i continued programming and other technical work life really took me away from the web programming aspect of things for the most part for about a decade and a half when i got back into developing for the web in 2018 the whole environment was completely different half the internet was running on javascript separate teams were working on the front end and back end there was complicated workflows and apis and it seemed like there was layer upon layer of frameworks to enable that same kind of dynamic interactive website so in some ways in 2018 i was really brand new to web development all over again but i remembered uh maybe with rose-colored glasses that web development was in many ways much more straightforward 20 years ago so it really brought to mind the question does modern web development have to be super complicated so what's the current state well django provides you with templates but how do you apply interactivity if you want to do partial page refreshes or submit a form without the entire page reloading what do you do and there's a variety of different approaches vanilla javascript you know you can throw some ajax inline in your page jquery allows you to do some really cool stuff but it's kind of outdated now single page applications gained a lot of popularity so you have div after div after div in your page you can use view directly which keeps things a little more lightweight uh you know you just import the view script and and you can do stuff pretty pretty straightforward and then there's more heavy things like react or angular but so many different directions and a lot of these are really heavy require you to learn a whole lot here's a few of the frameworks that have been developed over the past two decades and most of the tools in this image are focused at least in part on the front end you can see django in there you know at one point but most of these are front end tools and there's just a ton of them keep in mind that this image hasn't been updated for two years so just even in that time several more have come out and if you look at this roadmap of front-end development you'll see an incredible amount of things that a new person really needs to learn to get all of the effects all of the benefits of modern web development it's it's just a little crazy now what's amazing about this image is you can really ignore about half of the boxes in it when you apply hdmx and still get most of the same benefits so what's the standard approach in django for modern front end development how do we get the interactivity that we want well good question django was really created and initially came to popularity at a time when server side was really very much the norm you did all the development on the server side and you push that content to the front that's really how django templates work over the past decade there's been so many single page application approaches javascript front-end frameworks different tools and options that it really throws those who are new to django for a loop and it makes those uh who've been working with django for a little longer feel like they've got a bunch of new stuff to figure out there's really not a standard approach to the front end other than the built-in templating and many people feel that that approach is a little bit outdated so where's the middle ground well one potential approach is htmx the whole reason that we're here talking today hdmx is really just an extension to existing html so it's it's not something that requires you learning an entire new language uh or framework it's back-end agnostic so you can bring your own back-end it works well with django but it also works well with a variety of other back-ends fast api flask and and in other languages as well it's focused it only does a few things it's really you know all about the interactivity between the front end and the back end and allows you to access ajax css transitions websockets and servers and events all directly in your html you don't have to incorporate a bunch of additional javascript files or you know build out anything crazy you can do it all right in the html and the nice thing about htmx is that it's rather small once it's gzipped it's only about 11 kilobytes so how do we get from the traditional django template approach to a more modern approach with htmx while sidestepping all of those javascript frameworks and tools that we were talking about earlier well i'm going to take you through a few different examples the first one we're going to look at is in bunk inbox functionality so how do you mark something as red or archived or something like that and in this picture you'll see i have started with a basic bootstrap template just to make things look pretty real quick and you'll see we have two messages here the first message has been read its background is is kind of grayed out and the bottom message there is a new message and you'll see on the right hand side there's a button to archive it or mark it as read pretty straightforward this is a really common functionality that you'll need in a number of applications and if we look at the the views here on the left is kind of just the standard approach and on the right is the approach where we are making use of htmx and you'll notice really the only difference between these two views is that if we've marked a message as read instead of returning the entire template back to the user we're including just a fragment and in this case i have put the fragment in its own directory fragments under the messaging apps templates so we return that with a template response very simple so basically if if we get a get request we send the entire template back if we get a post request we only send that fragment and here's the differences between the the templates themselves on the top is the traditional approach and you'll see you know this is this is probably something that most of you have all seen before pretty straightforward just a form we've got our csrf token in there and a button that submits the form now the thing is that will refresh the entire page on the bottom very similar we've wrapped the whole thing in a div and i've i've kind of hidden the the form and some of the other content there but we wrapped the whole thing in a div and then you'll see instead of a button i've got a span there just to make things easy and there's a few different html parameters that are different than what you would normally see the hx post hs swap hx target and hx include now i've prepended those with data just to keep my ide from screaming because anything starting with data is is generally acceptable anything starting with something like hx is going to be called out even though it's going to work just fine so in this example when we click on the span that includes that little icon the little envelope icon what's happening here is htmx is posting to the messaging inbox htmx view it's going to swap the outer html which is that div and you can see the target we have a different div id for each message and then we are going to also include the contents of the hidden input there named item and the value of that hidden input is the message id so pretty straightforward when you hit the icon for archiving it'll post the message id so in this example we're using the same template fragment for the initial display of each message and for the content that is swapped in and in the main template itself we just have something that looks like this for each message we include the message fragment pretty straightforward the swapped content replaces the entire original content in this example so again when i hit that icon the outer html the entire div is replaced with a new div that has the updated message so here's a quick video just uh pretty straightforward nothing super crazy but you can see when we hit the icon the page doesn't have to refresh it just refreshes that small portion of the page so the next example that we'll look at is one click settings changes so in this example when i hit the check box i want that update to be made in the database without refreshing the whole page a template only based approach that's really not easily possible you're going to refresh the whole page in the initial case here you'll see that i'm using ajax to show you what uh you know a more realistic uh initial approach might be to enable that interaction between the front and the back end without page refreshes in the htm x example i've included a small amount of hyperscript which we'll talk about a little bit later to help with animation and here we are going to return html directly from the view instead of using a separate template fragment and then the last thing that's kind of different here is instead of loading the response to the div that encompasses the the content we're going to load that response to a different location a separate div so instead of replacing the entire outer html we're going to replace the contents of a particular div this is probably pretty straightforward if you've worked with ajax before but it might be a little bit intimidating if you're not really versed in javascript so in this example we have a standard form with the check box uh which would be duplicated uh in in real life with multiple check boxes and when the check box is checked or unchecked we pass the value of setting one or setting two or whichever one we've just checked to the user settings view for processing on the back end in the htmx version we can skip any of that special javascript we don't need any any ajax or anything like that and we can just add a few bits to the html for the checkbox itself here we're posting the value of a hidden input named settings to the user settings htmx view when we get a click event on the check box the html that we get back from the view will be put into the setting one response div down there at the bottom so what do the views look like in the traditional approach if the request is a post we just toggle the setting this is pretty straightforward here um you know we've received a post we get the settings value from that post from the request and then we either set or unset uh the boolean now in this example in the model on the user model i've set a model method toggle setting 1 and all that does is if it's a true it sets false and if it's a false it sets true and then saves to the database in the htm x version we really do the same thing but we're also going to return a chunk of html that displays a success alert and uses just a little bit of hyperscript to remove that alert after two seconds here you can see the end result we've got interactivity with those check boxes with just a few changes to our html and a few updates to the view itself to return some html this same method can really be used for any other type of instantly updating settings so if you have say a select box where the user can choose preferences for receiving emails or sms or something like that or if you have text inputs or any other inputs in a form you can use the same technique and expand it for that and the last example that we're going to look at here is a case where you want to display multiple independent forms on the same page now sometimes it's easiest to put those in individual tabs or or in some other way where most of the content is hidden away until you click on something and it changes to the content for for that thing so in this example i've got five different forms here but only one of them is visible to the user at any time each form is designed to submit separately from the others this is really a pattern that i use a lot in my own projects here's an example from one of my projects where i have three different forms available to the end user for specifying the water order requests at an irrigation company and that's not important here but just so you can see each form is is somewhat different but we kind of hide the other two forms behind tabs and it makes it easy for the irrigation company to see all of the order form options without it cluttering up the whole page you might use this sort of thing anywhere where you need lots of profile settings tenant configurations or variations on order forms like this one to demonstrate here i'm using just a really simple form duplicated in each tab all we're doing is looking at the username and email for the current user in reality you'd probably have a bunch of different forms and they might have you know dozens of different fields on each of them in the traditional approach to the template we load each form into each tab on the page so all of these forms are in the dom content for the page itself and when you click on one of those it just unhides the current tab and hides the the one that was visible before or as you can see here it literally is setting the active class on the active tag tab in the view we have to check to see which form was intended for processing by looking at the name of the submit button associated with that form some of the issues with this are you have to prefix each of your forms when you're putting them all on the same page in into the same template uh otherwise you're going to end up with forms that have the same id and that's really a no-no for html and will cause problems for multiple forms the views can get really long and complex because you have to display each form on the get request and process each form on the post request all in the same view it just gets really complicated one other potential issue is the amount of content that's loaded to a view like this if you have select boxes that have a bunch of options in each of the forms the page may take a long time to load because you're loading up the options for each of those select boxes at the load of that view so maybe some some things that you want to avoid so i've just kind of highlighted here the points that i made before about having to prefix each form so that it's uniquely identifiable in the browser it doesn't look so bad here with only two tabs shown but you can imagine it it really gets quickly overwhelming as the content that you're pushing into that view increases it definitely gets gets long so how would we approach this with htmx well with htmx we can split things up a bit in this case we're going to use separate templates and views for each tab and that might seem like a lot more work but i will tell you it's incredibly easier to troubleshoot and to read through and understand which bits of code do what when things are split out a little bit we use a single div for the content of all the tabs and we only load the content for the tab that is currently selected when the page initially loads up we will insert the contents for that first tab and then when any other tab is selected we load up the contents for that tab here's the update with htmx for the template itself and if you look on the left we have the base template for the view and one of the tab fragments is on the right so what's on the right there is what will be loaded into the div at the very bottom when any tab is selected each tab has some htmx attributes that do a get request for the contents when that tab is clicked and those contents like i said get loaded into the div at the bottom at the top there you'll see that we have another div and what we're doing there is if you look at the hx trigger attributes of that div it says load after 100 milliseconds so we are loading the contents of form one into the tab content div after the page has been loaded for 100 milliseconds at the end of the day the important thing is that each form inside the div in in the fragment there on the right performs a post of that form to the view associated with the tab so there's no more need for prefixing the form itself and if we look at the views themselves this top one tabs hdmx view loads up the main content really all it's doing is loading up a template uh that base template we looked at before there's almost nothing to it and then for each tab that we want we have a view that displays the form when we do a get request and processes it individually when we do a post request here's a video real quick just showing what it looks like it's a very simple example here but you could expand it considerably and it can definitely be beneficial keep in mind that the three examples that i've gone through here really only scratch the surface of what can be quickly implemented with hdmx without the need for extra you know heavy frameworks and learning new programming languages so having looked at a few examples of actually using htmx let's close out with some tips some best practices and resources that will help you move on with htmx and get involved with the community so cross-site forgery request forgeries csrf uh it's an attack that forces an end user to execute unwanted actions on a web application in which they're currently authenticated basically uh it it can compose a problem when you're doing posts posting a request putting a request submitting forms things like that uh it's a a potential issue and django has some built-in support to help you avoid csr f attacks it provides a token from the back end that you can then put in the template and it compares the token that it provided with the one that is submitted when you post or put or or delete from the front end so how do we include csrf tokens with our requests when htmx isn't always wrapped in a form we might be posting things when you click a button or something like that that doesn't have a form associated with it well there's two ways we can do that we can either include the hx headers which will apply that csrf token header in the post itself or you can just add this little snippet to the base template for your entire site and it will add that header on every request and just simplify things considerably you will no longer have to think about making sure that you have the csrf token in each of your requests one thing that you'll notice with htmx and i kind of hit on it before especially in the tab example above was that you may end up with more more views and this is not necessarily a negative thing being able to split up the functionality into multiple views that do just small things each can really help clarify what's going on in your application so don't be afraid of making more views at the end of the day it it will help i assure you now as i mentioned at the very beginning htmx is very focused its intent is not to do everything that vue or angular or react can do it's its focus is really on interactivity and that's that's the majority of it so if you find yourself trying to do things like uh transitions and animations and things that are a bit beyond the scope of htmlx itself there are a couple of recommended complementary javascript libraries that can help out so first is hyperscript it was designed by the creator of htmx to be complementary to htmx it's it's got its own website with some really good examples but keep in mind that its own designer will tell you that it is a pretty speculative library and subject to changes another option is alpine js which is very lightweight and focused it only has a few different features but just like with htmx you can get an incredible amount out of those few features so both of those are worthwhile to check out both of them are lightweight in the sense of they aren't designed to do everything and they aren't huge code wise so your pages won't be drug down in load time another thing to check out is django htm x developed by adam johnson among other things it provides a debug handler when the debug in your project is set to true it will help you with debugging things it has a method for easily determining whether a request was made from htmx or if it's just a standard full-page request and then it has a bunch of other useful utilities that you'll probably find helpful as you're developing with django and htmx conveniently adam also includes a nice example app that demonstrates the various tools available in his package and last a few additional resources to check out so htmx.org is the source for references for documentation for examples and for finding other resources awesome htmx is a github repository that lists out different blog posts videos and examples for htmx there is the htmx discord which has a fantastic community the designer of htmx is uh is on there on a regular basis along with other people interested in htmx and there's even a django and hdmx discord board there the htmx subreddit is worth checking out and then i've also got the notes and code for this presentation and the examples that i presented here available on github anyway that's it i appreciate you coming to my talk and hopefully it was helpful in showing what sort of things you can do with htmx with with relatively little effort and without having to learn an entirely new language like javascript or or get into the guts of it i appreciate you coming and i hope you enjoy the rest of the conference thank you goodbye [Music] [Music] [Music] you
Info
Channel: DjangoCon US
Views: 1,658
Rating: undefined out of 5
Keywords:
Id: t98bKdeUHsU
Channel Id: undefined
Length: 31min 57sec (1917 seconds)
Published: Fri Oct 22 2021
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.