Hello and welcome to Python Bytes, where we deliver Python news and headlines directly to your butts.
This is episode 122, recorded March 20th, 2019. I'm Michael Kennedy.
And I'm Brian Okken.
And this episode is brought to you by DigitalOcean. They have some big news to share with you. I'll
tell you all about that shortly. Check them out at pythonbytes.fm/digitalocean and get a
$100 credit for new users. So tell you more about that later. Brian, how are you doing?
I'm doing good. And if I chuckle, it's because you got your mic up and you kind of look like a
rapper doing the thing. Yeah, I'm going to drop it at the end of this episode.
Yeah. Anyway, no, people can't see. Yeah. Like, so I've got my microphone on a different stand. So
we'll see how it sounds. But yeah, I think it's working. All right. Yeah. Nice. All right. So
I find dictionaries sometimes get used in Python, like every now and then people will like make you
so that's fancy data structure. Yeah, definitely. One of the hard things,
and I don't have a link to this. Maybe we could drop it. But one of the things you need to do with
dictionaries is pull them apart and put them together and stuff. There's a PEP 584. It's
had the plus and minus operators to the built in dict class. Yeah, that makes a lot of sense to me. I
mean, we already have it for list. Well, not the minus, but we have the plus list makes sense because
it operators are neat. And the thing that throws me off is the massive difference between if you do
dictionary one plus dictionary two, it's different than dictionary two plus dictionary one,
because the second thing always wins. Right. If there's duplicate keys, the second one,
it's going to overwrite the first one. So you're saying that addition might not be
commutative. That might be a problem.
Well, maybe, but I mean, like strings are like that. Like if you've got, I don't know, do we do?
That's true. You don't get the same result of like hello plus world or world plus hello.
Yeah, exactly. So maybe it's okay. We'll link into the pep. Actually, I think it's nice because
if you look at the alternates, the alternates are gross. Like you can unpack both dictionaries and
then create a new dictionary or you can copy one and then update it with the other that all of those
are not obvious. And, and so I think plus would be good. So we're going to link to that article,
but also Guido Van Rossum wrote an article called why operators are useful that partly talks about
this. And then also there's an email link of why apparently one of the options for combining
dictionaries was to use the pipe operator instead of plus. And so I've got a link to that too, but
actually, so this is just a, we don't know if it'll go in, it's in draft status and it just got
proposed, but I think this is a, would be a neat thing to add to Python.
Yeah. I'm honestly a little bit surprised. It's not already there. it would be nice.
I certainly prefer plus over pipe. Like pipe is not something that's commonly used in Python for
combined stuff. Maybe if this was C or something, I don't know, but, it's certainly in the Python
world plus seems like a more natural choice here. So this next one comes from Matthew Rockland,
a guy behind ask and other data sciencey things. I recently interviewed him on talk Python, but you
know, time shifting, it will be in the future when that comes out. But I was,
reading through some of his articles and found something I thought, you know, well,
at least it's super resonated with me. I don't know how your world is Brian, but mine is like a
constant stream of like inbound inquiries, requests, comments, like watch the talk Python
Twitter account at my personal Twitter account. We share watching the Python bytes Twitter account.
I have a getter channel. I'm on a couple of slacks. I'm on like Cisco teams or something like this.
Email is insane. And there's just too many places that stuff comes at me. And I spend like,
there's times where I'll take a week and I'll take a full two days off to just write email and respond
to messages. And I'm still not all the way caught up. It's like, it's really a problem.
So when I read this article called why I avoid Slack by Matthew Rocklin, I'm like, Oh, yes,
this definitely resonates with me. Because when you get that much inbound stuff, like anything that's
transient is super hard to keep track of, right? Like at mentions on Twitter, like maybe I'll catch
them. But if I don't, like, I'm sorry, but I just, you know, it's I'd lost it. It went by in the stream
somehow on accident, or something on Slack, right? Like it's 100 messages back. And you know, I dropped
in there, I didn't check it, marked messages red and left. And now it's just gone, right? It's never
going to come back. So I feel like those kinds of things, while kind of fun and interesting and more
lively are also, you know, just adding stress and not not really positive. So Matthew wrote this cool
article said, saying why avoid Slack focused on for open source maintainers of projects,
right? Like, should we have a Slack channel for open source project? He says, no. So he says,
instead of doing something like that, I mean, I guess a Gitter channel would be basically equivalent.
So as I encourage colleagues to have technical and design conversations on GitHub or some other system
that is public, permanent, searchable and cross referenceable. What do you think?
Actually, especially for that case of open source projects, and, and those types of conversations,
I think I totally agree.
Yeah. So he says, you know, a couple reasons why, like, say, GitHub, public GitHub repos and their
issues and their conversations and PRs and whatnot around it are better than Slack would be because
you can engage collaborators who aren't on Slack, right? Not everyone is on Slack. But if you're working
with a person who doesn't have a web browser, that's probably okay, you can ignore that person.
But most people can get to the web and they can read, or even Google search and then find some kind
of thing. Also, you can record the conversation, because it sounds like his life's a little bit
like mine, like, hey, everybody just needs a couple of minutes of your time, every couple minutes,
you know, and it completely derails any form of productivity.
Yeah, so it's super hard. And the reason is, they'll drop in a Slack channel or some other
conversation and go, hey, why is it like this? Or just quick question about that. And it's like,
if you have it in an issue and discussed or something, you can say, that's issue 17725.
We talked about it for a week. Here's a whole detail, right? Also, you can serve the silent
majority. That is people who go to Google, and they type in a thing and say, I need help with this
thing. Or why does this work that way? GitHub ranks super high on Google. And those issues
often come up and you can see the whole conversation.
Oh, that's a great idea.
Yeah, the other one is encourage more thoughtful discourse. So if you're writing like one on one
or a couple of people on a Slack channel, you're willing to just throw out kind of quick,
off the cuff comments. If you're writing in a public permanent forum that's associated with
your GitHub profile, it's much more likely that you're going to write something thoughtful. And
finally, you get a cross reference issues. So you can say we talked about part of it here and part of
it over there and this other issue. And then there was this PR and then we're bringing it back here.
Slack is siloed. You can't cross reference people and conversations and things like that. So here's a
call to say enjoy Slack, chat in Slack, but don't use Slack for design decisions and other stuff,
right? Like maintainers come and go. Maybe you want to have a history of these things and not just a
transient chat stream.
Yeah. And the bigger a Slack channel gets, the more useful it is in some respects. You get answers
really quickly. But also the more it reflects like kind of just a topical party at somebody's house
with lots of conversations going on.
Right. There was a cool chat about this thing on the couch, but that doesn't, that's not the same as
like we wrote up our thoughts on that thing.
Yeah, exactly. I'll have to read this.
Yeah, it's pretty good. It's not much longer than actually what I talked about, but it's still
really helpful, I think.
Yeah.
What's the next one you got for us?
That reminds me, actually. No, I had a leak in my memory. No, that's bad.
That's pretty good, actually. It's so bad it's good. I like it.
There's an article from Zendesk from YQO that's called Hunting for Memory Leaks in Python
and we've covered memory leak stuff before, but I really like this write-up. And it's specifically,
they've got, Zendesk has a bunch of machine learning in Python written. And one of the problems they run
into is some of them will have really big memory spikes or memory leaks, and they want to try to
figure that out. So this was a specific use case. So he's not covering all of the options, just some of
the tools that were used there. And I think it's cool. I didn't know some of these things were around.
So there's a, for example, there's a combination of the memory profiler package with matplotlib
where you can easily run, without doing anything to your code, you can run some Python code and then
get a visual graph of the memory utilization, which was cool. If you're hunting into stuff and trying to
break things around, there was a discussion of using, adding some code to your code to use,
it looks like Muppi, M-U-P-P-I.
Yeah, Muppi.
That will dump, heap dump in certain places. So if you, if you think, sometimes time really doesn't
help you too much, but you can add certain places where you think you're at a stable state,
doing a heap dump, especially if it's somewhere, something that's looping, you might be able to
catch something there. A reference to object graph or object graph to profile memory object lineage.
So objects that create other objects.
Yeah, that can be tricky because you've got, maybe you have some object, it's a class and it's got some
field, that field, it's a list. In that list, it has a bunch of objects. One of those happens to hold on
to a pointer to some other huge dictionary that you thought like should be gone, but right, there's still
some reference keeping it alive, right? So this object graph will like tell you that basically.
Yeah. Nice.
Like for example, when he dumped some of the heap dumps, some of those examples,
it's just that you've got like so many megabytes towards strings. Well, I don't know if that really
helps you too much. Having a, finding out where it came from might be helpful.
Yep.
And then he ends the article with a, with a bunch of tips, do quick feedback. If you think something,
one of the things I liked, which is probably really good is if you have a memory intensive tasks
or something you think might be the problem, separate that into a separate process so you
can debug it separately. The Python built-in PDB has a bunch of stuff that can help you as
well. And then also watch out for leaky packages because the leak might not be in yours. It might
be in your dependencies.
Yeah. You might've pip installed a memory leak for sure.
Which I was surprised that he said, for example, pandas. And I'm like, really? Pandas is like,
must be tested the heck out of it. But apparently there's some known pandas problems in some corner
cases, but oh well.
Yeah. It probably is kind of tricky with like the C layer holding onto PI object references and all
sorts of funkiness. Right.
My first reaction to dealing with memory in Python is like, well, we're not supposed to have to,
so it must be a real pain in the rear. But these tools don't look that bad to work with if you need
to.
This object graph looks really cool. And it will actually create a PNG visual graph of the
relationships, which is cool. And you can even ask for back references. Like it seems like this is the
thing that has all the memory. It should be gone, but why is it not garbage collected or cleaned up?
And you can say, draw me a graph or not a, like a mathematical graph, not a parabola type graph,
a graph theory graph of all the back references to this object, which is pretty cool.
Oh, nice.
Yeah. So you can ask it in both directions.
Yeah. Right. If you think it should have been deleted and it's not, it's because somebody's
still referencing it.
Right. So who is that? Tell me about that. I need to know about that right now.
Yeah.
Yeah. That looks really cool. It's definitely something I'd like to explore. Actually,
let me rephrase that. I don't want to explore it. I don't want to have memory leaks,
but if I do, I will find it very useful.
Yes, definitely.
There you go. Also useful, DigitalOcean. Let me tell you a cool thing that they just released.
And this came from one of the listeners. They sent me a message like, Hey, this looks really
cool. Do you know about this? So they announced this thing called the DigitalOcean Marketplace.
So the idea is that different companies and other people can create these pre-configured
virtual machines. And then you can just do one click app, install them. Like if you want a ghost
ghost blog server configured with Nginx and all that, you just click ghost blog server,
pay your $5 and now you have one.
Nice.
Or maybe you want like GitLab Enterprise, a MongoDB server, or even you can say, I want a Django server. And it'll give you Django,
Nginx, G Unicorn, Postgres, CertBot, a whole bunch of stuff pre-configured all to work together like in a few seconds.
That's pretty cool, right?
Yeah, definitely.
Yeah, yeah. So I think this is a really nice feature. You know, it's already great to run
infrastructure there. And now if you can like get it much closer to the end, it's a little bit,
I'm sure it's a Docker inspired, right? It seems like that, but for their infrastructure.
You still have to figure all that stuff out and to be able to throw a few dollars to the people
who are willing to do the work to put it together. That's great.
Yeah, it's beautiful.
All right. So check them out over at pythonbytes.fm/DigitalOcean, create an account. And then once you
get into your account, there's a little marketplace tab over there. So super cool. So speaking of Docker
and all these other things, there's a cool article by Craig Kirstens, and it's called Give Me My Monolith
Back, or Give Me Back My Monolith, as opposed to a whole bunch of microservices, right? So there's
been a lot of hype, excitement, I don't know, take your, choose your side of the fence around microservices.
And this is the idea of like, yeah, you have a web app, and it's got like 500 Python files,
and maybe it's doing all these different things. And wouldn't it be better if we could take the credit
card processing and make it its own service with its own database? If we could make the caching its own
service, its user accounts, its own service, all that kind of stuff. And then that user account part is
super simple, right? Because the whole purpose of this application is, who are you? What can you do?
Can you log in? Can you reset your password? Or something like this, right?
This seems good, yeah? Yeah. There's a lot of really good uses for this. Like,
if you have a large team of people working on a large web app, it might make more sense to break
into these small pieces and have some people in charge of each piece. I think that actually
legitimately makes a lot of sense. It's easy to bring on a junior developer who can say,
all right, I'm going to work on this caching bit or whatever. And I don't have to know the whole
thing. I just got to work on my little API. It does court, async or whatever it does.
That makes a lot of sense. But most people who are working on web apps aren't in that space of having
like 30 people on their team, right? That's really rare, right? You've gone down this rant of you're
not Google, you're not Facebook, you're not LinkedIn, right? You don't need all these patterns because you
are not them. You're a little relatively smaller company or project. Anyway, this guy feels like,
you know, that adds a lot of complexity and challenges. And he lays them out of like,
why does the world have to be so hard? Wasn't it easy before? And now it's not,
not from the article, but just a thought of mine. Like when I think of this microservice architecture,
what you're doing is you're taking code complexity, and you're moving it to infrastructure complexity.
Yeah, definitely.
Instead of having one kind of complicated bit of code, I now have 12 super simple bits of code,
but they all have to work together in like fairly complicated network environments, failover,
you know, all this kind of stuff, this topography and whatnot. So my thought is at least, you know,
like, well, which of those two things are you good at? Infrastructure or code? You know,
that drives a lot of these decisions. But he runs down a couple of things that he said
used to be simple, but now we get to revisit them, get to. So setup went from like chemistry to quantum
mechanics. A lot of this has to do with bringing new people onto a team or junior developers and things
like that. So it says, onboarding a new engineer, at least for the initial environment used to be like
half a day. And now we've ventured into microservices, this onboarding time is skyrocketed,
and it's super complicated for them to understand all the moving pieces. And then the next one,
is so long for understanding our systems. You know, back when we had monolithic apps,
you had an error, it had a stack trace, you click on the hyperlink generated by your little
editor to take you to the line where the stack trace is. And now you have different services that
talk to another service that cue something on a message bus that another service pulls it out,
and then you get an error. What caused that? Right? How do you try? How do you follow that through?
How do you debug that? So it says, well, if we can't debug them, maybe we can test them talks
about the challenges of continuous integration, and whatnot, but also talks about some services
that were made into some apps that were made into microservice that are now moving back,
sort of in a reverse migration to these monoliths. And, you know, I got to say, I'm pretty sympathetic
with this. Like I, I see the value of microservices, but I also know that I'm not Google.
Right? And so, yeah, anyway, for me, I don't think this whole microservice world makes as much
sense in my space, but I don't know. What do you think?
We should go back to HTML and Perl.
That's right. Can't we just have static files? All this like logic is bust in your brain.
CGI used to be easy. No.
No, it actually was never, ever easy.
I think that there's different ways to solve problems. And I think that making sure that
you're paying attention to it, I think is a good, good idea. And make sure that people understand
that microservices are a, are sometimes it's a funny, funny, it's a shiny new thing to go learn. And,
and sometimes that's not bad if you're willing to take on the risks, but, but it is a changing
from what you know to what you don't know is a risk.
So it's definitely exciting. I mean, you can bring in Docker and Kubernetes and do all sorts of fun stuff,
but at the same time, just be aware of the trade-offs you're making.
Some of the things that it's solved are now solved by Async.
Yeah, that's true. Absolutely.
One of the things also is if you're in a single language or not. So one of the things that
microservices gives you is the different teams can do whatever language they want, as long as they
provide an interface that's compatible with everybody.
The authentication bits in Node.js, the, the caching tiers and something else. And you know,
the front ends in Python or whatever.
Yeah, definitely.
Yeah. Makes sense. Again, it's not something you will do that often when you're just a couple of people,
but if you're a big team or set of teams, then sure.
Makes a lot of sense.
Yeah.
All right. So I know of some famous laws and rules in software development, like the solid principles,
single responsibility principle, open, close principle. These are all good. You found some more
amusing ones, didn't you?
Yeah. Some of them are serious and some are amusing. All of them have kind of a little bit of truth.
And this is an older article, so I'm not really sure how I got a hold of it, but it's the famous laws of software development.
And there are 13 listed. I think I counted that many. I'm not going to read all 13. I guess it was written in 2017. It's not that old.
But okay, so Hofstetter's law, which is great. It always takes longer than you expect, even when you take into account Hofstetter's law. So it's self-referencing.
I love it. Yeah, I love it. There's some many good ones here.
So that's just funny. There's Conway's law, which it's not supposed to be funny, but it's sometimes depressing. Any piece of software reflects the organizational structure that produced it.
Yeah, I think that's true.
Like microservices are great for lots of teams. One team, one monolith or something. I don't know. But I've seen that before. Also, the hierarchy of different teams shows up in the software as well. And then, of course, a couple more I'd like to point out. The peer principle. In any hierarchy, every employee tends to rise to his level of incompetence.
Sounds like a quote from the despair, Inc. calendars or posters. That's great.
Yeah. And then the 90-90 rule, which I haven't actually heard before, but it's just hilarious. Have you heard this before?
No.
The first 90% of the code takes 10% of the time. The remaining 10% takes the other 90% of the time.
That sounds about right to me. Yeah, it's definitely, it feels like things just drag on and on right at the end of these projects.
So, the comments are good too. I noticed that some people, a guy named Corey threw in a thing and said, I'm shocked that Cunningham's Law isn't on the list. Cunningham's Law. The fastest way to get help over the internet is not to ask a question, but instead to answer it wrong.
And then someone also responds, maybe its omission was a conscious choice to invoke it.
That's awesome.
Yeah, it's really good. There's a bunch of nice ones in there.
Yeah, that's like real though. I mean, the best way to get people to help you on the internet is to start blogging the wrong stuff.
Yeah, enable comments and start writing. That's cool.
I got a quick one to round it out here. We talked about a plugin architecture before for building plugins that ran like within your app.
So, basically, ways to let people interface like simple bits of code into your other systems and version plugins and all that.
There's another one called beer garden plugins, which is pretty fun.
One of the listeners suggested this.
So, the idea is it's a framework that will convert your functions.
These are like regular Python scripts.
They don't know anything about the web or plugins or whatever.
Convert those into composable, discoverable, production-ready services, as in RESTful HTTP services with minimal overhead.
So, if you have a class, you can just go say this is a system and then the functions on the class, you go these are services and they take these parameters and you describe what they take, things like that.
And it will just go serve that.
And it even does cool stuff like it does swagger documentation of the services and whatnot.
So, yeah, it's a pretty interesting little quick way to convert code that was not meant to be a service into services.
Oh, very cool.
Yeah.
It's pretty cool.
It's apparently based on MongoDB, RabbitMQ, and it supports modern Python.
So, that's pretty cool.
It talks about what you have to do to get it running.
Or, something that's kind of nice, is it also comes in a Docker and Docker Compose form.
So, you can just clone the Docker Compose bit from GitHub and then you say Docker Compose up and now it's up and running.
And then you can give it these little apps and whatnot.
It's pretty cool.
Nice.
Yeah.
So, I think the idea is you run your code and it plugs into the server there.
So, yeah.
Anyway, it's pretty neat.
People can check that out if that sounds like something they're looking for.
All right.
Well, that's it for official items.
Anything else you want to cover here at the end?
Just had a really cool interview the other day.
This will go out as Test Encode 69, which should be available for everybody before you listen to this.
But it was with Andy Hunt, who is now at the head of Pragmatic Programmer.
I mean...
Yeah.
He's one of the original founders of it, right?
Him and one other guy, I think.
Yeah.
Is that right?
Andy Hunt and Dave Thomas wrote the Pragmatic Programmer.
And that was released in 99.
And then in 2003, they formed their own publishing company.
And they've been going strong.
And the pytest book was under their publishing company.
And so now Dave doesn't play an active role in the publishing anymore, but Andy does.
And so it's a really cool conversation.
Andy was also one of the original signers of the Agile Manifesto.
And so we talk a lot about...
Oh, right.
That's cool.
Yeah.
We talk a lot about that and quite a few other things.
So that's a fun thing to listen to.
Excellent.
I'm definitely going to check it out when you release it.
That's a good one.
How about you?
So I have two quick things to share with you.
First, there's this thing called Firefox Send.
Have you heard of this?
I have not.
Yeah.
So Firefox Send is actually not something built into Firefox, but it's more like a Mozilla
project to make the web better, right?
So here's what it does is it lets you share files securely, large files, like up to two and
a half gigs per file.
And it does end to end encryption, where the decryption key is actually stored in the
URL.
So if you don't share the URL, like even the Firefox Send people can't decrypt it or whatever.
Okay.
Interesting.
So basically, it's a way to serve these files around like without putting it into Dropbox
or OneDrive or Google Drive or whatever, where it's like permanently there, it's going to be
backed up.
It's, you know, who knows like if you would ever truly delete that thing, right?
Whereas here, the maximum life of one of these files is seven days.
And you can even say it can only be downloaded one time and delete it in an hour or something
like that.
And of course, the encryption key is not stored with the Firefox folks.
So like if it gets lost, you know, it's not that big of a deal.
Interesting.
I'll have to check that out.
Yeah.
It's a free, quick little thing.
You can either sign in and have a larger, larger file options or smaller ones if you want to
say and stay anonymous.
But yeah, definitely, I think it fills a cool need.
And it's kind of nice to see Mozilla just, you know, making the web better in that way.
And it's, it doesn't depend on Firefox.
It just happens to be made by them.
Okay.
Nice.
Speaking of making stuff better, do you know what I really hate?
I hate going to weather.com and I'm saying, oh, it looks like you're running an ad blocker.
We want to serve you crap ads from an ad network and that may have malicious content and
JavaScript in it.
So please whitelist us.
And every time I see that, I think if you, and these are not small little blogs or like
little article sites.
These are CNN, the weather channel, like major, major places.
Right.
And I always think, you know, look, if you want to serve ads to me, why don't you do it on
a system that is not broken on a way that will not put my computer and my information and everything
else at risk?
You could easily talk to your sponsors, put an image on your site, let people click on
it and it takes them to their offer.
But no, they want to run, you know, all sorts of retargeting and tracking.
And they want to figure out like, oh, are you, you are, are you a woman who is 36, who is
also search for this, right?
Like it's really shady.
So this is not a change for us, but this is more of a make it explicit for us on pythonbytes.fm
and also talk python.fm.
We don't pop up these.
Hey, it looks like you're running an ad blocker.
Please stop it.
Because our ads still show when there's an ad blocker, because all they are is images.
We're not trying to retarget anyone.
Isn't that cool?
That is very cool.
Yeah.
So there's this move I've seen on the internet to talk, just sort of a pushback on that to
say, no, these are ethical ads.
You know, you see this on read the docs and other places.
So I put a little note under our ad saying, these ads are served ethically.
We don't track you.
We don't retarget you.
We don't do anything.
But here's our sponsor.
If you like it, if you like the product, you want to support us, click on it.
And that will, that will, they'll know that you came from us because of the URL.
And that's all you need, right?
So I really wish all these places that say, please whitelist us instead said, could we
have a better business model where we don't have to track people and do all sorts of nefarious
stuff?
So we're opting out.
Good job.
Yeah.
Thanks.
All right.
Well, I believe it's time to laugh a little bit.
Yeah.
All right.
Go first.
I really like this joke that Derek Chambers submitted.
It is, what do you call it when a Python programmer refuses to implement custom objects?
What's that?
I don't know.
Self-deprivation.
And then he adds, sorry, that joke was really classless.
Yeah, that's pretty good.
I love it.
The classless, classless Python.
Cool.
So I have another one for you.
And I'm, I pretty much have an infinite supply of these now that I've pip X installed PyJokes.
Okay.
So I ran this before our episode and this one came up, said, I had a problem.
So I thought I'd use Java.
Now I have a problem factory.
I love it.
Anyway, that's, that's the jokes.
And if you, if you find yourself wanting more jokes between now and the next episode release,
you can always pip X install PyJokes and, you know, get your fix on the command line.
Yeah.
Oh, here's one more.
Okay.
I just ran it.
I got to do this one also.
There's only two hard problems in computer science.
Cash invalidation, naming things and off by one errors.
Nice.
Yeah.
There's good jokes in that PyJokes set.
I love it.
Yeah.
There's not an infinite number.
So people still keep sending us jokes.
We love them.
Yeah.
We're going to hit the limit eventually.
It's got to happen, but definitely fun.
So thank you for sending that in Derek and Brian.
Thanks for doing this with me as every week.
Yep.
Thank you.
You bet.
Talk to you later.
Thank you for listening to Python Bytes.
Follow the show on Twitter via at Python Bytes.
That's Python Bytes as in B-Y-T-E-S.
And get the full show notes at pythonbytes.fm.
If you have a news item you want featured, just visit pythonbytes.fm and send it our way.
We're always on the lookout for sharing something cool.
On behalf of myself and Brian Okken, this is Michael Kennedy.
Thank you for listening and sharing this podcast with your friends and colleagues.