Transcript #378: Python is on the edge
Return to episode page view on github00:00 >> Hello and welcome to Python Bytes, where we deliver Python news and headlines directly to your earbuds.
00:06 This is episode 378, recorded April 9th, 2024.
00:12 I'm Michael Kennedy.
00:14 >> I'm Brian Okken.
00:15 >> You can follow us over on Mastodon.
00:18 We're all on Fossodon, @brianaukin, @mkennedy, and @pythonbytes.
00:22 We'd love to talk to you over there.
00:23 We're also on X Twitter, if you want to be there as well, but we probably spend a little more time on Mastodon these days.
00:30 Support the show by supporting our work.
00:33 We have obviously a bunch of courses that Talk Python Training, Brian's complete pytest course,
00:38 and the Patreon as well.
00:39 Be part of the live show if you wish.
00:41 You can see the video version.
00:42 Absolutely not required, but always awesome to have people in the audience to give it
00:47 a little bit more of multiple perspectives.
00:50 We'll get some of that coming on in a second.
00:52 You can check that out at pythonbytes.fm/live, usually Tuesdays at 10 AM.
00:58 That's specific time.
01:00 Finally, if you want an artisanal handcrafted digest of what we talk about,
01:05 sent you an e-mail form, even if you don't listen, well, head over to the website pythonbytes.fm,
01:12 click "Newsletter" right in the middle and enter your e-mail address.
01:15 We will not share it or do other nefarious things.
01:18 We just want to be able to contact you and have a chat if you wish.
01:22 Well, Brian will be sending out something cool to everyone this week as usual.
01:26 Brian, do you have health news or something you got to share?
01:30 What's going on here, man?
01:31 >> Well, I've found a pacemaker.
01:35 >> Okay.
01:35 >> My ticker is doing good.
01:37 No problems with that.
01:39 But you can control your heart with Python.
01:43 >> Okay.
01:44 >> Actually, you can't control your heart yet.
01:46 Actually, I don't know if you can.
01:49 But I ran across a project from Brandon Rohr called Pacemaker.
01:55 What this does, it's not controlling your heart, it's controlling time per iteration loop.
02:02 I don't know if this has anything to do with UV or not, but one of the things that UV has brought us is
02:09 really fast installing of lots of packages if you have a lot.
02:12 Why not? This is a small package.
02:17 This is in Brandon's own words on the read me.
02:22 I think I saw this here.
02:24 It is essentially, it's a glorified snippet.
02:31 Instead of a snippet, he wrote a package, which I love this.
02:35 I'm taking a look at it.
02:37 It's a small package.
02:38 Good example though for how to do a package.
02:41 If you take a look at the pyproject.toml, it's pretty concise.
02:45 It's using setup tools, which is fine.
02:48 But it shows you how easy it is to put a package together, which is pretty fun.
02:53 Also with the code, I was taking a look at the code.
02:56 What this does is not terribly earth shattering, but it just sticks around.
03:04 You tell it that you want to, it's like a metronome thing.
03:07 You've got some code that you want to run, and here's an example.
03:12 You just say pacemaker beat, and it waits.
03:17 It's a busy wait or it does a sleep or something like that.
03:20 Yeah, sleep. But it sleeps and then comes back alive, does its thing, and then goes back.
03:26 You can have it be, like in this example, like does a beat for 100 times.
03:32 This is important in a lot of different types of code, a lot of monitoring code, a lot of other things.
03:37 Busy waits aren't necessarily always the greatest, but in a lot of cases, it works great.
03:43 The thing that I wanted to point out about this, there's a few things that I love about
03:46 this project or just wanted to point out.
03:48 Really great documentation even for a small project.
03:51 Also, I had forgot about time monotonic.
03:54 This is using time monotonic when it does the time comparisons.
04:00 There's a couple of times of timestamps, types of timestamps, and monotonic,
04:05 and then there's a monotonic nanoseconds.
04:07 If you really want to do really tight loops, you could modify it for that.
04:11 The thing that monotonic does is it makes sure that all time deltas are positive.
04:16 Even if something happens, like you change your system clock between timestamps,
04:25 it'll still do it correctly so that it is monotonically.
04:29 >> That's interesting.
04:31 >> Another thing could be, even you don't change it, but we all have our clocks set to auto.
04:37 >> Yeah.
04:37 >> Adjust, and it could come online and auto adjust or something.
04:40 >> Yeah. That would be weird if suddenly, especially with this project where one of the things it does,
04:48 and he warns about this, is, sleeps aren't exact science.
04:54 This isn't a real-time, especially on non-real-time operating systems, but I don't think Python is even a real-time thing.
05:01 It's an approximation for how long it's going to sleep, but it tries to correct it.
05:06 If you slept too long, it tries to do more events so that on average, you get the average amount of times you're running be correct.
05:16 It's a cool library, check it out.
05:19 A couple of things I wanted to point out about it.
05:22 One is the cool use of monotonic.
05:24 The other one is a good read-me documentation, even for a small thing.
05:28 But there's no tests.
05:31 Brandon, come on.
05:33 Anyway, actually, there's a couple of things around this.
05:37 I don't think that people should stop from putting a code online just because they don't have tests yet.
05:43 It might be that somebody could contribute and add tests.
05:46 It also might be that for you, if you're using this all the time, if Brandon uses this all the time,
05:52 the tests are covered by the calling code.
05:55 You're using this and you're covering it.
05:58 I guess I want to point out to everybody, for any library you're using, you probably should have tests that cover
06:05 the part of the library that you depend on, even if they do have tests.
06:09 This one doesn't, so buyer beware.
06:12 But even if they do, you probably should make sure that it is really working the way you think it's working.
06:17 >> Sometimes it's just hard to have meaningful tests.
06:21 A while ago, I released that Umami Python event library, for the analytics tracking.
06:27 All it does is serialize the messages that come to it from the Umami API.
06:34 I can test what my perception of the API is.
06:37 But the real danger is that that API changes in some way or another.
06:43 It's just 90 percent of the fragility is outside of, if you mock out all that stuff,
06:48 then well, you're just testing your view, which hopefully is already mostly encoded.
06:53 It's not completely useless, but there's certain things that are just tricky to get.
06:57 >> Right. Testing isn't necessarily always automated testing.
07:02 It could be that you're using it, the Umami API that you're using, it's you're using it so you'll know when it breaks.
07:10 Other things are like your use of it will break or the calling code.
07:17 I don't think that people should, especially with the internal stuff, maybe on PyPI, maybe we should have a little bit,
07:22 things eventually should have tests probably.
07:25 But for internal projects where you're sharing code, it's better to package and share code than to not share code.
07:32 If writing testers is what's stopping you from putting it in a central repository,
07:37 don't let that stop you.
07:38 It's better than just, I mean, we have snippets.
07:41 Like he said, it's a glorified snippet, so why not package it?
07:44 >> Yeah. Very nice. I like the monotonic.
07:46 That's news to me.
07:48 I hadn't paid attention to that before.
07:49 >> Yeah. It's cool. I want to try the nanosecond monotonic.
07:53 >> Other stuff that people might want to pay attention to, and this is not to drum up a bunch of fear and concern so much.
08:02 It's not huge news in that regard to people.
08:04 But it's more to just put out there what the PyPA, the Python Packaging Authority folks to deal with.
08:11 Kind of say a thanks.
08:13 The news comes to us from Bleeping Computer, which usually does pretty good news,
08:16 but this article is pretty vacuous of information.
08:20 But the title says a lot.
08:21 PyPI suspends new user registrations to block malware campaign.
08:27 There's some interesting things in here.
08:29 It basically says, look, when was this?
08:32 This is March 28th, a little bit, a couple of weeks ago.
08:35 PyPI temporarily suspended user registration in the creation of new projects to deal with ongoing malware campaign.
08:42 Then it proceeds to tell you what PyPI is basically.
08:46 Then it says, look, there were some problems.
08:49 People are uploading bad stuff, but it doesn't tell you, for example, what projects.
08:53 What did the malware do?
08:56 If you jump over to the status.python.org, actually that tells you about the status of Python infrastructure,
09:04 which is cool. It says same deal.
09:07 This is the official reporting.
09:09 Did it say how long the event went for?
09:12 No, just that it was a thing.
09:14 I guess if I did math, that would be 10 hours, about 10 hours, 30 minutes.
09:19 That's a ways. This is the real article you want to read.
09:23 It is over on Medium PyPI is under attack project creation and user registration.
09:27 It's been adhered to the details by Yehuda Gelb.
09:30 I hate to link to Medium.
09:32 I hate Medium. I think it's a crummy place.
09:35 I don't know, it just seems gross, but they have really good details.
09:38 Basically, this was a typo squatting attack.
09:42 What's interesting, it was a multi-stage attack, stealing all sorts of things,
09:47 crypto wallets, obviously.
09:49 But real sketchy is browser cookies.
09:53 You're logged into your bank for a session that's good for 20 minutes.
09:56 If they could grab that and log in as you, that might be less good or log into your e-mail and reset stuff and so on.
10:03 What happened is there was a bunch of packages in here somewhere.
10:08 There's the package list.
10:09 You can see these are all about capturing people who, one, misspelled things but also just didn't quite understand.
10:18 For example, one of the packages is requirements.txt, requirements.txt without the dot or requirements.
10:25 If you say pip install requirements, without the dash r or the dot txt, you're getting this.
10:32 There's a bunch of others, TensorFlow and Selenium.
10:36 They're all over the requirements business, so it's just everywhere.
10:40 The deal was basically each one of these had a malicious setup.py, which is why I think it's interesting to look at.
10:48 Inside the malicious setup.py, it encrypted using the cryptography.fairnet library,
10:55 which just listed as a dependency, I imagine.
10:58 It then decrypts some URL that it very lightly.
11:04 It's funny, it's like using little analytics.
11:06 It'll passes the query string of which one hacked me before you get going.
11:11 They download some thing that installs and runs and basically installs a backdoor ongoing thing.
11:17 So even if you pip uninstall this, there's this thing running that just monitors your system,
11:22 which is not ideal to be honest.
11:24 >> That's not what you want.
11:26 >> No, one does not want this.
11:28 Henry out in the audience says, "In addition to all the stuff I said, that actually blocked all uploads for a few hours and
11:35 couldn't upload build 1.2.1.
11:38 What a hassle. This is why we can't have nice things. Come on now." >> Yeah. I guess there's a lesson here to make sure that
11:46 you're careful when you pip install something because even if you catch it and you're like,
11:51 "Oh, that's not what I meant," you may have already done damage.
11:54 Isn't there a way, I don't remember off the top of my head, to say pip install but don't run,
11:58 only use wheels, don't allow anything to run?
12:00 >> I don't know.
12:01 >> I'm not sure. I feel like there was.
12:03 Probably some of the audience is going, "Yes, yes, of course.
12:06 How do you not know this?" But that doesn't mean this is not going to happen.
12:10 It just means you have to use the code as opposed to just the act of installing it or sneaking it into a requirements file somehow.
12:18 Yes, and I knew Henry would come through and say, "--only-binary." Indeed, that's it.
12:24 >> Well, they were on top of it.
12:27 The fact that this was completely dealt with within 12 hours is pretty awesome.
12:31 The fact that it has to happen, not so much.
12:33 >> Yeah.
12:34 >> Over to you, Brian.
12:36 >> I guess the world has changed a little bit with UV and other rustified things.
12:45 We have an updated blog post from Hennick, Python Project Local Virtual Env Management Redux.
13:00 He's just really talking about all of the tools that he uses around virtual environments.
13:06 I just enjoyed it because it matches my own use quite a bit.
13:11 Some caveats in here that says this is what works for me.
13:14 I'm not necessarily saying you have to use this, of course.
13:17 But it's a good list of how dealing with virtual environments.
13:24 The major thing that happened is UV, and it's changed a lot of how we deal with it,
13:29 but it makes things a lot faster.
13:31 Some of the things I thought I want to revisit in here, so it's pretty great.
13:37 He's using .venv in each project directory.
13:43 It's close to what I use.
13:44 I use the venv, I just don't use the dot.
13:48 >> I do as well, Brian.
13:50 I know the dot means it's not really important, put it to the side.
13:55 But I love to be able to open up a project in Finder or Explorer and look at it and go,
14:00 "All right, this one has a virtual environment.
14:02 This one doesn't, I need to make one." I don't want to have to keep like show hidden files,
14:07 hide hidden files over and over.
14:09 While I appreciate the dot, I'm 100 percent with you.
14:13 >> Yeah. Direnv, I think I want to revisit this.
14:18 I've tried it a while ago, but I haven't tried it lately.
14:21 Is a way to have an envrc file or .envrc file in your directory, and that gets run when you CD into it or something.
14:35 Anyway, I think this is cool stuff, but I don't use it.
14:39 Do you use this, Michael?
14:40 >> No. I love the idea of it, and in practice, I just haven't done it now.
14:46 >> There's some cool tricks in here that he's using that I want to get back to trying it again.
14:52 I guess thanks, Sanik, for bringing this up so I can take a look again.
14:56 Using Astral's UV over Rai, I never went to Rai, but it looks like he switched from Rai to UV.
15:04 Python installations, now switch to both, just always using python.org downloads
15:10 because they're now universal builds mostly, and it just works.
15:15 That's what I've been using also for installing Python.
15:18 Dead snakes for Linux, of course.
15:21 Then there's a mention of Python build standalone for various other projects that are needed.
15:27 That's neat. A discussion about unpinned versus pinned packages, and then also using a.python version default within a directory.
15:39 The tie-in back to Durenv is cool, is he's got some tricks in here.
15:46 If you drop in a.python version default, it tells you what version to use by default in a directory,
15:57 and then you check it in so that the development environment can be recreated easily,
16:00 and he's got some in VRC that's part of Durenv.
16:04 That is a little snippet that will activate it based on which Python you're using,
16:09 using UV, which is a neat little trick to use Durenv and Python versions and UV altogether.
16:18 I'll definitely have to try that.
16:20 That's a neat trick.
16:21 >> That's neat.
16:22 >> Using all of this as well helps with GitHub Actions.
16:27 He's describing how to do that as input to the setup Python GitHub Action,
16:34 which is, I didn't know you could do this.
16:36 You can say the Python version file and you can just give it that Python version default so
16:42 the GitHub Actions uses the right default version.
16:44 This is cool trick. He's got some tricks on how to use it with the fish shell.
16:51 I don't use fish, but for those fish users, that'd be great.
16:55 The other part that I really enjoyed seeing is because of all of this, in which version and stuff,
17:03 you can use, he's using the requires Python and PyProjectToml, which I'm using for everything now.
17:10 But he has a way, a little sed snippet to parse that out of the PyProject.toml and pass it into using the GitHub Actions,
17:22 the animal file to pass it to a Docker build.
17:25 But it's grabbing this version of Python so you could use it for other things within your GitHub Action or something else,
17:37 or other tool if you needed to pass what Python version to use.
17:41 That's some pretty clever things in here, that I, something old, something new, some neat tricks.
17:47 >> Yeah, very interesting.
17:49 A lot of stuff to explore.
17:51 Interesting comments in the audience about liking and disliking, all the magic, the auto magic.
17:56 >> Well, and it's also another example of, I like these posts, even for different people just to see,
18:02 this is how I work, this is the workflow I use.
18:05 Not necessarily just focusing on one tool, but I use all these things together and this is how they work together.
18:11 It's fun to read.
18:12 >> Yeah, absolutely.
18:13 Even if you don't adopt it, it's cool to just see the tools and the things you can do.
18:17 >> Yeah.
18:18 >> All right. On to the next one.
18:20 This one is super exciting.
18:23 We need to talk for just a second about Cloudflare and Edge Workers.
18:30 Now, this is just a Cloudflare thing, but I think it's sufficiently interesting that it's worth calling out.
18:37 CDNs like Cloudflare, like bunny.net, the one that we use and stuff like that,
18:43 have a bunch of what are called POPs, points of presence.
18:47 Traditionally, these have been, how do I get my files really close to you so they
18:52 feel immediate no matter where you are in the world?
18:55 For example, I don't know about Cloudflare's details like their stats, but I know bunny.net has something like
19:00 115 servers that are points of presence throughout the world.
19:04 So if you visit the Python by itself website, all the static content like images and CSS and stuff
19:11 are delivered from one of those POPs right by you.
19:14 >> Yeah.
19:14 >> Obviously, the MP3s as well.
19:18 Now, those things have started to have programmable models where in addition to just having the content of say a static file near you,
19:28 they'll have some of the logic of the application near you.
19:32 So if you've got like a React front-end that talks to APIs, maybe it's only talking just down the street to the point of presence,
19:38 not halfway around the world to New York where our server lives.
19:41 This has traditionally been JavaScript.
19:44 So with that set as the stage, Cloudflare has these things called, I think they call them web workers.
19:51 Yeah, something like that. We'll see in just a second.
19:54 Those have been traditionally done in JavaScript.
19:57 So there's a whole infrastructure about distributed databases and things like that,
20:01 that these workers can work with. It's pretty interesting.
20:04 But the news is Cloudflare announces, they're bringing Python to these workers with Pyodide and WebAssembly.
20:12 So now you can start to program these edge devices, these points of present things like right near each other with first-class Python support,
20:20 based on all the work of Pyodide and WebAssembly and all those things.
20:25 Isn't that excellent?
20:26 >> It is excellent.
20:27 >> This is a big announcement. I got the Omnivore page pulled up, and the read time is 16 minutes.
20:33 We're not going to go through all that.
20:34 So let me just pull out some highlights here.
20:37 So one of the things that's really made this possible, made interesting is they've put a huge amount of effort into
20:42 optimizing the runtime for JavaScript to make it work well.
20:47 It's Pyodide's integration with JavaScript for that runtime performance implementation side to make this work really well.
20:58 So it says, "Beyond just compile to WebAssembly." Each worker is what's called a V8 isolate.
21:06 So it's like a container, but just less, just an isolated version of the V8 runtime,
21:13 which is the Chrome's JavaScript engine that also runs WebAssembly.
21:17 So it says, "It's not just as easy as copying over the WebAssembly stuff and running it because they have
21:22 thousands of these things running on one server.
21:25 If each one had to do full-on startup for WebAssembly, full-on startup for Pyodide,
21:30 which is six megs and takes some delay to get going and so on, it wouldn't be practical.
21:36 So they've done all this work to memory snapshot an almost running pip installed setup version of this,
21:44 and then deliver it to you upon request.
21:47 So there's a lot of shared memory or shared processing.
21:50 Here's how you write it, Ryan.
21:51 From JavaScript, import response, async def on fetch, then do your Python and return some response.
21:58 >> Cool.
21:59 >> Let's see. There's a cool graph that compares what's VMs versus containers,
22:04 versus these isolate things.
22:06 Like I said, it's a lot more put together.
22:10 One of the things that's pretty interesting here is it has support for FastAPI and LingChain.
22:17 So there's a bunch, like I said, this is really long, but let's look at the FastAPI version here.
22:23 There's a whole example, I'll point people at, of code, Python worker examples, and Cloudflare's GitHub repo.
22:30 So if you go to the FastAPI one here, and you go to the source, and you pull up the worker,
22:35 and you hide the symbol so we can all see.
22:37 Basically, check this out.
22:38 So this is Python code running effectively in a node style like thing, in WebAssembly on the edge of one of these workers.
22:47 Here's what you write. From FastAPI, import FastAPI and request from Pydantic import base model,
22:53 use app equals FastAPI, app.get.
22:55 Here's your document you return.
22:58 Here's your async function that you write, you can go do async things.
23:01 Here's your Pydantic model with Python types.
23:04 What do you think? Here's your post, your puts, your gets.
23:06 >> This is pretty cool.
23:08 >> Yeah, and they've got some database thing that it integrates with so you can have persistent data and so on.
23:14 But like I said, I don't do a ton with these things, but I might start paying attention if I can do it in Python.
23:19 >> Yeah, definitely. Yeah.
23:21 Yeah, back in my day, a V8 isolate was just carrots.
23:24 >> Exactly. It's the part that sinks to the bottom and then you take it out, right?
23:30 >> No. If people use Cloudflare already and those are workers, this is super interesting.
23:36 If you just want to see some cool unique uses, and I guess in a way, one of the real first production uses of
23:43 PyOdied and Python in WebAssembly.
23:46 >> Yeah.
23:46 >> Check this out.
23:47 >> Definitely.
23:48 >> All right. That's all of our main topics, right?
23:50 >> That is.
23:52 >> All right. How extra are you feeling today?
23:54 >> I have zero extras.
23:56 >> Zero?
23:57 >> Zero extras. Just a better job later.
23:59 >> All right. Well, I got a couple.
24:00 I'll go through quickly here for us.
24:02 First of all, Brian Skin sent both of us a message and said, "Look, there's a decent chance the podcast audience
24:08 has already filled you in on this.
24:10 But last week since I talked about LPython and the related projects are spearheaded by Andre Sertic."
24:17 Brian, you are, Brian Skin, you are the podcast audience who has filled us in. Thank you.
24:23 Actually, Brian did a whole hour-long interview with him on it.
24:28 So if people want to check out LPython further, which we talked about before, check that out. That's pretty cool.
24:33 Next, I really like this idea.
24:35 We talked about JustPath last time.
24:38 >> Yeah.
24:39 >> How it helped you diagnose your path, like duplicates, missing directories, all that kind of stuff.
24:44 Listen to last week if you want the whole details.
24:46 But the guy behind it said, "Hey, that was really awesome. You covered it.
24:51 I'm going to create a badge, a Python bytes GitHub badge for the project."
24:56 What do you think about that, Brian?
24:57 >> I think that's really cool.
24:59 >> I do too. So I'm going to try to set it up so that there's an automatic GitHub badge that people can put on their readme,
25:07 if their project was featured in Python bytes, and I'll put that at the top,
25:11 put the code you can get for that or something at the top of the show on the episode page.
25:15 It's not there yet, but eventually, you should be able to get a cool little badge like this that says,
25:20 "My project was featured on the podcast on this episode," and here's a link to it all within one badge.
25:24 >> The badge has the number shows what episode it was on.
25:30 >> Yeah, exactly. Instead of saying Python 3.12, it says Python bytes and the episode number. It's excellent.
25:35 >> Yeah, that's pretty cool.
25:38 >> Thanks for that. I am as well. Let's see what else.
25:43 Brian, we have a brand new server going strong now. Did you see?
25:48 >> I did. That's pretty exciting. Was that a lot of work?
25:50 >> Yes. It was a lot of stress, not a lot of work.
25:54 So I decided it's time to upgrade the server, get some more RAM.
25:58 More CPUs is always nice, but I couldn't reasonably get more RAM without more CPU,
26:02 so I'll just take them.
26:03 So we had some downtime for about 20 minutes actually last night.
26:09 So if you ran into that, I apologize. That took out everything because this
26:13 was not one of the Docker pieces out of the Docker.
26:16 This was the host of all the Docker clusters.
26:18 So it was gone.
26:20 I couldn't even reasonably put up a word down page because it was the host thing that was down,
26:26 not part of the site.
26:27 Anyway, now, I don't know where the reply went.
26:33 If I'm not logged in, it doesn't show me.
26:35 But we now have a sweet machine running along just like before.
26:40 So that worked out pretty well.
26:41 Before that, I was so happy, Brian.
26:43 We had for the last 30 days running a 99.98 percent global uptime.
26:50 That was awesome.
26:51 >> That is pretty great.
26:52 >> I know turning off the server for 20 minutes.
26:56 With 20 gigs of database records, it takes a while to copy that from one VM to another.
27:03 So that's what took so long.
27:05 >> It's only three nines though.
27:06 You need to work on that.
27:08 >> Well, it's three nines and then an eight on the end.
27:11 It's almost four nines. It's so close.
27:13 I'm going to try to make it better now.
27:15 But it went down to I think 99.94 percent, which I think is still pretty darn good
27:22 for some random dude in Oregon running a server.
27:25 >> That's pretty awesome.
27:26 Python test went down last week for 12 hours or something like that.
27:31 >> Oh, no. Was that something that had nothing to do with you, just the host of it or something?
27:35 >> It had something to do with me, but it was a DNS thing.
27:39 The DNS glitch, it was an accounting thing on my part.
27:47 When it got repaired, they didn't repair all the DNS records.
27:52 So I had to go recreate all the DNS records.
27:54 >> What a hassle.
27:55 >> Yeah.
27:55 >> Yeah, it's a huge hassle. All right.
27:57 >> Cool.
27:58 >> But before we go on for a joke, Henry out there on his points, what about rich and textual?
28:04 They'll just be overrun with these badges.
28:07 >> Yeah.
28:08 >> These Python bytes badges.
28:11 >> We'll have to do an infinity symbol for those projects.
28:14 >> Exactly. Maybe some sequence like this 100 dot dot dot 400.
28:21 >> Yeah.
28:22 >> Something like that.
28:22 >> Also, backing up a little bit, the Edge workers from Andrew Bayer, Pyedide works in Web Workers now too,
28:33 which is totally different thing, but also cool.
28:35 That is very cool.
28:36 >> Awesome. Okay, that is very cool. Thanks, Andrew.
28:38 I think Web Workers are basically like background threads on your web app,
28:42 which I think there used to be troubles with that as well.
28:46 All right. This one, I thought of you when I got this joke, right?
28:49 >> Okay.
28:50 >> This makes us a little AI, a little bit of C++, the graphic is crummy,
28:56 so it's hard to read. But Gemini, the Google AI, this person says, Gemini is apparently told your Google account age,
29:06 and will answer questions with the appropriate caution.
29:10 If you're like a minor, you're like 12-year-old kid with a Gmail account,
29:16 you don't want this thing to just tell you all the secrets of life, like, "Hey kid, Santa Claus is fake."
29:22 No. All right.
29:23 But here it is, in fact, talking about something else.
29:26 It says, "Here is Gemini refusing to help someone with C++ because they're under 18
29:32 and advanced C++ is a danger to a young mind." Are you ready?
29:37 >> Yeah.
29:38 >> The person just says, "I have a function inline bool is key down standard namespace,
29:43 same as template of key auto dot dot dot keys." It's pretty intense code, right?
29:50 It says, Gemini says, "I'd be glad to help you with that C++ code conversion,
29:55 but I'll need to refrain from providing code examples or solutions that directly involve concepts.
30:01 As you're under 18, concepts are an advanced feature of C++ that introduce
30:06 potential risks and I want to prioritize your safety.
30:10 Here are some alternative approaches you could consider depending on your specific requirements,
30:14 traditional variadic templates and so on." >> Because you're under age, I'm going to focus on traditional variadic templates?
30:24 >> You're good. What do you think?
30:29 Is that a good one or what?
30:30 >> Yeah, that'll scare them away from C++.
30:32 >> I'll go back to Python.
30:34 >> Yeah, nice.
30:35 >> All right.
30:36 >> Okay. I've got a quick baseball joke.
30:39 So we're just deep into baseball season now.
30:44 If you take a trip to see a baseball game, what is that called?
30:48 It's an inning outing.
30:50 >> An inning outing. I love it.
30:53 >> That joke.
30:54 >> I love it. Yeah, we have no baseball.
30:57 We've got to dive to all of our professional sports, besides soccer and basketball.
31:02 >> So it's been a while. It's been a while since I've been to a game.
31:05 >> It's been a long time since I've been to a game.
31:07 >> It's been a long time since I've been on an inning outing.
31:09 >> An inning outing. Yeah, and yet I still find T-shirts.
31:13 You can get T-shirts other places.
31:15 >> Yeah. T-shirts, they persist for sure.
31:17 That and conference T-shirts.
31:19 >> Yeah.
31:20 >> All right. Well, thanks as always.
31:22 >> Thank you.
31:22 >> See you later.