Python Bytes - #374 Climbing the Python Web Mountain

Episode Date: March 11, 2024

Topics covered in this episode: 6 ways to improve the architecture of your Python project (using import-linter) Mountaineer Why Python's Integer Division Floors Hatchet Extras Joke See the full ...show notes for this episode on the website at pythonbytes.fm/374

Transcript
Discussion (0)
Starting point is 00:00:00 Hello and welcome to Python Bytes where we deliver Python news and headlines directly to your earbuds. This is episode 374, recorded March 11th, 2024. I am Michael Kennedy. And I'm Brian Ocken. And this episode is brought to you by Scout APM. Check them out at pythonbytes.fm slash scout. I'll tell you more about them later. If you'd like to connect with us, Mastodon is the main place. We're also on ex-Twitter, but primarily on Mastodon.
Starting point is 00:00:32 And that's at mkennedy, at Brian Ocken, and at Pythonbytes, all at fostodon.org. And watch us live, usually Tuesdays at 10 a.m. Pacific time. However, different today, but check it out at Pythonbytes.fm slash live. You'll be able to like get notified about the next upcoming recording. I usually put that up right after we're done with this one. Brian, before we jump into your first topic, I want to just take a
Starting point is 00:00:55 moment and appreciate the beginning of summer, the first step towards summer coming. It is daylight savings switch over here in the U S and I know it is much maligned by people, but I was delighted to see the sun was up past 7 PM yesterday after living in dark and rain for months and months. I'm feeling, I'm feeling the summer. I know it's not quite there yet, but yeah, I didn't really notice it until after I woke up. Um, yeah. I woke up and I'm like, Oh gosh, I, I thought'd slept in until like 10, but it was really 11. So sleep the day away. Oh, beautiful.
Starting point is 00:01:32 Beautiful, beautiful. All right. Well, over to Python. What's your first thing? Okay. Well, I want to talk about spaghetti code a little bit. Actually, or how to fix it. So there's an article.
Starting point is 00:01:43 Is that what you get when you're real hungry? You're like, what are you going to have for dinner? Maybe some spaghetti code. The little carbonara. Is that how you pronounce it? I've never been able to pronounce it. I'm probably going to get emailed that it's not, but that's how I pronounce it.
Starting point is 00:01:56 Article from somebody that goes by Piggly. Six ways to improve the architecture of your Python project using import linter. And I kind of like this article, even if you don't want project using import linter. And I kind of like this article, even if you don't want to use import linter. So because of the six ways to improve the architecture, I love that. I love digging into that. So and I actually have a couple projects that I'm working on that I would like to maybe clean up the architecture a bit. So kind of a fun picture, not sure what's going on here, just a whole bunch of boxes pointing at each other, I guess, just indicating that there's circular dependencies
Starting point is 00:02:30 or something going on. And anyway, so a little bit of a discussion about why complex architecture might be bad, but I don't think any of us need convincing of that. Simplifying is a good thing. So the first part talks about maybe setting up an idea of like maybe you could you have an idea of like setting your architecture into layers. If that's what you want to do, like a user layer or an application layer plus utilities or something services. But there's a tool called the import linter that there's a discussion about how to set it up so that you so that you can use that to both configure what you want your layers to be and then test for it. It's a like a linting to make sure that you're not importing in the wrong direction. So the idea would be like you're not importing like if you want the top level one to be calling the lower level ones, but not the other way around. So the importing is a way to test that.
Starting point is 00:03:29 Because of that, I'm not sure what these arrows mean, because it doesn't quite make sense if it's not inheritance or calling. I don't know. Anyway, it's just. That looks pretty interesting. I think that means that something from that layer is importing something from the bottom layer, the lower layer. Yeah, but, yeah, okay. You can have stuff like import across within, but then it can only, I think it would be an error or a warning if maybe, say, like the data layer imported the UI layer sort of thing. I think that's what it's saying.
Starting point is 00:04:02 Yeah. Oh, and it makes more sense if I would have drawn the top layer at the top. I think it makes more sense to me if we do it the other way. Anyway, that's, that's a drawing thing. It doesn't really matter. And also it was by somebody in Australia because everything is upside down down there. Oh yeah. Yeah.
Starting point is 00:04:18 That makes sense. Yeah. Yeah. That was it. Okay. Okay. So what happens when you run this is you're probably, the recommendation is you're probably going to get a bunch of Lint warnings or errors. Or maybe not.
Starting point is 00:04:31 If not, awesome. But if you do, the recommendation here, which I kind of thought was cool, was to kind of exclude all of them. Like go through and add these ignore imports and just go through and ignore the ones that failed. And I'm like, okay, well, then you're going to pass and it's just going to ignore everything. But the idea behind it is to do it one at a time. So it's going to be overwhelming to get a bunch of errors. So ignore them all and then unignore one at a time and then go through and fix them. So that's where the reason why I picked out this article isn't really because import linear is cool.
Starting point is 00:05:10 It might be cool, but it's that these ways to fix these import dependencies I thought were really great to walk through. There's six of them. First one is merging and splitting modules. And there's an example where you've got resources that calls clusters, clusters calls resources dot cluster utils, and that's going the wrong direction. But to fix it, you maybe move those cluster utils down into the lower, like a lower library, like splitting them off. Kind of sort of straightforward, but
Starting point is 00:05:42 it's good to like think about this so i like that that part of it dependency injection and if you're the kind of person that's kind of afraid of dependency injection then don't even think about that term because it's not actually that scary just the term was scary to me for a while so uh anyway dependency injection might help to be able to pass uh a pass dependencies down into lower layers from upper layers. So that's a good way to get around it. The interesting, I'm glad they dug into this, is when you do the inversion of, what is it? I forget, the inversion of control.
Starting point is 00:06:20 Inversion of control, yeah. Yeah. Sometimes with Python, that works great except for type hints um sometimes you need to to get the type hints getting those right so talking about how to use the um protocol uh from typing to get that to work right that's that discussion's in here which is great i love protocol um then another discussion about using simpler dependency types and then delaying function implementation um and then uh and then even what was the the last one look at for six configuration driven that was interesting um i've never really thought about doing this the
Starting point is 00:06:57 the idea is you'd have a like a settings file or something and have that have and then have the string that you would import like marketing.send sms and then later on in your calling thing you use import string to import it so you're you still have the backwards dependency but you don't know it at at run at compile you know at write time you know at run time i don know. I don't know what I think about that, but anyway. Yeah. Yeah. That's interesting. It's, it's a way to do it. So, and then the last one is a replace function calls with event driven and purchase. So like callbacks and stuff like that. So these are a great architecture things to think about when you're cleaning up architecture, because it's not always trivial to just say, just don't do that. Don't do those imports. Well, how do you get around it if you've designed it that way? So I think a decent discussion about software architecture here. So I do think that's
Starting point is 00:07:54 pretty interesting. And also just more broadly, I like the idea of ignoring all the issues you might run into with lenders and then slowly turning the screws to make it a little tighter is good advice because if you have existing code of any significant size and you've never done linting on it and then you turn on a linter. Yeah. Like you feel bad about yourself.
Starting point is 00:08:14 You're like, I've done all that wrong. 593 errors. Great. Well, we'll turn that back off because I got work to do. You know what I mean? Yeah. Well, I'm kind of going through that
Starting point is 00:08:24 with the rough right now. So got some projects where default rough works fine but the rough has like 800 rules or something you can add and so i'm trying to turn on some of those extra features i have a just a few at a time see testing the waters see if how many failures i get and whether i want to clean them up. So, yeah. Yeah, interesting. Just interesting timing. I'm going to be speaking with Charlie Marsh on TalkPython tomorrow. Oh, awesome.
Starting point is 00:08:52 About 24 hours from now, whatever that makes it for you. Yeah. Out there listening. Yeah, and we're going to talk mostly about UV, but I'm sure we'll talk a bit about rough as well. Cool. Well, I'm going to release an episode
Starting point is 00:09:02 with Charlie Marsh today. Well, how about that? Awesome, awesome awesome do you guys talk about uv as well yeah we talked about uh yeah flick eight or not flick eight um talked about rough and astral and uh and uv most of the conversations around uv and some of the discussion around that so Nice. That'll be fun. All right. On to the next one here by Pierce Freeman. That's kind of a cool name, isn't it? It could be like a 00 sort of agent. Yeah. 009.
Starting point is 00:09:33 I don't know what that is. Not James, but something like that. Anyway. Pierce Freeman to the rescue. Exactly. To bring you React and FastAPI and Python. In fact, with this framework called Mountaineer. So Mountaineer is a batteries-included web framework for Python and React.
Starting point is 00:09:51 So this, it plays in a similar space as FastUI from Samuel Colvin and the Pydantic crew. I don't know enough about them to know how truly similar they are. I think this is coming from a different angle. I think you you're doing, you know, the, so fast UI is more about maybe you don't really have to do the react side unless you want. And it kind of brings that stuff together. Whereas this kind of like you're embracing TypeScript, you're embracing react, but you also get some really nice Python integration.
Starting point is 00:10:23 And so if you look down here what does it say it says it lets you easily build web apps in python and react and if you are familiar this it should sound familiar to you and should basically seem like what you're used to and if not then yeah maybe not but it says each framework like flask or fast api or django or whatever has its trade-offs and features. And for this one, it focuses on developer productivity above all else with production speed of close seconds. So type hints up and down the stack, front-end, back-end database, trivially easy client-server
Starting point is 00:10:56 communication. So you don't find yourself creating a bunch of APIs so that your React stuff can talk to the APIs so it can actually get its data and all that, which is pretty interesting. It comes, this is kind of cool. So one of the things you can run into, I'm sure you've seen this, Brian, it drives me absolutely bonkers. You'll go to a website and it'll have something on the screen. And then like half a second later, it'll shift around and stuff will like all come into existence. existence you know you'll be like it'll have like the footer will be touching the top and then it'll bump out it'll be a spinner and then stuff
Starting point is 00:11:29 you know it's like what is it what is it doing well especially if you start reading and then a picture pops in and your what you read pops off the screen and yeah another thing that drives me crazy is um if you paste something into a input but but you don't type it, sometimes that won't trigger the data binding. And, you know, like if he's a password, password manager type thing or something, or you just paste something, it'll say, oh, this is invalid. What is wrong with this? Oh, if you put a space and delete the space.
Starting point is 00:11:57 Oh, oh, it's valid now. It's like, oh, I see. So something that would be really nice is if you just could ship straight HTML, right? Yeah. Or the first view of that was. And so what this comes with is they actually bundle the V8 engine. So on the server side, it can act,
Starting point is 00:12:15 it can render what your browser would do for you as final HTML and it delivers it with. So optimize server side rendering for better accessibility and SEO. That's pretty cool. I think. that was cool. As a Python thing. Like normally you hear that as a node thing or something right yeah it also does static analysis for validations of like links and css and so on and like i said skip the api uh or node.js server just for front-end clients okay so all of these things are pretty cool if let me give you a warning and a disclaimer
Starting point is 00:12:46 one, if you don't know react real well, I don't think you'll really appreciate the benefits here that much. Like this is really for react people. 100%. Second, that's not me. So I'm going to do my best to like tell you why you might want this. I think I can get there. So first of all, it has a scaffolding type thing called create mountaineer app and they suggest pipx and i'm loving to see more pipx come along for these kinds of tools right like you run this once it's not part of your app you just pipx install it and everything gets going it's great also uses poetry pretty heavily um so what it does is it creates some python bits and then some TypeScript stuff for your
Starting point is 00:13:26 front end. And it comes with a CLI as well, which is nice. It has a built-in Docker containers for like managing Postgres databases and so on, if you want to use that, but you don't have to. And let's see. So another interesting integration is it uses SQL model. So that's the typing and the data layer aspect. So SQL model is Pydantic plus SQL alchemy, basically the typing and the data layer aspect. So SQL model is
Starting point is 00:13:45 PyDantic plus SQL alchemy, basically by Sebastian Ramirez. So that's cool. And then you go down here and you create controllers. So it's kind of a class-based type of thing. First, it seems a little unnecessary, but as you interact with it and expose more features to the React layer, you'll see that kind of relevant there. So you just say, I'm going to render, say, my database things and some other pieces of data. And then down somewhere, you've got your React code and your TSX, your React component there.
Starting point is 00:14:18 And if you've written React stuff, you should know pretty well how it works. But it manages passing all that data over like serverstate.todos. Then you can just work with that, which is interesting. But it gets more interesting later if you say, let's add an async function like add one of my to-dos. They have a to-do example, right?
Starting point is 00:14:36 So if you put this at side effect decorator on it, here's where the React integration comes in. That's pretty wild. So it automatically generates typed, typed, let's just say typed TypeScript because, I mean, you can't have non-typed TypeScript, but generally TypeScript is typed. It generates TypeScript versions of the functions
Starting point is 00:14:55 that you write in Python on the JavaScript side so you immediately can just start calling it and using those features, right? So it kind of has this really tight integration with React, like, as you would expect. What else? I think that's pretty much it, it and using those features right so it kind of has this really tight integration with react like as you would expect what else i think that's pretty much it but it's if you're a heavy react shop and you want a nice python back in and you want a tight data integration between those this is probably worth a look yeah neat yeah yeah it looks pretty neat to me too i'm not like i said
Starting point is 00:15:22 i'm not really a react person so i'm not sure that I'm necessarily going to use it. But if I were to start adopting React, I may well decide that that's what I want. Speaking of cool things, Brian, how about Scout APM? Let me tell you real quick about Scout APM. They're big supporters of Python Byte. So we appreciate that very much.
Starting point is 00:15:44 So if you are tired of spending hours trying to find the root cause of issues impacting your performance, then you owe it to yourself to check out Scout APM. They're a leading Python application performance monitoring tool, APM, that helps you identify and solve performance abnormalities faster and easier. Scout APM ties bottlenecks such as memory leaks, slow database queries, background jobs, and the dreaded N plus one queries that you can end up if you do lazy loading in your ORM and then you say, oh no, why is it so slow? Why are you doing 200 database queries for what should be one? So you can find out things like that. And it links it back directly to source code so you can spend less time in the debugger and healing logs and just finding the problems and moving on. And you'll love it because it's built for developers by developers.
Starting point is 00:16:30 It makes it easy to get set up. Seriously. You can do it in less than four minutes. So that's awesome. And the best part is the pricing is straight forward. You only pay for the data that you use with no hidden overage fees or per seat pricing. And I just learned this, Brian, they also have, they provide the pro version for free to all open source projects. So if you're an open source maintainer and you want to have Scout APM for that project, just shoot them a message or something on their pricing page about that. So you can start your free trial and get instant
Starting point is 00:17:01 insights today. Visit pythonbytes.fm scout the link is in your podcast player show notes as well and please use that link don't just search for them because otherwise they don't think you came from us and then they'd stop supporting the show so please use our link pythonbytes.fm scout check them out it really supports the show awesome awesome what's next brian well what's next is Guido van Rossum. Oh, yeah. So he's blogging a little bit lately, and he put up a post called
Starting point is 00:17:32 Why Python's Integer Division Floors. And I think this is just an interesting little bit of history. And this was a difference between Python 2 and 3. I guess, no, integer division always did flooring, but we did kind of a thing of what one slash meant.
Starting point is 00:17:56 If you do two slashes, it's always integer division. If you do one slash, if it was both integers in Python 2, it would be integer division, and it would possibly not be the floating point result. But in Python 3, it will generate a float if you have it. Like, for instance, one third will, one divided by three results in a float. But if you do integer division, it's not.
Starting point is 00:18:21 It's something else. Is that why the two to three conversion was so hard? I'm just kidding. What was that? It was strings. Everyone knows it's not it's something else is that why the two to three conversion was so hard i'm just kidding what was that it was strings everyone knows it's strings so is that why the integer the the python two to three uh story was so hard no i'm just joking yeah um so uh yeah so if you do five to two slashes so integer division of five divided by two, you get two. And which is normal. That's everywhere. But if you do it, like, say, negative five, you get you don't get negative two.
Starting point is 00:18:57 You get negative three. So that's the there's a question. So Guido said that he had a question about that of why it's different um why it's like that and so it's going it does a division and then it goes to the the closest integer to the negative closest to negative infinity so um and there's there's reasonings behind that and but it's different than c apparently i completely forgot what C did. C does it closer to zero. So you'd both negative five divided by two would, you'd end up with two negative two.
Starting point is 00:19:31 So the, the history there is that there was a, there was a choice to make and you could either with you, it works with the modulo operator as well. Modulo will create the remainder where integer division creates the integer quotient. So such that a divided by b equals q with remainder r such that r is between 0 and b. There's math here. But you have a choice as to what you want to do,
Starting point is 00:20:07 whether you want R to be possibly negative, positive or negative for the remainder, or if you want R to always be positive. And basically Guido chose the one that looks nicer in math. So that we go do a floor division instead. The interesting take on this, I thought, was why did C choose the other way? And that's the part that I thought was really interesting. And his answer, or his guess, is that, well, C was doing it way before Python was. And C was doing it way before Python was, and C was doing it on hardware that
Starting point is 00:20:46 it may have been easier to do division closer to zero instead of floor division. And part of that reason might be because some of the early hardware architectures were using sine plus magnitude rather than two's complement, which is kind of, I didn't know that. I must have, either if I did know it from CS, I forgot it. Definitely remember two's complement. But anyway, it's an interesting history there. Also, one of the things I brought up,
Starting point is 00:21:17 one of the reasons, it's kind of a silly little article to bring up, but one of the things I wanted to bring it up is because a lot of new python people actually don't remember um we'll forget about integer division and just assume that division is division and that but inner division is really handy for a lot of cases so don't forget about that's true actually yeah i find myself sometimes doing int of some float result. Maybe I could just double slash it and not have to. So comment from the chat, which I'm not sure how to take this.
Starting point is 00:21:51 I'm thinking that they're bored with this topic, but... I'm not sure either. Anyway. No comment. All right. You know what? We're going to bring the hatchet out on this one, Ryan. Bring in the hatchet.
Starting point is 00:22:13 So there's this thing I ran across called Hatchet, which is a distributed task queue for more resilient web apps. Now, I don't recall exactly what it is written in. I don't think it's written in Python. It's unclear. Its primary language is Python, but also has a Go. Anyway, it doesn't matter. It has a Python. Its first SDK,
Starting point is 00:22:32 its first integration is with Python. So here's the idea. You've got some work. It's going to take a little while to run. You know, your web app says, hey, I want you to ship this thing or I want you to run some analytics. And if those analytics take 10, 15 seconds to run, maybe they're computational and they should run out on another computer rather than on your main web front end, or they shouldn't block it for 15
Starting point is 00:22:57 seconds or whatever. When you were talking about your, how do you break up import dependencies across the wrong layers and stuff? Maybe one way to fix that is to move some of the compute work completely to its own place, right? This whole queuing mechanism is super fascinating for creating truly scalable multi-user thing, right? So if the majority of your work is in some place and you kind of don't really need the answer to give a response, you can just throw it onto one of these background cues and and let it go so it one of the problems though you run into though is what if something goes wrong or how do i see what is running something fails can i resume it maybe it was really important like ship this thing to the customer but when i put that on the queue and it finally got around to being run, the API at UPS was down for who knows, whatever reason, right?
Starting point is 00:23:48 Things like that. And you can't ship it. And they just go into the ether as an error or you resume it. Another problem you run into is fairness, right? If there's a ton of work coming in faster than the processor can handle, is there some thing where maybe only the new ones get worked on and the older ones get almost abandoned, right? There's all these interesting things. So this thing called Hatchet is in the realm of many different things that attempt to solve this problem, right? It's interesting. It's Y Combinator backed. It's a company that presumably will have a
Starting point is 00:24:21 price, but there's also just an open source self, you know, take it for yourself and run with it version over on GitHub. So 100% open source, 2,200 GitHub stars. Pretty interesting. But I think the business model is, it says request cloud access. Like they can run it for you
Starting point is 00:24:38 or you can run your own, right? Yeah. So the website has a bunch of these little animations, which are kind of cool talks about fairness uh batch processing and like as you click on them see how they like has these little fun fun animations like what does this mean oh i see oh i love it i do too i do too so talks about uh fairness batch processing workflow and event stuff. It's engineered for scaling challenges, which is pretty awesome. So low latency, 25 milliseconds on average, which means if you put something into the queue,
Starting point is 00:25:11 there's ways in which you can sort of make callbacks to check on the process of the work, and it shouldn't take all that long. A bunch of rules about rate limiting. also durable. So you can replay events. You can do cron jobs and say, hey, every morning, just drop this into the queue and run it at 7 a.m. or whatever. You can schedule one-time jobs. It has ability to avoid being destroyed by spikes. Like if for some reason,
Starting point is 00:25:40 a whole bunch of work comes in all at once, maybe you got IoT things that do a bunch of work when people come into the office and they very first sees a bunch of stuff and in all at once and maybe you got iot things that like do a bunch of work when people come into the office and you very first sees a bunch of stuff and then it chills out right you could smooth that out all kinds of stuff but like i said it supports three technologies python number one typescript number two and go number three and it's really easy uh to do you just go down here and you just put a you know when this event happens i want you to run this class and then it has a bunch of functions methods you say here's a step step one do this work step two so you just basically put some decorators on a class and then plug it in and off it goes super easy and to run it you just say push an event whatever the name it is with the
Starting point is 00:26:21 data and it'll go put it off in the background and run it so yeah it also has like nice visualizations like here you can see there's this um on hatchet.run you can see there's this like live view of how is the work running through the system and all kinds of stuff so it looks pretty neat to me open source people can check it out it's worth knowing about yeah it's pretty cool neat yep indeed indeed uh that's it for our items how are you feeling how extra are you feeling i have only got one extra that i almost that i pretty much mentioned already so i'll do it quickly so um python test is at 215 right now as we look but the most recent episode that will come out probably today is two 16, which will be, um, Charlie Marsh, uh,
Starting point is 00:27:05 talking about UV. So check that out. Also. Awesome. Yeah, you did mention that. That's, that's really good though.
Starting point is 00:27:11 How about you got any extras? I'm feeling somewhat extra. I got two exciting announcements. One, I have a free new course over at talk Python training that covers a bunch of awesome technologies, but the, the core idea, the title is Build an Audio App with AI, with Python and Assembly AI.
Starting point is 00:27:31 So the idea is, what would you do if you, say, had access to, I don't know, a podcast worth of data that's been going for many years? Like Python Bytes or TalkPy Python are honestly the thing we build lets you access a whole library of podcasts. And you go in there and do things like, hey, create me a transcript, which seems kind of straightforward. But once you have transcript data, you could get really cool search, like building your own custom search engine, not just over the title and the show notes and stuff, but also all the spoken words, which is kind of neat. Then you also bring more of the AI stuff in. You could create a summary. What are the key moments of this? And actually, what if I could
Starting point is 00:28:10 just have a Q&A with like you and me around what we said in the show? So kind of creating an LLM chat GPT type of thing, but where it knows about any given episode out on the internet. So really fun. People will learn FastAPI. They learn Pydantic. They learn HTMX. They learn Beanie. And they learn Assembly AI and build a cool thing. And the whole course is like a four-hour free course.
Starting point is 00:28:36 So they can check that out. Wow, neat. Sounds fun. Thanks. And next to it, another new course, Rock Solid Python with Python with python typing so this one is not a free one but it basically shows you not just the how but the why and when of python typing a bunch of different examples um you know obviously the language but you know things like fast api and pydantic how do they use it um what you talked about protocol before what is
Starting point is 00:29:05 protocol where does it fit um bunch of design patterns and guidance for python typing and how to think about how you should use it so people should also check this one out i'm really proud of this one and it is also around four hours 4.4 hours and uh pradeep asks out there are these courses cater free yes the build an Audio app course is 100% free. You just have to create an account. The Rock Solid Python course is 49 bucks. Yeah, but that's like 10 bucks an hour. That's almost free.
Starting point is 00:29:35 Yes. It's certainly not a lot of money, you know, compared to other ways you might go learn about things like this. So anyway, both of these courses are awesome. People should check them out. So those are the two big announcements. I also have a couple of interesting things I just want to give a quick shout out to. Previously, we spoke about Doku. I'm going to go with Doku because I think it's based on Docker. I don't know. Yes. Doku. And this is an open source platform as a service alternative to Heroku. We already spoke about that. But when we did, Ray out there on Macedon,
Starting point is 00:30:08 thank you, Ray, said, hey, you guys, love the episode on Daku. Haven't tried it myself. Big fan of Heroku. However, I set up Coolify. Coolify. I haven't talked about this, have I? I don't think so.
Starting point is 00:30:22 Yeah, I don't think so. Okay. So Coolify is kind of the same. So it's pretty similar, but it has a nice GUI to configure everything and keep an eye on the status and all those things. So Coolify is self-hosting with superpowers. It's a self-hosted alternative to not just Heroku, but also Netlify and Verisell. So Netlify for static sites.
Starting point is 00:30:44 You basically set this thing up, get it goinglify and Verisell. So Netlify for static sites, you basically set this thing up, get it going. It'll run any language on basically any server. You just push to some Git branch to deploy it. It does automatic SSL certificates. So if it just had a static site and I just want it to run over SSL on the internet, boom, done. It just lets encrypt automatically as part of creating the app up there and gets it going. So it's probably a little bit of setup to get it going and get it running on Docker and stuff. But once you do, it just becomes the substrate for all of your apps that you want to put out there. And you don't have to think about anything but Git basically. That's pretty cool actually yeah it looks really really nice so
Starting point is 00:31:25 people can check this out um yeah it has a paid cloud version and a self-hosted version with 17 000 or more people using it uh self-hosted so that's pretty cool it's interesting they give stats there but that's my last one i think this is really neat as well. So Ray, thanks for sharing extra details. Yeah, nice. Cool. Shall we close it off with a joke? Yeah, let's. Yeah, okay.
Starting point is 00:31:51 So speaking of, I want to run my stuff on production. How do I do it? This is a great, a great one. Back to workchronicles.com. And so I don't know how you feel about this, Brian, but I think it's pretty true. There's two engineers talking. It says, oh, no, I broke production.
Starting point is 00:32:08 Will I get fired? The Morrissey developer looks over. If we fire engineers who break production, we will need to fire everyone eventually. Yeah. Yeah. Also, if you fix it, you'll get a promotion or a raise or something. So there you go. Yeah. Yeah. Also, if you fix it, you'll get a promotion or a raise or something. There you go. Yeah. Maybe you just need to keep your fix rate above your destroy rate.
Starting point is 00:32:33 Yeah. Yeah, there you go. Well, that's what I brought for us today. Cool. I like it. Yeah. Excellent. Okay, well, nice to kick off the week with a little Python Bytes. Happy to do it early. Yeah, good to see you.
Starting point is 00:32:47 And thanks to everyone who joined. Bye.

There aren't comments yet for this episode. Click on any sentence in the transcript to leave a comment.