Episode notes
For years, "Django and async" came with an asterisk. The docs themselves warned you off it. Scary performance notes, a story that felt half-finished. Well, that story just got rewritten, literally, and the person who rewrote it is here to tell you why the old framing was wrong. Carlton Gibson is a former Django Fellow, sat on the security team for eight years, and he's on the steering council. On this episode we get into the async topic doc rewrite, what actually remains versus what was just fear, the new Tasks framework in 6.0, DB-level cascades and fetch modes landing in 6.1, and why…
Transcript
Read the transcript · about 12,690 words, follows along as you listen
Michael Kennedy:For years, Django and Async came with an asterisk. The docs themselves warned you off it. Scary performance notes. A story that felt half-finished. Well, that story just got rewritten, literally. And the person who rewrote it is here to tell you why that old framing was wrong. Carlton Gibson is a former Django fellow, sat on the security team for eight years, and he's on the steering council. On this episode, we get into the Async topic doc rewrite.
Michael Kennedy:what actually remains versus what was just fear and the new tasks framework in 6.0, DB-level cascades and fetch models landing in 6.1, and why free threading is the bet it's about to pay off big for Django. If you've been told that Django's async story isn't ready, this episode puts that myth to bed. This is Talk Python To Me, episode 556, recorded July 2nd, 2026. Welcome to Talk Python To Me, the number one Python podcast for developers and data scientists.
Michael Kennedy:This is your host, Michael Kennedy. I'm a PSF fellow who's been coding for over 25 years. Let's connect on social media. You'll find me and Talk Python on Mastodon, Bluesky, and X. The social links are all in your show notes. You can find over 10 years of past episodes at talkpython.fm. And if you want to be part of the show, you can join our recording live streams. That's right. We live stream the raw uncut version of each episode on YouTube. Just visit talkpython.fm/youtube to see the schedule of upcoming events.
Michael Kennedy:Be sure to subscribe there and press the bell so you'll get notified anytime we're recording. This episode is brought to you by Sentry. Don't let those errors go unnoticed. Use Sentry like we do here at Talk Python. Sign up at Talk Python.fm slash Sentry. Carlton, welcome back to Talk Python To Me. Amazing to have you here. Thank you, Michael. Thank you for having me on again. Always fun to talk with you. Fun to have you back. We're going to talk about one of my favorite topics, async, both for the reasons it's amazing and the reasons it's like, why? Why is it this way?
Carlton Gibson:Why do we do this to ourselves is the thing, right?
Michael Kennedy:Exactly. Wait, I want to say, oh, but I didn't want it like that. No, just kidding. Specifically with regard to Django, you did some really interesting updates with Django that we're going to talk about. But first, your teams, they're still in the World Cup. How are we doing?
Carlton Gibson:Oh, yeah. Well, so I'm British by birth, so English by birth. So I was supposed to support England, but I live in Spain. So depending on who's winning, who's doing better, I get to flip my allegiance.
Michael Kennedy:you know i think that's really that's really amazing because you if one of your team's not doing well you can just like i'm gonna just cheer for the other one it's it's great you get like two
Carlton Gibson:shots at the thing yeah i mean in the last uh european championships we had the england spain final so i couldn't lose really yeah that's amazing yeah so the u.s team um advanced yesterday as well
Michael Kennedy:they played really well so i'm very very excited for that yeah it's lovely to see new new nation emerging nations do well in the World Cup. You know, a long time ago, that would have been like some kind of joke. People are like, ah, surely you're joking. Surely you're joking about this. But honestly, soccer or football, non-American football, is popular in America. So super cool. Glad to hear it. And you're back. So tell people just what have you been up to?
Michael Kennedy:You know, not everyone listens every episode. So a quick introduction for yourself, maybe.
Carlton Gibson:Okay. So my name is Carlton. I've long time worked with Django. I'm a former Django fellow, did that for five years. I'm on the Django steering council. I was on the security team for eight years. I maintain a whole load of packages in the ecosystem. So, you know, I'm quite vested there. And, yes, you know, basically I use Django and have done for, I don't know, however many years to build web applications to pay the bills. Had a busy spring. I was everywhere I went to.
Carlton Gibson:There was a Pi TV event organized by JetBrains in Amsterdam in March that I went to. That was all on YouTube. There was, I don't know, 11 hours of live streaming or something. It was amazing. Then I was in DjangoCon Europe in Athens in, I think, May. No, April. And then in May, I was at Paikon Italia, which is in Bologna. Paikon Italia really is a lovely conference. You should make your way there. And now I'm just home and I'm exhausted. I had a quick holiday with the family, but now I'm hiding at home until September, where we've got Django on the Med, which is a three-day sprint event, which is going to be in Pescara, Italy, which we're looking forward to.
Michael Kennedy:That sounds really, really nice. I love traveling, but the jet lag kind of blows me out eventually. I'm like, ah, this is 11 hours jet lag. I don't really want to do this anymore. It sounds to me like you're kind of able to keep it in the broader Euro neighborhood, which is nice.
Carlton Gibson:Yes, I was. I was, which it does help because there isn't that massive time change. But it's still hard work, right? Even though you have fun at these events, even though you're seeing your friends, even though it's, you know, doing what you're vested in. It's their long days and you have to be full on, you know, in action all day, each day. And so by the time you get home, you are, you know, kind of exhausted. And then obviously you've been away and you get home and, you know, you need to be present for your family too.
Carlton Gibson:So there's a limit to how many of these I can do.
Michael Kennedy:So I won't do any other events this year because it's just too much. Yeah, that's good. Just too much.
Carlton Gibson:Yeah.
Michael Kennedy:I remember traveling when we had little kids and that was a whole nother level because you'd come back. It's like, you've been gone for a week, so I need some help. But I'm exhausted. You don't understand. But at the same time, it's a fair request, you know?
Carlton Gibson:Yeah, no, absolutely. Absolutely. I mean, our kids are older now. The eldest is 18, or will be 18 next week, just about to go to university, and then 16, and 13, 14. So they are a lot easier than they used to be. But still, it's a big ask on my partner to go away and they're alone for the whole week. Absolutely. In that point position, we might call it.
Michael Kennedy:Yes, exactly. so uh tell people you mentioned django on the med yes i talked to paulo about this a couple episodes ago but yeah tell me okay you're going to be part of this too yeah yeah yeah so paulo and i
Carlton Gibson:this was paulo's idea several years ago to have core developer sprints for django um because at the the end of jank on europe or the end of jank on yes we always have a couple of days of sprints and they're some of the best parts of the conference um but also it's around the time people are leaving and your people are already kind of exhausted you know having the three days of talks plus then of the sprints so it's like we wanted more and um we decided to to do this event and we were like yeah this is a good idea but it didn't happen and then i think dublin a year a year and a half ago now uh we were like no come on let's like it so we said we're going to have it in palo vijay which is my hometown um we did that last september and all last october sorry beginning of october and we're doing it in paulo's hometown pescara this september and it's as i say It's three days to get together and work on Django.
Carlton Gibson:And we had some really big features landed. Like, for instance, Django 6.1 is in pre-release now. And it's adding an ability to have DB-level cascade options for the on-delete. So on-delete is, well, you've got a foreign key, so I've got a user, and that user has a bookmark. Well, what happens when I delete the user? What happens to the bookmark? It's got a parent relationship. And so normally you would cascade that. Now, Django's always offered this option, but historically, it's done that in memory.
Carlton Gibson:In Python, it's pulled, it's walked the tree, and it's got the objects, and then it's deleted the leaves, and then the stems, and only finally down to the branches. And now, that can be very costly at scale.
Michael Kennedy:I'm going to delete this one record that references several tables with a million entries. That could be a lot of money.
Carlton Gibson:Exactly. You've got an organization that's got team members and projects, and you delete the organization. it just brings down your application basically you get out of memory memory issues so the database still has to do that work but the database is much much much better at doing that work than python is um and so that's so anyway we've got this new option this ticket had been open for i don't know so many years because it's it was really hard and we had marish feliciak who's a former django fellow and one of the core um orm contributors simon charette is one of the core open source contributors Lily Foote, Jacob Tyler-Wells, who's the new Django fellow. We had the four of them just there working together and they were able to get this over the line. And it's literally something which would never have happened except for the time that was available at Django on the Met. So we've got exciting plans for this time. We're hoping to get people again, people from around the community to come. And I know, I'm really excited about it. The first one was a proof of concept. It went really well. The second one's lining up to be amazing too. And once we've done two, well, it's kind of
Michael Kennedy:established and you know we're yeah well it's tradition you gotta do it yeah yeah exactly you gotta go hang out with the mediterranean so i've done i've done a lot of remote work in my life and i find you know when we do in-person meetups get the people who are all distributed together it just changes the energy you know there's something about the bandwidth of face-to-face
Carlton Gibson:communication which just isn't rec replicable record you which you can't replicate replica online yeah thank you mike thank you my but yeah it's it's i don't know i mean look it works online but as well we had another it was a good session as well so with um django we've got this um we've had recently this new features board which was an attempt to take people suggesting features away from django's track instance which is kind of old and scary and is a place for for the work to be done and put it into a GitHub project and where we could have a project board and we could have upvotes and we could have a Kanban board to see what were being advanced to try and give a bit more visibility into the process. And sometimes there's disagreements and those disagreements online, they can go on forever and ever, but we were able to have a session and there were different voices from different opinions. And we were able to come to agreements in five minutes on topics which had been rolling on the boards for months. And that kind of, look, I can see why you're saying this. It's really hard to get that online. You know, there's money emojis
Michael Kennedy:we use as much as we try and communicate openly it's just as much slack as you want to throw out there and you know i mean since 2020 it's it's kind of been just oh yeah obviously remote is better and so on and there are mega advantages don't get me wrong but it's not always better and in lots of ways so yeah so i guess for this good gone you you mentioned 2020 and it's covid it's one thing that
Carlton Gibson:um i was um django fellow over over that period and um you know it was a really hard time for because i think that the pandemic really knocked the back out of the community not we had we had older people stepping away we had young roots that were starting to come and then the put the the pandemic came and it was kind of like this really really really tough period and it's now five six years later that we're looking at it we're thinking actually now the community you know the activity is going on with things like jang and on space and the new community the new members that are coming through and the people who who are active in the community think well next year when the steering council is re-elected. There's obvious candidates who weren't there two years ago.
Carlton Gibson:And it's taken us, I think, half a decade to recover from the real knock that was COVID.
Michael Kennedy:Wow. I believe it. I believe it. So is this for just for core devs or is this open to people who just want to contribute? No, it's open to everybody. Obviously, if you're an established
Carlton Gibson:contributor, it's going to be easy to get going. But it's also about bringing on new and teaming people up. And, you know, if you come and you've got a particular interest in Django, if you're a total Django novice, it would be strange to come to choose Django on the Met as your first event. But if you're into Django and you know it and you want to get contributing, it's, yeah, that's part of the plan too, is that we have both experienced and new contributors and we can team people up and get people working together.
Carlton Gibson:And, you know, part of the contributing to Django problem is the learning curve. So it feels like it's a big, scary thing. Whereas if you sit down with somebody in a room and you work on what they're working on, you're like, actually, I could work on this side ticket. And all of a sudden people are off.
Michael Kennedy:Well, it suffers from what many of the successful projects out there do. It's super polished. It's used by millions and millions of projects. It's hard to just look at it and go, oh, I'll just change this without regard to all that knock on effect, right?
Carlton Gibson:Yes. And that's where part of the new features repo was about giving a space where people could put their ideas forward without having them immediately closed as won't fix. Because if you went and, you know, oh, can we integrate React? No, we're not going to do that. You can use React and here's how we use React, but we're not going to integrate it into JankRusate as an example. And that would be open, it'd be no, no, close, won't fix. And people felt that that was a little bit too...
Carlton Gibson:A little too stack over flowy. Well, yeah, it wasn't ideal. So the new features repo is to allow space to develop for a conversation. And then those ideas which have a bit of traction, we can say, no, do you know what? A lot of people have said they support this one or we can advance it.
Michael Kennedy:Hey, one second. Normally, this would be an ad break from Sentry, but not this time. Let's just thank them for supporting the show and get right back to the conversation. Also, visit talkpython.fm/sentry after the show. Thanks, Sentry. You have another project coming along, The Mantle. Tell us what this is.
Carlton Gibson:Django Mantle. So it's my take on a modern serialization story for Django. So the big topic we've had is about REST Framework, and REST Framework is aging. And REST Framework is wonderful, and it has been wonderful. But the serializers in particular, they're kind of last generation. And there are much more modern approaches available now, involved in Pydantic, in msgspec, in Attrs and Catters, which is what I use, are much, much faster than they used to be.
Carlton Gibson:They generate code which is almost as quick as you would see if you hand-wrote it. If you wrote the code to literally pull this attribute, this attribute, this attribute, the code that's generated for you by, say, caters is as quick as that code, which is amazing. Whereas REST Framework serializes, they go through and get the field object from the model. They get the value from it. It's like, hang on, all of those loopings are very slow by comparison.
Carlton Gibson:So then the question is, well, why don't we just use Pydantic? Well, Pydantic's fantastic, but it's not ORM aware. It doesn't have any insight into how Django works or anything. So Django Mantle is my take on that. It's the type-save wrapper around Django's liquid core. So you write these atters classes, and then you just instantiate a query object, and you go fetch, and it fully instantiates your object to the shape you define, and it fetches all the data all in one go, and it can do that for nested objects, and you can do writes with validation, all these things.
Carlton Gibson:And it's ORM aware in that it only selects the fields that it needs, and it does the pre-fetch relateds for you so that you don't get this N plus one query problem, right? And it's very good for performant fetches of just the exact data you want. You end up with your objects being fully Python typed. They're at its classes, so they're typed. Your type checker knows the way around them. mypy or PyRefly is now adding support for Atis classes too, I see this week.
Carlton Gibson:Oh, cool. So anyway, it's an attempt to show what a serialization story using these modern approaches can look like. And then from there, it's like, well, okay, what does an API framework in 2026 look?
Michael Kennedy:I love it. I love this idea. I think there's a lot of value in taking some of these very focused, lightweight, dedicated like data structures right like c attrs or pydantic or just straight data classes and somehow integrating them in here without just this heavyweight stuff like you talked about the eager loading that's and some of the other things like the typing can be weird as well like sql alchemy you kind of have to lie to it yes somehow do you either lie about it being a database thing or do you lie about it being an integer when it actually gets the value right like yeah yeah yeah
Carlton Gibson:Yeah, because the actual type is a Django deferred field, right? For a Django modifier, it's a deferred field. What on earth is a deferred field? Where it's an object that has the descriptive protocol so that when you access it, it gives you the converted value. I don't want to type that.
Michael Kennedy:Exactly. Even if you do, then you try to add it to an integer. It's like, you can't add that to an integer. That's not the same thing. You're like, but it's going to be.
Carlton Gibson:Yeah, it's going to be. So this was the topic of my talk that I gave in Amsterdam and Django in Europe and PyCon in Thailand. It's slightly different versions because I had more time at DjangoCon Europe. So I went more into the way we grow from, say, an active record pattern, which is like a Django model, right? It's an active record. It's your database row, but it's also an object that's got logical behaviors to a more separated approach where you're like, hang on, I don't want my display logic and my aggregation logic and my user validation logic all living on this one database class.
Carlton Gibson:So how do we separate those off? That's kind of where mantle came from originally. But the idea was that, and my take is that Django's ORM is built on these very powerful dynamic patterns that Python allows. And retrofitting static typing onto that is going to be a real problem. So instead of that, that's also a dynamic C. On top of that, we have these static islands where we can have all the nice type safety features of modern Python, but we're not trying to eliminate the very powerful dynamic features that we have underneath.
Carlton Gibson:And so the mantles, the shape classes that you define, they're your static islands. And there you can add all your domain logic that you want to, and you can have it fully separated from the database. And they are just pure Python classes. There's no data mutability in there. There's no like, say, oh, I modified a property and saved, and now I've updated something. No, there's none of that active record stuff going on. So it's a kind of way of getting some of the benefits of this sort of separation layers
Michael Kennedy:type approach whilst still keeping everything you love from the aura uh spoken like someone who appreciates some nice architecture and layers are very cool well the issue is as your application
Carlton Gibson:grows the complexity grows with it and you need more structure to manage that complexity like you simply do like it the issue isn't that you started with a Django model it's that your Django model grew and then grew and it grew and all of a sudden it's got it's got methods on it which are several distinct responsibilities. And then you think, oh, I'm getting a lot of code here. So you start doing dry, you start abstracting methods. But that abstracted method wasn't for a single responsibility. So it's not clean so that you've got, ah. And everybody who's grown a Django app has seen this. And it's perfectly natural and it's perfectly normal. It's just how applications grow.
Carlton Gibson:And Mantle is kind of my take on, well, how do we deal with that? How do we grow from the active record pattern that we began to, to something that's more robust. And it's not that you should start with the more robust patterns because you're over-engineering them. There's a nice road we have to walk between these two problems. And that's the joy of crafting the application over time,
Michael Kennedy:right? That's why we're programmed. I love it. I love it. All right. Let's talk about Django 6.1. Yes. I think it's coming out. It's not quite finished, but there's a lot of features we're going to talk about that are pretty exciting and related here, right? A lot of new things coming out of the database, for example.
Carlton Gibson:Yes. So I think it's in beta now. So it's going to be a release candidate in a couple of weeks, and then we're about a month away from the final release. Oh, by the way, I see you've got the page up there. The Django Developer Survey is on right now. Do take it, folks. We want as many replies as we can. It really does help drive forward the development of Django. So do give that five minutes there of your time to answer the questions. But what's exciting?
Carlton Gibson:Well, we already talked about database-level cascades, right? That's my big feature because that's something that you just couldn't work around. And there's no in Python solution to that. We wanted that. You'd have to, well, in the past, I have created a custom database backend and changed the way it creates. No, that's not a sustainable way. So database-level cascades are my favorite one. The one that I think more people are excited about is called fetch modes, which are on query sets.
Carlton Gibson:So we talked about the prefetch related with the way Mantle handles it. But the idea is you've got an author and so you fetch a user and they've got a list of bookmarks. And so you get the author, you get the user, and then you iterate for, bookmark in users.bookmark, do display the bookmark. And so what happens is it goes through and you get this N plus one query where it goes and fetches the lazy related object. And that's great at small scales and when you're getting going, but it's a performance nightmare, basically.
Carlton Gibson:And this N plus one problem that comes up is something that people hit all and all again. So fetch modes let you say, look, fetch peers, which is the exciting one. It lets you say, if I access the first element in a list of related objects, go and get them all at once. And so it's like a deferred pre-fetch related. And that's going to be a lot easier to manage in a lot of cases than having to manually add the pre-fetch related in each case, because those often become difficult to do by hand.
Carlton Gibson:They're all right to add the first time, but they become difficult to keep updated. And then you're suddenly pre-fetch relating something which you're no longer using. And so fetch mode.
Michael Kennedy:Yeah, your data access layer, maybe you're right, says get me all the books. But then you might have to add like some kind of flag that says and the authors. Because sometimes you want to call that function and you want the authors, but sometimes you want to just list the books, you know, and you don't need that. And it's like, yeah, so this way kind of just lets you says, if you're ever going to do this lazy loading, then basically upgrade it to an eager load.
Carlton Gibson:Yes. And there's, I don't think the videos are quite out yet, but Jacob Tyler was, you found a great talk at DjangoCon Europe on the, on how fetch modes work. They'll, they'll be out very soon. I think they'll be on YouTube, but do look out for them in the interest, but how, how, how fetchmates work and what the limitations were and you know where it's not you know it's not a magic solution it's not just oh let's enable fetch peers in all cases you know without thinking about it no but it it's a good change and um when i've spoken to people about what they're excited about in 6.1 most people have pointed to this as their headline feature nice nice so that's good and then i guess um a little bit yeah go ahead well i was going to say about the other thing that i'm excited about that you know there's an old list of features the thing with django releases every there's this big long release pack go and read it go and pick your favorite features but there's always lots in there for everything but you we can now customize the multi-part parser class for on the request object now whoever wants to do that well it turns out but that you can when you're
Carlton Gibson:getting multi-part requests if you're getting big ones with lots of multi-parts in swapping out a different multi-parts class could save you maybe 30 on your passing time which is 30 cpu on pass it on request for a passing time, that may be a non-negagable game. So I'm excited about that. But I'm excited because it starts to open the pathway to more customizations on the request. And so, you know, Django's got this implementation, but can we swap out that implementation and compare it and see if we can get some performance gains by being able to turn some of these nods under the hood.
Michael Kennedy:That's really nice. And having it be customizable is really great. I'm working on this. I'm working with this project that I just want to use. I don't want to be an author of it, but it has no real extensibility. So anything I want to do, I have to write little custom bits and change the source code and run it. And I'm like, as soon as there's a new version, how am I going to pay for this? You know what I mean? And so this is really nice.
Carlton Gibson:Yeah. Again, this is customizing the multi-part pass class. I don't think that's for the majority of people. But when you need it, it's going to be there. And it's like, okay, actually, there's a big win. So those are my favorites.
Michael Kennedy:Yeah. Okay. What's the timeline? It's in beta, you say?
Carlton Gibson:It's in beta now. So the pre-release is three months. So the alpha was a month ago. The beta is just now. And then the release candidate will be in a week or so. And then a couple of weeks after that will be the final. So I guess August will be. So it's coming fast. Oh, yes, yes, yes. It's very nearly there. Excellent. So just a call to action. If you're using Django and you could just install it against your application and run the beta, run your test suite against the beta.
Carlton Gibson:That would be amazing because if it passes, then you're all good. You're good to update. If it doesn't pass, then we want to know that. We want to know, well, what changed?
Michael Kennedy:It's got to be such a challenge to work on a project that's used, not just consumed by people, but as a programmer, code integrated with this project, right?
Carlton Gibson:Yeah, yeah, yeah. And there's the whole ecosystem, right? So, I mean, why do people use Django? One of the big reasons they use Django is for the third-party packages that are available, CMSs or image processing packages or whatever it is that you want to do. Did we break any integrations with them? Ah, well, we hope not. But unless people test and tell us, we don't find out. And when I was a fellow for five years and in every release, we would have on release day bug reports saying, oh, there's some regression here when we could have had those a week before and fix them before the final release.
Michael Kennedy:Yeah. Have you looked lately what the... I'll just do it like this. Have you looked at what it says used by? On GitHub here? You know, it says, does it say how many projects? I don't know. Oh yeah, here we go. This is just the public projects on GitHub, but two million? Couple of million. Yeah, right. Okay, good. There's so many that are private. There's so many that have nothing to do with GitHub. It's like a very small sample.
Carlton Gibson:That's still crazy. Jay, a couple of years ago at DjangoCon US, I think maybe 2024, Jacob Kaplan Moss gave a sort of best estimate about the user base, about 4 million, something like that as a kind of you know four million in action django projects in in the wild
Michael Kennedy:so okay you know if you count all the internal apps given that two million public repos on gmail if you count all the internal private things that people just threw up for like a little internal company app i bet it's way more than four million now i obviously couldn't prove it but yeah i mean
Carlton Gibson:i'd have to ask jacob how he came up with the figures but it was in terms of downloads and
Michael Kennedy:looking at this and looking yeah yeah exactly yeah probably the big query data pipe yeah or Yeah. Honestly, I feel like that stuff's kind of broken these days. Like 10 years ago, that was pretty representative. But right now, I think it's kind of a little weird on both ends. I think it's weird because there's so many Docker builds, right? This project can say, well, it got a hundred downloads. Well, that's because we just built something in CI a bunch of times today. We didn't really intend to download it, that many projects. But also at the same time, there's a bunch of caching layers. Like you might grab a Docker image that has it or build a Docker image and never reload that or use uv caching like it's just so opaque i think i mean a lot of people
Carlton Gibson:run little local pi pi pi cache or pip caches sorry so when you do pip install you're not you fetched it once you but you might have installed it a hundred times from that so yeah exactly what's
Michael Kennedy:that meant to be counted as one or i i think it's why it's so hard i don't have no idea so anyway um incredible and this obviously is right i was gonna say once upon a time there was a an idea
Carlton Gibson:to add some kind of telemetry into Django. And obviously that didn't go anywhere because no one wants to go anywhere near that. But we still sometimes would like some idea about how we estimate because the sort of visible Django community is like a thousandth of a percent. So say Jacob's 4 million users isn't too far off. The sort of visible community, the people who subscribe to the newsletter or do the survey or come to Django cons or all these things, they're about a thousandth of that, like 4,000 or 5,000 people that we can sort of point to and go, I know who you are.
Carlton Gibson:Yes, I've heard of you. Yes, I know you're on LinkedIn. But that's a fraction of the total user base. It would be lovely if we had some way
Michael Kennedy:of just reaching more. I know. I have a new term for you, Carlton. Dark matter Django.
Carlton Gibson:Yeah, brilliant. I'm having that. Let me write that down.
Michael Kennedy:Dark matter Django. Well, we're talking about stuff that is not dark matter. So you recently did a bunch of work on the documentation and positioning of async in general for django yeah yes yeah so the topic
Carlton Gibson:guide which is here that you've got up on the page the asynchronous support topic guide it was first written when we very first added um async support to django back in like that Django 3. something or i can't remember exactly but i think it was um python 3.6 it was was when it is and um async's come an awful long way since then and it was very negative it was like oh we still haven't finished this it's still in development it's still not ready and the performance implications are terrible
Michael Kennedy:unless you do it 100 perfectly but you and there was regular back in um go back in um python three five three six days it async and await and this async concept really had kind of a two to three issue like i would even if i wanted to do it i got to call this library which is talking to the internet or into the database but it's not async so what's the point yes yes and the costs of so
Carlton Gibson:the the big thing we'll come and talk about a lot is threats so in um django uh we use a lot of what of a helper um from the asgirf library called sync to async where we um you take async function and you you wrap it into a call routine so that you can wait into a coroutine so you can await that and it gets run in a thread and async io has the two thread thing which is the same um but essentially the same option um sync to async has some ability to track which thread it was called from so for instance database connections they're tied to a thread um and the transaction state is all tied to that thread so it's important that database um queries are run on the same thread as the connection came from. Otherwise, you're going to have problems. Sync2AdsAsync adds a few niceties around that, but it's essentially the same as AsyncIO2 thread. Go and run this in an executor on a separate thread. That's great, but that used to cost orders of milliseconds to bootstrap and set up. With latest pythons, it's tens of nanoseconds, or tens of microseconds, sorry.
Carlton Gibson:Tens of microseconds when you're doing milliseconds requests, they're not a significant thing, But the documentation was like, no, this is going to slow down your requests. And it's like, hang on, it's really not. And the API is complete. The ORM, the cache framework, authentication, session, signals, it's all got async API.
Michael Kennedy:So from a user perspective, it really is all there.
Carlton Gibson:It doesn't mean there's no work to be done. It's an ongoing project. We keep developing it. We keep fixing new things. We keep adding new things. But this idea that the topic guy presented that somehow the story wasn't finished, well, that's not quite, that wasn't quite right. So we wanted to update that. And we wanted to take some of the warnings about performance and just downgrade them to notes. You know, they're a bit overplayed in this latter day.
Michael Kennedy:I agree. I think the sync to async and back and forth is pretty interesting. And more broadly, you know, one of the things people use as a, I don't really want to use async. It's kind of bad. they'll call it like a virus or something and a lot of times what they mean is like well you've got some low level function it's async so in order to call that the thing above it has to be async which means like the rest of your app like it just cascades you know it's sort of viral in the gpl sense right um but yes that's a you don't have to live with that you can yeah go ahead sorry well
Carlton Gibson:they call it function coloring problem right is that once you've got a blue function or red function all the functions are called it have to be the same color yes but but you there's nothing
Michael Kennedy:to stop you from going in a synchronous function just async to sync boom and like kind of just stop the propagation there or create your own async io event loop and just run that one bit down below and so you could have a synchronous function but it maybe calls five external endpoints and you could do all that with async in parallel and just like run that but cap it right there i think there's a lot more creativity that we can bring just just just say like oh it's virus either it's amazing or we don't want it at all, you know?
Michael Kennedy:Yes.
Carlton Gibson:No, that example, that example you gave of calling five, you know, five external things concurrently, that's one of the easiest ways into AsyncVagenda. So you've got your WSGI app, it's deployed, it's got its, you've run Gunicorn, it's got, you know, four workers running, saying handling requests, each one in a single thread, nice and separated, so they're not getting in each other's ways, sorry, in a separate process, each kind of single threaded, doing its thing.
Carlton Gibson:And then you're like, I want to make some, API requests. So you can define a single async view and Django's handlers will run that in an event loop for you and you can run, say, your five HTTP requests and you can aggregate them together and you can return a single response. And that can just be done in a fraction of the time of calling one and then the other.
Michael Kennedy:Yeah, yeah, yeah. And it's just so clearly a win, right? Do you have to switch to an ASGI, an ASGI server mechanism if you're going to use async views in Django?
Carlton Gibson:No, you can run async views under WSGI. But what you don't get, this is a good question. So say I'm deployed, say I'm a Django developer, when should I switch to ASCII? When should I switch to async? And the real question is if you want long-lived requests. If you want to do, say, something where you hold open a connection and you, say, do service center events where every five seconds you get an update. Like a stock ticker is a good example, right?
Carlton Gibson:You get what was the latest stock price. Okay, it keeps coming down the wire at you. Well, you don't want to do that on the WSGI model because each connection is a worker on WSGI. And so you say you've got four workers. Well, that's great. But then, well, hang on. I've got three of those held open by clients. well, now I've only got one serving requests. Well, okay, double your workers. But then you're going to double your users. And if you're using pre-forked workers where each worker lives in a separate process, that's a lot of times that your Django application is loaded into RAM and say the cache is primed or the database connections are set up.
Carlton Gibson:There's a lot of overhead to running multiple processes. Whereas if you can do it with a NASGI worker, you can hold open that connection and it can just be served on the event loop. You can have many connections just for one worker.
Michael Kennedy:It's basically tied to an event loop and then that can share that thread or that worker as it interlaces across that one event loop, right? Yeah, exactly.
Carlton Gibson:And that's where the exciting things come. If you've got long-lived connections, even if you're just doing polling, you can do polling quite quickly, once a second, and you're not really going to overload your whiskey workers. But if you're holding a connection open, Ah, at that point, Async and ASCII is really called for. Yeah, that's cool. So you can kind of have this progressive scale. Yeah, yeah. I mean, standardly, the people that, I mean, we have an awful lot of people doing very exciting things, you know, with Async.
Carlton Gibson:They're either running small projects where a single ASCII worker is enough and it can handle enough connections and you don't actually need multiple processes. Or they tend to be running at the moment a WSGI base for their app, so a standard WSGI base, which is handling most of the work. And then the async endpoints are just running in a single ASCII process as a sort of sidecar. And they do this because something we'll get into is you get what's called you get kind of contention for CPU-bound work on the event.
Carlton Gibson:And we can talk about that in a bit. But I think that's the way people are deploying most successfully
Michael Kennedy:at the slightly larger applications. Yeah, that makes sense. And this contention, it is very interesting. It certainly is. I want it actually, I searched for the wrong thing. Hold on. That is, I wanted to actually show. I recently went through this whole process of like, how could I make my server use less memory? brought and i had some of my web apps were running purely synchronous as whiskey and some of them i had upgraded to like true async running on asgi on granian right and i'm just i was looking the server i'm like it's using i don't know nine gigs of ram for all these problems like 27 containers running but still it's a lot i'm like is there a way that i could just maybe reduce the workers a little bit and make it chill.
Michael Kennedy:And so I wrote this article about like going through all these different things. But one of the things that I found really helpful was if I could switch to more of the processes, more of the requests being processed by an ASGI server with like truly async calls and down to the database layer and so on, maybe I can use fewer workers. And so I like, just off of like one of my web apps, I cut like 500 megs off because I could just reduce the number of workers because each one was more capable and didn't get bound up.
Michael Kennedy:There's still this computational problem you have, but at least you're not doing like I'm waiting a second for this API endpoint, you know? Yes, yes, yes. I thought that was pretty interesting.
Carlton Gibson:No, it is. And it's like people, it's one reason why people run. So I always run, not always, but I default to running, say, Gun & Corn with multiple workers, multiple processes as workers because it's separate and you don't get the guild contention issues. But there is a great approach, depending on how much of this CPU work that you're busy doing and how the guild contention comes into play. But if you run with the threaded worker, you've just got one process.
Carlton Gibson:And you've got much less memory overhead from running one process than you have from running four. Shared initialization and all that. Connection pooling, everything. Yeah, all of it. But it's never as simple as, oh, this is the way to deploy. How do you deploy your application? how long you got and how many developers are we asking because we'll all give different answers for all these really interesting reasons that trade off against each other yeah something i
Michael Kennedy:would like to get your thoughts on is i feel like sometimes people say like why are we making python so complicated like the magic of python was that it was simple and yet there's also another side of that story where people's like well i have to switch to go because i can't i can't do this and so you got to walk this tight balance of there has to be a simple story but you don't want there to not be a nice upper bound or high upper bound because you're going to lose maybe your your biggest proponents or your your biggest users right yeah what do you think about that um no i think look
Carlton Gibson:python so you know i this fits my brain idea i think it's something i'm very into and one of my sort of grumbles about the type about typing is that it becomes not pipe it fits your brain i mean And, you know, I was told a story at PyCon Italia, I showed five typing experts sat around a table trying to work out the correct type in. And these are the absolute gurus, right? And that's not fit your brain, is it? So part of me is like, ah, on that front.
Carlton Gibson:But we have to be performant. You don't want to have to change language just because you need to increase your throughput, just because you're doing a more serious application. That's not good for, that wouldn't be good for long-term sustainability of the project.
Michael Kennedy:No, it definitely wouldn't. And the fact that you don't have to add typing, you don't have to write async views. I think that's part of where it's really good because you can grow into that. There is space to grow into.
Carlton Gibson:There is, though, a kind of pressure to the original DEP, which added type hints to Python. said, we don't intend to make type hints compulsory, even by convention. But I think there is very much people coming into the Python landscape. There is a cultural pressure to adopt typing, even if perhaps it's not relevant to you. It's like, oh, no, but this is how you do it. And there is a you should, which perhaps doesn't respect that original promise in the dead.
Michael Kennedy:Fair. And I think AI throws a whole spanner into it as well. And let's not go too deeply down this because we can spend the next three hours on but you know if you ask an ai to write python a lot of times it'll do typed python now sure without asking yes and um the big issue
Carlton Gibson:with um ai output is can you verify it and so you know type safety any type safety that you get from the type checker is going to help the ai um verify the output or help you verify the output 100 i
Michael Kennedy:think it's a big bonus to ai as well whether yes people care about that you know that's a different deal. Indeed. So what's left? Where else do people need to focus? Okay, so performance realities is,
Carlton Gibson:you know, DB parallelism is your limit, right? So each DB connection is a ordered, like, it takes, you know, it takes a query and it gets a response. And so whether you're coming, whether you're doing that in threads, the way Django does it, or if you're doing it with greenlets, the way some other ORMs do it, you're still limited by the size of your connection pool. Again, and that's whether you're doing it with WSGI or ASCII, the limit always has been the number of database connections you could hold open at a time, basically.
Carlton Gibson:So that doesn't really change anything. If you want to scale up, you need to increase the size of your connection pool or handle that more efficiently. That's one thing. Async transactions is something that, because of the way Django's connections are tied to a thread local, we're never going to have async transactions in the sense that you can call await inside an atomic block. Why not? Because that await call may not be on the same thread as the connection, right?
Carlton Gibson:So the transaction state is held on the connection, which is on a thread, and if that await call handles in a different thread, you're going to be in big trouble. So it's always going to be the case with Django's choice that you need to take if you want. It doesn't mean you can't have transactions in async. You just wrap your transaction in a single function, which you then call within a single sync to async. So that's always going to be the case.
Carlton Gibson:Then there's CPU band work. Look, if you do work on CPU, you either block the event loop or you throw it to a thread. And then, you know, if there's a lot of CPU work going on, you've got GIL contention that we'll talk about momentarily. Or you have to throw it out to a separate process. But throwing work out to a separate process is just crazily heavy. You've got to bootstrap that process. You've got to marshal your data. You've got to work out returns.
Carlton Gibson:So, you know, async frameworks have tools to throw out to a separate process. But it's not something you want to address lightly. Really, really, threading was the way you wanted to go.
Michael Kennedy:But you are going to hit the gill, essentially. Yeah, yeah. For people who don't know, if by default, when you use async and await on a standard event loop, that's single threaded. Even though stuff is happening, it's literally single threaded. And the way that it time slices it or preemptively shares it is anytime you hit an await block, like on a database call or whatever, it's like, okay, that's waiting. So now the same thread can go process something else.
Michael Kennedy:But soon as you're back in regular Python, just jamming on something, well, there's no way to time slice that, right? So everything else is waiting on that computationally.
Carlton Gibson:And you end up with really horrible things. And I'm going to say it's horrible. I think it really is horrible, right? It's where you've got a loop of CPU-heavy work. I know you're rendering it and you add in an asyncio sleep zero just to release work. And it's like, why are we doing that? We're doing that because we're running CPU work on the event loop. The event loop wasn't for that. It was for our handling I.O., by async I.O. And we really want to throw CPU bound work to a thread.
Carlton Gibson:We just want to. But then we've got Python's guild. So this is where I'm super excited.
Michael Kennedy:It effectively says, well, you have as many threads as you want, but you still can run one at a time.
Carlton Gibson:Yeah, exactly. Either way. So either you do the CPU work on your one thread, which is running the event loop, or you throw it out to different threads and they get GIL contention and so you end up with essentially one cpu or one threads worth of clock time no matter which way you cut it which is python's real problem and it has you know it it's not actually about switching threads it's not actually about creating threads it's not actually about spinning up event loops those are relatively quick things it's about the inability to genuinely run parallel work in in multiple threads in python up
Michael Kennedy:until very recently. Yeah, it's another axis of that. You probably don't need it, but it's a low upper bound that shouldn't be there for people who need to grow into it. Yes, entirely. And you
Carlton Gibson:shouldn't need it. It can come in at quite moderate scales. Okay, my Hello World blog application, I'm not going to hit gil contention with my 10 requests a minute. It's not a problem if I'm lucky. Yeah, that's when it gets popular, yeah, in the article. Yeah, yeah, yeah. Oh, I hit Hacker News. I've got 10 requests in a minute. You know, you're not going to hit GitGil contention there. But if you're, again, serious about using Python, a bigger application, yes, you are going to have to do CPU work at some point.
Carlton Gibson:Otherwise, the computer's not doing anything, right? The program, if it's going to do something, it's going to have to use the CPU at some point. And so if you're doing that at scale, the Git has been an impediment to that. And people are, oh, I'm going to switch to Rast. I'm going to switch to Go. So do we have to switch language again? Can we not do that?
Michael Kennedy:Yeah, let's make it so we don't have to. And you don't have to have an insane amount of requests to benefit from this. Kind of like my little example I just showed with the memory thing. If you have to run enough workers that you needed two servers, if this free threading thing and the async stuff let you shrink that back down to one more manageable server, it saves you on DevOps. It saves you on complexity. It saves your money. So if you want money, all these things.
Michael Kennedy:So you don't have to be Instagram level of Django requests to benefit from some of these ideas, right? No, absolutely not.
Carlton Gibson:I mean, it turns out, and I've always said for years, with a medium-sized box, you can run a very high-traffic server in realistic terms. But the more you can do on the smaller box, absolutely the better. Absolutely. So three threading is the big win. It's the big exciting thing because Django kind of looked clumsy almost when it said, no, let's just put all the sync work into a thread. But actually, as three threading becomes more established and it works through the ecosystem, it looks as if Django's bet's going to pay off.
Carlton Gibson:That bet will have aged very well. Because we always really wanted to do CPU work in the thread. I think it's great.
Michael Kennedy:Yeah, I mean, you can have a thread pool. Your threads could each have sort of a hanging around database connection for any time you need it, ready to go. And yeah, you just delegate it out and you actually get parallelism. Yeah, no, and that's the thing.
Carlton Gibson:Actual parallelism within Python is really exciting. And that's for everybody. I mean, you know, to go back, why did we update the async topic docs? It's because there are problems that remain with async, but they're not Django-specific problems. The same GIL contention problems you have, you type FastAPI concurrency in, or scaling problems, and you read the same sort of problems. And so it's not Django specific. It's not a Django problem there. It's a Python structural problem.
Carlton Gibson:Same database scaling. How do we do it? What do database pools? Well, same using Flask. You're going to scale it that way, et cetera. It's nice that these are general problems that we all share, I think.
Michael Kennedy:Yes, absolutely. yeah i mean and let's see i think let's open it no there we go i think it's just so easy these days to try out free threaded python too it used to be oh you got to get this weird thing and build it or whatever but now with uv it's just literally uv python install like what do you want do you want three fourteen six t yeah that's all you're saying in two seconds you've got free threaded Python to play with and try out.
Carlton Gibson:Yes. The thing here, there's still work to be done here. Most of it is about the ecosystem, not about the architecture. The architecture is already in Plex. So if you're at an app level, because people have been running threaded Django for a long time. We're talking about people deploying Whiskey with threaded workers. They've been doing that for a long time. But standardly, at the app level, you don't touch things which are multi-thread. You might have, I don't know, some module level caching.
Carlton Gibson:You might have a property at the module level. Well, hang on. Is that really thread safe? Do you need to wrap that in a lock? But it's extensions, it's libraries. Are they doing these kind of patterns? And we just need to work through them and run all our test suites against them and make sure that we're compatible with re-threading. And then I think we're actually going to unlock an awful lot of performance for everybody. So instead of having to run multiple processes to get parallelism, you'll be able to run it all within one process.
Michael Kennedy:You know, it's a really exciting thing. Yeah, I have some really interesting experiments I want to put together with free threading, but the more important work is still out there. Yeah. With AI, I'm not ready to, like, go and work on these. Like, I don't, I can't do another open source project yet.
Carlton Gibson:Yeah, no, and you must avoid it because the trouble is that, I maintain a lot of packages, right? And it's a burden. It's a thing that once you've taken it on, you can't just put that. And you might think, oh, it's just a casual thing. must be very conscious and careful about what you package up and put out there in the world because
Michael Kennedy:you're making a promise to people like yeah carlton i'm thinking this is going to be a really good gist not a repo you know what i mean yes right exactly put up a gist do a blog post put up a gist say
Carlton Gibson:here it is but don't put it up as a as a package and unless you mean it if you mean it then it's a package on pypi and you know all the rest people can install pip installs directly from github You don't have often version control. You don't have to put it on PyPI for people to be able to play with it. Yeah, absolutely.
Michael Kennedy:So one thing I want to talk to you about, I know you're excited about, is the built-in task framework. Because all of this stuff about threading and all of that, you know, parallelism and, you know, event loops, it's fine. But if you could just say, let's just run that somewhere else. Don't hassle me. Tell us about this.
Carlton Gibson:Okay. So this is a great question, because when we first added async to Django, people were like, oh, this is background tasks. And it's like, no, no, no, it's not. It's all about I.O. and multiple connections and long-lived requests and things like that. It's nothing to do with having a queue where you want to do some asynchronous task. So asynchronous is the word has appeared, but it means other than making people wait. So the standard web, you've got a request and you send a response, and you want that to be as quick as you can.
Carlton Gibson:But let's say somebody has a password reset and you want to send them an email so that they can click on the password reset link and they can reset their password. Well, historically, you would have made the request, sent the email, wait for the email to send, which can take almost any amount of time. And then only then do they get the HTTP response. Well, that's a long time to wait. That's a bad user experience, right? The much better is to make the request, say, yes, we've accepted it, put it, we'll talk about where we put it in a moment, and just send the response quickly saying, look, it's on its way.
Carlton Gibson:Give it a few seconds to arrive.
Michael Kennedy:It's already email. It's already a single. There's nothing you can do to wait for delivery.
Carlton Gibson:Yeah, yeah, yeah. So all you can do, though, is send. So what you do now is you quickly write a task to, say, the database with the Django task framework. And you would send that, there'd be a worker process running totally separately, which could then send out the email, say, for instance. Now, people have historically done this with either Celery or RQ or Django Q or then Django Q2. And there are Huey, there's a billion of these task queues out there.
Carlton Gibson:And problem there is that, say, Django itself couldn't rely on them. And neither could any third party package rely on them. Well, I could, but then I'd have to commit to, we're using Django Q2 for this. And all the people who were using Celery or RQ or Huey, they'd be excluded. And so what Django Tasks does is to provide a kind of back-end API that says, look, any package can use this API to enqueue a task and to check results and do the core activities that you need to do around asynchronous tasks.
Carlton Gibson:And then just by the user, just by configuring in the settings what their back end is, can either go for Celery or RQ or it depends. As long as those packages have implemented a Django tasks adapter, you can use those for the back end. And so I think, for instance, Celery hasn't yet done it, but there's an open issue and it will just it will become. But there are a couple of back ends that are available. There's a Redis one, there's one that uses the ORM to just store in your database and you can get going with those now.
Carlton Gibson:And for me as a third-party package maintainer, that's fantastic because now I can add tasks to my third-party package and users can benefit from those without me having to know anything about which backend they're using. Yeah.
Michael Kennedy:Your pip install or uv install instructions for your package aren't like bracket celery, bracket, whatever. And if none of those are there, it's going to throw an acceptance. Well, you didn't install any of the queuing options. So now we're busted, you know, like, yeah, you can just delegate. Yeah.
Carlton Gibson:And Cellerie's wonderful. It really is a truly wonderful piece of software. But it's literally overkill for 99% of projects. And it's operationally difficult to keep going. You end up running three or four different things. You need a monitor, a beat server, the actual worker. It's designed for a level of sophistication that most applications really don't need.
Michael Kennedy:I love that you call out the operational complexity as well. Because like you say, it would be nice to just let people who don't have something complicated use this feature without going, yeah, look, I know you used to, look, that was fun when you could just put it on a platform as a service thing and let it run. But now what we're doing is we're setting up a private network and now we've got poison messages and we've got downtime because the celery version had to change.
Michael Kennedy:Oh my gosh. It's a step jump, right? And just to be able to avoid that is great.
Carlton Gibson:No, it's a serious, serious. If you are taking on celery, then there is a serious question to ask. You know, if you're an established team, but if you're growing and suddenly it's like, shall we add celery? It's like, well, hang on, look at your ops capacity and look at your ability to, you know, do you have someone on call for when the workers break down at two o'clock in the morning and page notifications and all those things? Because it's a world up from self-hosting, you know, your bog standard Django app.
Michael Kennedy:As someone who does a lot of DevOps without a lot of support, I hear that. So, you know, Carl, I think this could have been like a three-hour show easily, I'm starting to realize. But let's sort of get some advice to kind of wrap things up. We're on a glide path here for people. Should they write async views today? What do you think about this? Yes, right.
Carlton Gibson:So if I'm writing a small application, like just my local blog application, I want to add a little bit of async sprinkle to it. I might just deploy a single ASGI worker by itself. It's probably big enough. You're not going to hit scaling problems, you know, with low traffic. So, you know, just a single ASGI application. I think the, as I say, the people who are doing this at a bigger level than that, I think they're running their core application as WSGI and the standard ways because the scaling patterns there are so established and known.
Carlton Gibson:and it's almost trivial by comparison. But then they're running a little sidecar to handle their app. So just have, you know, engine XA can route by the path or it can route by other things. But, you know, if it's got connection header, keep route, but that's a little advanced. Just route by path, put everything under an A prefix. And then, right, those are your async ones for, I don't know, your long-lib service center events requests. And then send everything else back by your whiskey.
Carlton Gibson:I mean, just do that. Get the hang of it. You'll find the scaling, that scales very well. And then you can say, okay, well, now if I move this to async, oh, okay, I start to see some of the complications of async appear. And I think that's the danger I see is when people dive feet first into async without really understanding that it is an order of magnitude more complicated to correctly handle async code than to just code synchronously. For all these reasons about blocking the event loop and you get deadlocks.
Carlton Gibson:These are really complex patterns that grow into them rather than jumping headphones.
Michael Kennedy:yeah yeah but django is ready yes no django's async story is there the problems that i see come up
Carlton Gibson:time and time and time again are problems with python and python's async story that we all share not django specific problems yeah or even that asynchronous programming in general yes asynchronous yeah they are yeah they are async or guild problems not um django specific django specific
Michael Kennedy:problems. Absolutely. I want to just put this out in the universe. If you're looking at your web app and you're like, ah, these are a little bit slow, these requests. So we're going to need to set up some parallelism so that we can handle multiple slow requests at a time. Like just take an hour and look at your database indexes, please. Database indexes are magic. And I'm not saying it's not a benefit to go async or whatever, but if slow is a problem, please just do, you know, look at the query plans, look and make sure every hot path is using a database index and so on.
Michael Kennedy:Yes, yes, exactly.
Carlton Gibson:I mean, and if it, so when you make a database, we always talk about the database, right? But if Django makes a database request, there's a little bit of CPU time to compile the request. And then there's the IO bit where it's talking to the database. And, you know, PsychoPG already releases the gil in that context. So you're already getting, you know, what concurrency or parallelism you would have at that point. And then there's CPU time to sort of marshal the return into, or structure the returned data into ORM objects.
Carlton Gibson:So those bits are CPU bound. But that core bit is already releasing the gil. You're already going to get parallelism there. So the chances are you're not going to get much more by jumping to Async or adding more workers. It was your database all along that was the thing that was taking the time.
Michael Kennedy:These things that we've been talking about,
Carlton Gibson:about CPU contention and all the rest. It's, ah, they come up in only specialized cases. They're kind of advanced topics, if that makes sense. They're often not the problem. Amazing when you need them, but it's not a panacea, yeah. Yeah, and we, I mean, how would I phrase it? We spend so much time thinking about the use cases for the advanced cases that we sometimes forget that the simpler ones are much more simple stories. And yeah, should I be writing async views?
Carlton Gibson:well, do it gently. Don't jump into it thinking it's some cure-all. Yeah, but Django's ready. That's cool. Yeah, yeah, yeah. No, absolutely. And that's why we made the effort to update the topic, because we realized we were giving users bad advice. Yeah, you're scaring them off. Yeah, no, we really were. We were like, oh, it's still incomplete. It's not ready. No, it's there. And yes, you will run into problems as you scale up, but that's not Django.
Carlton Gibson:That's async.
Michael Kennedy:Yeah, indeed. Final call to action. People consider Django. Maybe we're considering async for their existing Django projects or other things like the Django tasks, background tasks and so on. What do you tell them?
Carlton Gibson:Yeah, I mean, I would get going with Django tasks. You install the database backend for that, which is all the Redis ones work perfectly as well. If you've already got Redis in your stack and you want a little bit more, but most people don't need that. Just use the ORM database queue. It's a great storage. That's where you want to throw most of your work. You don't really want to be... With Async.io, you can, yes, throw something off to an executor.
Carlton Gibson:No, but don't do that because you've got no queue controls. You've got no result. You can't say, did it fail and then have logic to retry, any of those sorts of things. It's just running on the event loop. And if it crashes, well, what do you do about that? How do you recover from that? There's no elegance to that. So, yes, Django tasks is probably where I would point people first. And then do I need long-lived requests? Do I want to do things like service and events or WebSockets?
Carlton Gibson:Yeah, that's where. Or streaming, streaming responses. Async, great, great example. Yeah.
Michael Kennedy:You want to adopt Datastar or one of these frameworks that really leverages service and events. Yeah.
Carlton Gibson:Or HTMX version 4, which is in beta whatever now, which I think is the risk.
Michael Kennedy:Oh, is that coming with that as well?
Carlton Gibson:Yeah, yeah, yeah. So they basically were like, right, it's okay. So I think Carson was like, we're never going to do an HTMX version 3. and he's kept his promise because he's jumped straight from two to four um but the it was um it was inspired by some of the things from um data star and the surrounding projects it's
Michael Kennedy:like hang on we can have a go at that as well i think said goss you have to get him on and he can talk you through it yeah i i love carson i think what he's doing is great and i've had him on before i'm a fan of hdmx so that's cool maybe we'll do another no other round yeah so when i stepped
Carlton Gibson:down as a fellow in 23 i started a new application been building with hdmx and alpine since day one and just absolutely adore it. It's combined with template partials, which we added into Django, it's really changed the way I write web applications. It's amazing. All for the better as well.
Michael Kennedy:It's like JavaScript magic fairy dust. Yeah, it's how it should be. Yeah, exactly. Sprinkle it on there. It doesn't have to be a spa. Everyone calm down. We could still do some stuff on templates and so on.
Carlton Gibson:But when I learned JavaScript, that was how it was. You detach a few event listeners and just do your little thing.
Michael Kennedy:And that was enough, right? hashtag dollar document ready. Let's go. A little jQuery back in the day, right? Yeah. That's how it was. Yeah, yeah. Cool. Select something, do something. Exactly. Carlton, thanks for first all the stuff on Django for everybody and second, coming on the show to share.
Carlton Gibson:No, thanks. Thanks for the chat. It's been really good.
Michael Kennedy:It's really lovely because you pick on the topics
Carlton Gibson:and I'm like, yeah, yeah, this is right.
Michael Kennedy:Thanks. See you later. Thank you, Michael. This has been another episode of Talk Python To Me. Thank you to our sponsors. Be sure to check out what they're offering. It really helps support the show. Take some stress out of your life. Get notified immediately about errors and performance issues in your web or mobile applications with Sentry. Just visit talkpython.fm/sentry and get started for free. Be sure to use our code, talkpython26. That's Talk Python, the numbers two, six, all one word.
Michael Kennedy:If you or your team needs to learn Python, we have over 270 hours of beginner and advanced courses on topics ranging from complete beginners to async code, Flask, Django, HTMX, and even LLMs. Best of all, there's no subscription in sight. Browse the catalog at talkpython.fm. And if you're not already subscribed to the show on your favorite podcast player, what are you waiting for? Just search for Python in your podcast player. We should be right at the top.
Michael Kennedy:If you enjoy that geeky rap song, you can download the full track. The link is actually in your podcast blur show notes. This is your host, Michael Kennedy. Thank you so much for listening. I really appreciate it. I'll see you next time. We tapped into that modern vibe overcame each storm. Talk Python To Me. async is the norm. .
Transcript supplied by the publisher with the episode.
Talk Python To Me
by Michael Kennedy · English · Tech & Science
Talk Python to Me is a weekly podcast hosted by developer and entrepreneur Michael Kennedy. We dive deep into the popular packages and software developers, data scientists, and incredible hobbyists doing amazing things with Python. If you're new to Python, you'll quickly learn the ins and outs…
More from Talk Python To Me
-
E559 · 19 Aug 2026 · 1 hr 8 min
#559: 12 Things You Should (and Shouldn't) Do in AWS
Your site is down. It's 3am. Is it a bug, a bill, or a breach? You can't tell yet, and everyone is watching you find out. Matt Lea has spent fifteen years being the person companies call when an outage is costing them real money per hour, and his whole argument is that everything you'd want in that moment gets decided months earlier, on ordinary afternoons, when someone chose the convenient thing. We walk his top twelve dos and don'ts in AWS - infrastructure as code, IAM roles instead of access keys, private subnets, no wildcards, no public buckets - and I push on which of them actually…
-
E558 · 10 Aug 2026 · 1 hr 2 min
#558: Hyper-Personal Software with Python
Every company has one. The little internal tool that Jane built back in 2021, and then Jane left. Nobody understands it, nobody will touch it. There are two unwritten rules around it: don't change it, it's working. And if you break it, you bought it. That's dark-matter enterprise software. For every app you can actually see, there are ten of these sitting in the shadows, frozen. Michael Booth thinks that just changed. He read my article on hyper-personal software and ran with it, writing about hyper-team software: small teams inside big companies finally building the tools that were never…
-
E557 · 2 Aug 2026 · 1 hr 8 min
#557: Security of everything at PyCon 2026
Security has always been the vegetables of software. Everyone agrees it matters, and somehow it never quite makes it onto the plate. At PyCon US this year, that changed. For the first time ever, security got its own dedicated, day-long track, one of just two at the whole conference, sitting right next to AI. And the room was packed to the back wall. On this episode, I'm joined by the three people at the center of it. Seth Larson, Security Developer in Residence at the Python Software Foundation and, very recently, a CPython core developer. Juanita Gomez, a PhD researcher at UC Santa Cruz in…
-
E555 · 13 Jul 2026 · 1 hr 5 min
#555: Marimo Pair - A Canvas for Agent + Developers Collaboration
Coding agents have gotten really good at one kind of work. You scope a feature, edit some files, run the tests, ship it. It all happens on disk. But that is not how data work feels. You load something, you look at it, you run a cell, you watch how it responds, and you decide the next move from whatever is sitting in memory. And until now, your agent couldn't see any of that. It only saw the files. Never the live state. This episode, that wall comes down. marimo pair drops a coding agent right inside a running notebook, with full access to every variable Python is holding in memory. The…
-
E554 · 10 Jul 2026 · 1 hr 1 min
#554: Trustworthy AI in Healthcare and Longevity
You ask an AI a question and it answers with total confidence. Most of the time, a confidently wrong answer is just an annoyance. But what if the question is medical, and there's a real patient on the other end? In that world, a hallucination isn't a bug, it's a patient-safety event. Sumit Gundawar is a London-based software engineer who builds the clinical platform for a UK longevity and aesthetic-medicine clinic, and his whole argument is that in high-stakes AI, the model is the easy part. Earning trust is the real engineering. We dig into grounding, refusal logic, human-in-the-loop…
-
E553 · 26 Jun 2026 · 55 min
#553: All of our tools
This episode is a fun crossover from our Python news and tips podcast, Python Bytes. We have had some big changes over there. Brian Okken has moved on and Calvin Hendryx-Parker has joined the show as the new co-host. To kick off this new era, we decided to do a longer and more personal episode called "All Our Tools". The idea is both of us talk about some of our most useful day-to-day developer and business owner tools that we think you all would find useful. It was so well received, that I'm bringing it to you all as a crossover episode. Enjoy and we hope you find something new and awesome…
-
E565 · 2 Oct 2026 · 1 hr 28 min
#565: Tachyon, Python 3.15's Built-in Sampling Profiler
Do you know what's actually slow in your Python app? Or are you guessing? Until now, profiling Python meant a tracing profiler that made your code 2 to 3 times slower. Or a third-party tool that broke with every new release. Python 3.15 fixes that. It ships Tachyon, a sampling profiler built into the standard library. It attaches to live production apps with almost zero overhead. My guests are Pablo Galindo Salgado, CPython core developer and Steering Council member, and László Kiss Kollár from Bloomberg's Python infrastructure team. Their first prototype ran at two samples a second. Now it…
-
E564 · 22 Sep 2026 · 1 hr 8 min
#564: EVE Online Departs for Python 3
Every ship in EVE Online eventually undocks and leaves the station. This time, it's the whole game. EVE has run on Python 2 since it launched in 2003, all 2.4 million lines of it, on a custom Stackless interpreter that stopped at 3.8 and was archived last year. Destination: Python 3.12. The route runs through 6,500 lines of division that decide who wins a fight, and 100 gigabytes of pickled Python objects that have to survive the jump intact. Kristinn Sigurbergsson was on this show ten years ago. He's back, with Jamie Bannister, who is flying the EVE Online migration right now, and Thomas…
-
E563 · 16 Sep 2026 · 1 hr 11 min
#563: Getting Started with Rust as Python Devs
Lint the entire CPython code base from scratch. It takes 0.3 seconds. Three blinks of an eye. That is ruff, and it is written in Rust. So are Pydantic, Polars, uv, and Granian. Rust shows up in Python three ways: tools that happen to be Rust, libraries Python imports, and servers that run Python inside Rust. This is Rust for Python developers, not Rust experts. Christopher Trudeau is back on Talk Python to discuss Rust and his latest course Up and Running with Rust. The core rule is that only one thing can own a value at a time. Pass it around freely in Python and the garbage collector…
-
E562 · 10 Sep 2026 · 1 hr 11 min
#562: DuckLake: The Lakehouse That's Just SQL and Parquet
How many files does your query read before it reads any data? On some data lakes, you go through JSON and metadata files first, just to learn which Parquet files matter. DuckLake asks one SQL question instead. The metadata lives in a real database. The data stays in plain Parquet. That's the entire format. Pedro Holanda joined DuckDB in 2018, when it was still a research prototype at CWI. He's the lead DuckLake developer. Guillermo Sanchez Dionis works on DuckLake and the new Quack protocol. With Quack as the catalog, DuckLake handles 200 transactions a second under heavy contention. No…
