1
00:00:12,502 --> 00:00:17,360
>> Hello, welcome back to Curlyboi 
Theatre for our last talk of the day.  

2
00:00:18,320 --> 00:00:23,840
Um, because this is our last talk of the 
day, please remember that the conference  

3
00:00:23,840 --> 00:00:28,000
closing will be in this room, where we 
are right now, after this talk. They'll  

4
00:00:28,000 --> 00:00:35,760
be a very short break in between, stick around 
to hear from our lovely conference organizers. 

5
00:00:36,720 --> 00:00:45,840
Okay. So, we have, for us all today, Sebastian 
Witowski to talk about Python Versions and  

6
00:00:45,840 --> 00:00:52,960
Dependencies Made Easy, if I get the title 
correct. Sebastian is a consultant in Poland.  

7
00:00:56,960 --> 00:01:02,560
He fell in love with Python and teaching and 
is helping companies untangle their complicated  

8
00:01:02,560 --> 00:01:07,680
architecture and build all sorts of interesting 
Python projects. So, if there is time at the end,  

9
00:01:07,680 --> 00:01:14,000
Sebastian will be taking questions so please put 
your questions in the question tab in Venueless.  

10
00:01:14,000 --> 00:01:19,120
You should all know where it is by now, 
hopefully, if not, ask away. And I'll ask  

11
00:01:19,120 --> 00:01:24,560
Sebastian at the end. Over to you, Sebastian.
SEBASTIAN WITOWSKI: Cool. Thank you so much. Hi,  

12
00:01:24,560 --> 00:01:36,560
everyone. My name is Sebastian Witowski. I join 
different teams and work on different projects.  

13
00:01:37,280 --> 00:01:42,800
And as I work on those different projects, I 
notice they often suffer from one of two problems.  

14
00:01:43,920 --> 00:01:51,680
They're overengineered or stacked in the 90s. 
The overengineered ones involve jumping on every  

15
00:01:51,680 --> 00:01:55,200
shiny, new tool that you find 
on the first page of Hacker News  

16
00:01:56,080 --> 00:02:02,000
and then everyone gets excited because it's fun to 
work with something brand new. What is not fun is  

17
00:02:02,000 --> 00:02:08,640
when your tool gets deprecated. Maybe the creator 
gets bored and stops working on it. You have to  

18
00:02:10,000 --> 00:02:21,360
keep it up to date yourself or do it yourself.
Some people think because it was fun to manage  

19
00:02:21,360 --> 00:02:33,520
everything using bar scripts, but to be 
honest, when was the last time you wrote one?  

20
00:02:34,880 --> 00:02:39,440
Writing them from scratch is not that bad. 
Maintaining a bar script that someone else  

21
00:02:39,440 --> 00:02:55,840
wrote is not great. So, neither of the situations 
is good. You should update your tools but at the  

22
00:02:55,840 --> 00:03:01,120
same time, you should choose those tools that 
you know that they are proven and they will be  

23
00:03:01,120 --> 00:03:06,880
supported for the next few years. So that's why 
I've decided to make this presentation. I want  

24
00:03:06,880 --> 00:03:12,880
to show you some useful Python tools, tools that 
I recommend to my colleagues and to my clients. 

25
00:03:14,320 --> 00:03:21,680
We'll talk about things that a lot of beginner 
programmers struggle with at some point. First,  

26
00:03:21,680 --> 00:03:28,160
I will show you how to install different Python 
versions and how to manage them using pyenv.  

27
00:03:29,520 --> 00:03:34,800
Next, I will talk about Python dependency and I 
will explain you what are virtual environments,  

28
00:03:34,800 --> 00:03:38,720
how they work and why you need them if 
you work with multiple Python projects.  

29
00:03:39,440 --> 00:03:49,040
I'll compare the built in module, like 
Virtual and Wrapper. We will talk about pipx,  

30
00:03:49,600 --> 00:03:53,680
this is a great tool if you want to 
install some Python package globally,  

31
00:03:53,680 --> 00:03:57,040
but you still want to isolate it 
from other packages on your computer. 

32
00:03:59,120 --> 00:04:04,000
And before we move on, I really want to 
highlight one thing, those are all just  

33
00:04:04,000 --> 00:04:09,200
tools and there are a lot of other tools that 
do the same thing. If you use something else,  

34
00:04:09,200 --> 00:04:16,240
that's great. My goal, here, is not to convince 
you that those tools are the best. No. I just  

35
00:04:16,240 --> 00:04:21,280
want to show you how to solve some basic problems 
when you configure your development environment.  

36
00:04:22,160 --> 00:04:28,560
If you are using conda and you are happy 
with it, the first two bullet points are  

37
00:04:28,560 --> 00:04:35,680
already solved for you. But if you don't know 
what to use, let me show you some recommendations.  

38
00:04:37,520 --> 00:04:42,000
So, first let's talk about 
installing Python on your computer. 

39
00:04:42,000 --> 00:04:46,800
Depending on your operating system, your computer 
might already come with some version of Python  

40
00:04:46,800 --> 00:04:58,960
installed. If you're using Mac OS, it is 2.7. 
In windows, you don't have any Python installed.  

41
00:05:00,960 --> 00:05:04,320
Let's say that your operating system 
comes with some Python version,  

42
00:05:04,320 --> 00:05:09,840
this Python version that is already installed 
on your computer is often called System Python.  

43
00:05:11,920 --> 00:05:18,240
No matter what system version of Python you 
have, I strongly suggest you don't use it. In  

44
00:05:18,240 --> 00:05:27,120
many cases, as we saw with Mac OS, it's outdated. 
2.7 is not supported by the core developers so  

45
00:05:27,120 --> 00:05:34,640
hopefully you are not using it since a long time.
You might be tempted to update the system Python  

46
00:05:34,640 --> 00:05:41,760
to Python 3, but you probably have some programs 
that require Python 2.7. You would be surprised  

47
00:05:41,760 --> 00:05:47,520
how many programs, or even parts of the 
operator system still requires Python 2.7  

48
00:05:48,480 --> 00:05:59,920
in Mac OS. If you change the Python version that 
comes pre installed, you risk your computer will  

49
00:05:59,920 --> 00:06:06,640
stop working at all and that is not fun. I have 
done this in the past, when I didn't know much  

50
00:06:06,640 --> 00:06:11,200
about programming and operating systems and I 
had to re install the whole operating system.  

51
00:06:12,480 --> 00:06:21,040
My advice is to leave it alone and pretend that it 
doesn't exist. No matter what operating system you  

52
00:06:21,040 --> 00:06:25,920
have, you will need to install Python and there 
are many different ways how you can do this. 

53
00:06:27,120 --> 00:06:31,760
You can download the installer 
for your operating system.  

54
00:06:32,880 --> 00:06:41,360
You can use a package manager like Home brew on 
Mac and compile Python from the source files.  

55
00:06:43,680 --> 00:06:48,880
However, my favorite way of installing Python, 
that I have been using since a few years,  

56
00:06:48,880 --> 00:06:58,240
is to use a tool called pyenv. It managing Python 
versions. You can install a Python version on  

57
00:06:58,240 --> 00:07:03,520
your computer and quickly switch between 
those versions you have already installed.  

58
00:07:04,480 --> 00:07:09,440
It might not be a big deal if you only 
use one Python version at the time. But  

59
00:07:09,440 --> 00:07:14,800
if you're working with multiple Python projects 
that require different Python versions, this is  

60
00:07:14,800 --> 00:07:25,920
extremely useful. I try to use the latest version 
with Python. But my clients don't usually use the  

61
00:07:25,920 --> 00:07:32,240
latest version of Python. I've been using pyenv 
for years and it works very well. If you have  

62
00:07:32,240 --> 00:07:42,560
worked with you might recognize similar tools, 
for example, there is Ruby and Node JS. Pyenv  

63
00:07:46,480 --> 00:07:57,040
will work fine on Mac OS and Linux, check 
out the pyenv win. It might not have all the  

64
00:07:57,040 --> 00:08:02,080
features that the standard pyenv has, but it has 
all the essential ones that I will talk about. 

65
00:08:03,040 --> 00:08:10,480
But then again, if you are Windows and you are 
a happy conda user, there's actually no point  

66
00:08:10,480 --> 00:08:16,320
in switching to use pyenv. One of the things 
conda can do is creator virtual environments.  

67
00:08:30,560 --> 00:08:36,720
You can use pyenv with Home brew and use the 
tool called pyenv Installer. And, while this last  

68
00:08:36,720 --> 00:08:41,440
option requires you to download a bar script from 
the internet and run it in a terminal which is a  

69
00:08:41,440 --> 00:08:50,320
big security no no, it's actually very convenient. 
It will install some additional plugins like  

70
00:08:50,320 --> 00:08:55,280
pyenv doctor that you can use to verify that 
your pyenv installation is working fine. 

71
00:08:57,360 --> 00:09:01,760
So, once you have pyenv installed, you 
can use it to install new Python version.  

72
00:09:01,760 --> 00:09:07,840
To see the list of all the available Python 
versions, you can run pyenvinstall list  

73
00:09:08,880 --> 00:09:15,040
and you will see a huge list of Python available 
installations. We have the standard Python  

74
00:09:15,040 --> 00:09:24,080
versions. Apart from that, we have Anaconda, and 
so on. All those different versions of Python  

75
00:09:24,080 --> 00:09:29,680
can be installed with pyenv. If you ever wanted 
to try PyPI, now you can very easily do this. 

76
00:09:31,840 --> 00:09:37,520
Once you select the version from this list, 
type "pyenvinstall" and the version number and  

77
00:09:37,520 --> 00:09:42,240
go make yourself a coffee. I mean it. The 
installation usually takes a few minutes.  

78
00:09:43,360 --> 00:09:53,120
There is OpenSSL that you can use. If you don't 
have those libraries installed, each time you  

79
00:09:53,120 --> 00:09:59,200
try to download a new Python version, pyenv 
will try to download it and temporarily use it  

80
00:09:59,200 --> 00:10:05,440
so I suggest you take a look at the GitHub 
page for the list of the required dependencies. 

81
00:10:07,200 --> 00:10:13,760
Okay. So, once this is done, you can run pyenv 
versions to see if this new version is on this  

82
00:10:13,760 --> 00:10:21,280
list. If you can see it there, then it means 
that you're all set. So, now we have to tell  

83
00:10:21,280 --> 00:10:27,840
pyenv to use that version. And for that, we have 
to choose one of three different levels at which  

84
00:10:27,840 --> 00:10:35,040
we can change the Python version. We have global, 
local or shell. So, what does it mean? Well,  

85
00:10:36,080 --> 00:10:42,800
9 out of 10 times, you probably want to change the 
global Python version and to do that, you just run  

86
00:10:42,800 --> 00:10:49,200
"pyenv global 3.9.0" and that changes the 
global Python version on your computer. 

87
00:10:51,040 --> 00:10:58,480
Then we have pyenv local. So, imagine that most 
of the time you are working with Python 3.9, but  

88
00:10:58,480 --> 00:11:04,640
you have this one project on your computer that 
requires Python 3.7 and for some strange reason,  

89
00:11:04,640 --> 00:11:11,280
it won't work with any other Python version. So, 
instead of changing the global Python version  

90
00:11:11,280 --> 00:11:17,520
to 3.7 when you work on this project and then 
changing it back to 3.9 when you stop working on  

91
00:11:17,520 --> 00:11:24,400
this project you can set a local Python version. 
And that's where the pyenv local command comes in.  

92
00:11:25,200 --> 00:11:34,160
You can run pyenv local 3.7 or 3.9 and will 
set that version for the current folder and  

93
00:11:34,160 --> 00:11:41,040
all its subfolders. So, whenever you go inside 
this folder, Python version will automatically  

94
00:11:41,040 --> 00:11:46,400
change and when you go outside of this 
folder, it will change back to the global one. 

95
00:11:48,640 --> 00:11:54,000
That's very handy when you work with multiple 
projects that use different Python versions. So,  

96
00:11:54,000 --> 00:11:59,280
instead of changing the global Python version 
back and forth, you just have to run pyenv local  

97
00:11:59,280 --> 00:12:06,720
in one folder, pyenv local in another folder and 
then pyenv will automatically change the version  

98
00:12:06,720 --> 00:12:13,760
when you go inside each of those folders.
And then finally, we have pyenv shell. And  

99
00:12:13,760 --> 00:12:18,080
this changes the Python version you use 
in your current shell session. You might  

100
00:12:18,080 --> 00:12:22,400
want to use it, for example, when you want 
to temporarily change the Python version.  

101
00:12:24,000 --> 00:12:33,920
You want to run code under Python 2, you run pyenv 
shell 2.7.18 and you can use Python 2. But once  

102
00:12:33,920 --> 00:12:38,720
you open a new session in your terminal, you go 
back to using the previous version of Python. 

103
00:12:41,520 --> 00:12:44,800
So, that's how we can easily manage 
Python versions on your computer.  

104
00:12:45,360 --> 00:12:51,840
Let's talk about dependencies. Let's start with 
pypi. Pypi is a package manager for Python.  

105
00:12:52,560 --> 00:12:58,000
Whenever you want to install a new package, all 
you need to do is to run pip install, the name  

106
00:12:58,000 --> 00:13:04,560
of the package, and it's running. However, 
pypi has one big problem. Whenever you ask  

107
00:13:04,560 --> 00:13:11,680
it to install a specific version of a package, it 
will uninstall the previous versions and install  

108
00:13:11,680 --> 00:13:17,680
the one that you asked for. Let me show you an 
example of what I mean. Imagine you are a web  

109
00:13:17,680 --> 00:13:27,040
developer and you want to build a Django website, 
you install the latest version of Django and pypi.  

110
00:13:28,720 --> 00:13:37,360
Everything works great. You build an awesome 
website and the website is so awesome and they ask  

111
00:13:37,360 --> 00:13:46,800
you, hey, you're making awesome Django websites 
so can you fix my Django website? As it often  

112
00:13:46,800 --> 00:13:52,240
happens with clients, they are not using Django 
3, they are still using, let's say, Django 2.2. 

113
00:13:54,160 --> 00:13:58,560
So, you install that specific version 
by typing "pypi install Django"  

114
00:14:00,640 --> 00:14:10,480
and you start working on this website for your 
client. So far, so good. But, later that day,  

115
00:14:10,480 --> 00:14:19,120
you discover that your personal website, so 
this one, built with Django 3, has a bug. When  

116
00:14:19,120 --> 00:14:24,480
you want to test it and make sure that it is 
working fine, you get an error message saying  

117
00:14:24,480 --> 00:14:30,560
"Django 3 is not installed." Like, what? I mean, 
we installed it yesterday, what happened with it?  

118
00:14:31,360 --> 00:14:39,200
Well, when we told pypi to install Django 2.2, 
pypi first checked if we already have Django  

119
00:14:39,200 --> 00:14:48,880
installed and we did, it's just it wasn't Django 
2.2 so pypi uninstalled that version. So we just  

120
00:14:48,880 --> 00:14:55,280
run into a problem with dependencies management.
We have this problem because pypi installs Python  

121
00:14:55,280 --> 00:15:02,160
packages inside the side packages folder 
and puts each package into a separate folder  

122
00:15:02,160 --> 00:15:07,920
named after that package. So, Django 3 
is placed inside side package/Django.  

123
00:15:08,640 --> 00:15:16,960
But when we want to install Django 2, it will also 
be placed inside sidepackages/Django. So, pypi has  

124
00:15:16,960 --> 00:15:22,960
to first remove what's inside this Django folder 
and then install a different version. If you only  

125
00:15:22,960 --> 00:15:28,000
work with one Python project all the time, then 
you're probably not affected by this problem.  

126
00:15:28,560 --> 00:15:34,400
But sooner or later, you will need to install 
different versions of the same package and you're  

127
00:15:34,400 --> 00:15:39,840
going to run into issues with pypi uninstalling 
some dependencies of some other packages. 

128
00:15:41,280 --> 00:15:47,520
The problem with pypi is that it installs 
all the packages in the same folder so  

129
00:15:48,080 --> 00:15:55,040
how about we tell pypi to temporarily install 
packages into a separate folder and then we  

130
00:15:55,040 --> 00:16:01,200
tell our Python interpreter to use packages from 
that folder? Well, that's exactly what virtual  

131
00:16:01,200 --> 00:16:08,080
environment does. A virtual environment is a 
folder that contains a Python installation and  

132
00:16:08,080 --> 00:16:14,160
any additional packages that you install. When you 
activate a virtual environment, two things happen.  

133
00:16:15,280 --> 00:16:21,200
So, first, you tell pypi, hey, I want you to 
install any new Python package in that folder and  

134
00:16:21,200 --> 00:16:26,080
you tell Python interpreter, hey, I want you to 
use Python and Python packages from that folder.  

135
00:16:27,520 --> 00:16:37,200
If we try to install Python packages, pypi won't 
uninstall because it's no longer using the global  

136
00:16:37,200 --> 00:16:42,160
site packages. It's using side packages 
from this specific virtual environment. 

137
00:16:43,680 --> 00:16:48,560
So, how does it look in practice? Well, first 
we need to create a virtual environment.  

138
00:16:48,560 --> 00:17:08,320
Python has a built in module called Venv. So, 
in my case, I'm creating a folder called ".venv"  

139
00:17:12,800 --> 00:17:19,440
are both a common name used for folders with 
virtual environments so it makes it obvious that  

140
00:17:19,440 --> 00:17:25,680
whenever you go into some Python project and 
you see this folder inside, there are things  

141
00:17:25,680 --> 00:17:31,840
related to virtual environment. But, it also has 
another benefit. Some code editors, like PyCharm  

142
00:17:32,960 --> 00:17:38,880
will recognize this as a virtual environment and 
automatically start using it on your project. 

143
00:17:41,040 --> 00:17:45,840
So, we have created a virtual environment 
and now we have to activate it.  

144
00:17:47,840 --> 00:17:53,440
We have a bin directory and then we have the 
activate script. Since this is a bar script,  

145
00:17:53,440 --> 00:17:57,600
we have to run it with source command and of 
course, if you're using a different shell,  

146
00:17:57,600 --> 00:18:02,960
there are different files that you can use. 
For Windows users, there is activate and so on. 

147
00:18:05,600 --> 00:18:09,920
Once you activate it, you should see a 
difference in your terminal's prompt.  

148
00:18:09,920 --> 00:18:12,960
It should not display the name of 
the current virtual environment  

149
00:18:13,680 --> 00:18:18,160
so if you see something like this venv in 
parenthesis, that's great because it means  

150
00:18:18,800 --> 00:18:25,600
a given virtual environment is now active. And, 
now we do everything that we would normally do.  

151
00:18:27,440 --> 00:18:31,360
It we install it with pypi, it will be 
installed with this virtual environment  

152
00:18:32,000 --> 00:18:37,440
and it will have access to the Python 
packages from this virtual environment.  

153
00:18:39,360 --> 00:18:43,920
If you want to stop using the virtual environment, 
you have to run the deactivate command.  

154
00:18:44,560 --> 00:18:49,920
When you call it, it will revert all 
the changes that the activate did. So,  

155
00:18:49,920 --> 00:18:55,840
you will go back to using the global Python 
version and back to global pypi packages. 

156
00:18:57,600 --> 00:19:02,800
So, a typical workflow using virtual environments 
involves creating one virtual environment for each  

157
00:19:02,800 --> 00:19:08,080
of your projects. If you're working with two 
Django projects, you first create a table one  

158
00:19:08,080 --> 00:19:15,200
virtual environment, you work on it. Then 
if you want to switch to another project,  

159
00:19:15,200 --> 00:19:19,680
you create another virtual environment. 
You activate and you work on that project. 

160
00:19:22,960 --> 00:19:32,640
Venv module is perfectly fine for managing virtual 
environments, but I want to show you another tool  

161
00:19:32,640 --> 00:19:44,160
I have been using for a long time. It's called 
Virtualenvwrapper. You can install it with pypi  

162
00:19:44,880 --> 00:19:50,400
and of course, it works on Linux and Mac and 
Windows users, you have to do something else.  

163
00:19:50,960 --> 00:20:01,840
There is virtualenvwrapperwindows. If you're 
a happy conda user, you can stick to this. 

164
00:20:02,720 --> 00:20:15,440
It stores all the virtual environments inside the 
.virtual env folder inside your home directory and  

165
00:20:15,440 --> 00:20:23,920
it provides you with useful commands. You can 
create a new virtual environment by typing  

166
00:20:23,920 --> 00:20:33,600
"mkvirtualenv." It's not creating the 
virtual environment in the folder.  

167
00:20:38,400 --> 00:20:47,840
If you want to activate, you have to call "work 
on Django to app" and then it will figure out  

168
00:20:47,840 --> 00:20:54,080
where is the activation script. You don't have 
to type the whole path to the activate script  

169
00:20:54,080 --> 00:21:09,760
and figure out in which folder it's located. You 
can call "lsvirtualenv." Again, it's impossible to  

170
00:21:09,760 --> 00:21:19,280
get this list because venv doesn't keep track. And 
virtualenvwrapper stores everything in the list.  

171
00:21:21,360 --> 00:21:22,880
To remove, you run "rmvirtualenv" 
and the virtual environment. 

172
00:21:22,880 --> 00:21:43,440
You are probably wondering which is better? Both 
are great. I use virtualenvwrapper because I don't  

173
00:21:43,440 --> 00:21:52,000
want to type this whole thing where, of course, 
half of the time, I'm in, like, some subfolder  

174
00:21:52,800 --> 00:21:58,880
and get an error that it doesn't exist so I have 
to figure out where the activation script is  

175
00:21:58,880 --> 00:22:10,000
located. I like to say, "work on Django 2 up" 
and be done with it. I create a table virtual  

176
00:22:10,000 --> 00:22:17,200
environments that connected to a project. 
I have a bunch of data science libraries.  

177
00:22:24,240 --> 00:22:31,680
Virtualenvwrapper can create temporary virtual 
environment. It will make a virtual environment  

178
00:22:35,120 --> 00:22:40,320
and when you deactivate it, it disappears. 
It's nice for testing some pypi packages. 

179
00:22:43,760 --> 00:22:49,520
If you store virtual environments in the same 
folder, your code editor will pick it up and  

180
00:22:49,520 --> 00:22:55,280
start using it automatically. When you delete this 
project, you also delete the virtual environment. 

181
00:23:05,440 --> 00:23:07,840
All right. So, we have covered 
how to manage Python packages  

182
00:23:08,560 --> 00:23:12,240
inside your projects, what about global 
Python packages on your computer?  

183
00:23:19,040 --> 00:23:24,000
Some tools are much more convenient to use 
when you install them globally instead of  

184
00:23:24,000 --> 00:23:36,000
installing them in a specific virtual 
environment. You want to use those tools  

185
00:23:36,000 --> 00:23:40,080
across all your projects, or even before 
you create a table a project. For example,  

186
00:23:40,800 --> 00:23:47,200
with virtualenvwrapper, we would 
create a virtual environment.  

187
00:23:49,600 --> 00:23:56,080
But then again, if two different tools require two 
different versions of the same dependency, we have  

188
00:23:56,080 --> 00:24:01,600
a problem. You install one tool and everything 
is fine, you install a second tool, it changes  

189
00:24:04,640 --> 00:24:07,840
dependencies of the first tool and 
then the first tool stops working.  

190
00:24:11,120 --> 00:24:16,000
We could install each of those tools 
inside a separate virtual environment,  

191
00:24:16,000 --> 00:24:20,160
but this is a lot of hassle to use it like 
that. Each time, you'd have to activate,  

192
00:24:21,600 --> 00:24:36,320
run it and deactivate. We can easily solve 
this problem with pipx. Pipx installs Python  

193
00:24:36,320 --> 00:24:42,240
packages inside separate environments, but at 
the same time, those packages act like if they  

194
00:24:42,240 --> 00:24:47,360
were installed globally so you don't have to 
activate any virtual environment to use them. 

195
00:24:48,800 --> 00:24:53,280
How does it look in practice? Let's say you 
want to install [Indiscernible] for Python code.  

196
00:24:54,320 --> 00:25:01,680
I run well, we run pipx install black and after 
a few seconds, we get a message saying that  

197
00:25:01,680 --> 00:25:08,240
Black has been installed and now we have those 
three commands, black, black primer and black D.  

198
00:25:10,080 --> 00:25:13,920
And now we can use Black as 
if it was installed with pypi.  

199
00:25:13,920 --> 00:25:20,960
It doesn't matter if we were inside of a 
virtual environment or not. We don't have to  

200
00:25:20,960 --> 00:25:27,120
activate anything. We run the same commands 
as we would run if we weren't using pipx. 

201
00:25:29,600 --> 00:25:34,160
And if we want to install a different version 
of Black inside of a virtual environment,  

202
00:25:34,160 --> 00:25:38,800
we can still do this. This Black, 
from inside a virtual environment,  

203
00:25:38,800 --> 00:25:47,200
will take precedence over the global Black. You'll 
be using Black from this virtual environment.  

204
00:25:49,120 --> 00:25:54,560
What else we can do with pipx? We can install 
packages to see what commands they offer.  

205
00:25:55,360 --> 00:26:00,080
We can uninstall a package and this will 
also clean up its virtual environment.  

206
00:26:00,080 --> 00:26:13,520
We can upgrade with one command and pipx inject. 
It will install a pypi package inside of a virtual  

207
00:26:13,520 --> 00:26:27,600
environment of another package. You might use 
it to install pytest. We can't just run pipx  

208
00:26:27,600 --> 00:26:43,200
install Python Discov because it will be inside 
its own virtual environment. So we have to call  

209
00:26:43,200 --> 00:26:51,840
pipx inject pytest and it will install it 
inside the virtual environment of pytest. 

210
00:26:53,360 --> 00:26:57,680
And that brings us to the end of my presentation 
so let's quickly summarize what we saw.  

211
00:26:58,880 --> 00:27:04,560
First, use pyenv to install new Python versions. 
Once you set it up, it's really easy to install  

212
00:27:04,560 --> 00:27:13,680
new Python versions. Then use virtual environments 
when you want to isolate their dependencies.  

213
00:27:15,200 --> 00:27:18,320
Create a separate virtual environment 
for each of your projects.  

214
00:27:19,680 --> 00:27:28,960
It has venv and it's perfectly fine to use it. 
Virtualenvwrapper is also a really great choice.  

215
00:27:30,240 --> 00:27:35,680
And, finally, if you want to install some tools 
globally, you can use pypi outside of the virtual  

216
00:27:35,680 --> 00:27:41,040
environment but you risk that if there is some 
version conflict, they won't work together.  

217
00:27:41,680 --> 00:27:48,320
So a much better tool to use is called pipx and 
this will install global package into a separate  

218
00:27:48,880 --> 00:27:53,680
into a separate virtual environment but for you, 
there won't be any difference in how you use them. 

219
00:27:55,760 --> 00:27:59,360
Thank you very much for listening and I 
think we still have some time for questions. 

220
00:27:59,360 --> 00:28:07,520
>> Thank you, Sebastian. We probably 
have time for one question. And,  

221
00:28:09,200 --> 00:28:18,800
we we have we have two questions. So, 
I'm going to use my use my powers to pick  

222
00:28:20,000 --> 00:28:26,560
I lost it. Um, okay. So, someone asks, I'd 
love to know which one is used in production?  

223
00:28:26,560 --> 00:28:33,360
Is there a set of best practices to follow?
SEBASTIAN WITOWSKI: For production, I use yet  

224
00:28:33,360 --> 00:28:40,800
another tool that I didn't have time to put in 
this talk. I use a tool called what was the name?  

225
00:28:42,720 --> 00:28:47,520
Pypi tools. It has a command called pypi compile 
and you can provide a list of dependencies,  

226
00:28:48,160 --> 00:28:50,400
like, you just specified, I 
want Django, I want pytest.  

227
00:28:53,760 --> 00:28:58,080
It will take those requirement files 
and resolve all the dependencies and  

228
00:29:01,440 --> 00:29:08,640
third party packages, dependencies that you use. 
You take this and you put it into a Docker image  

229
00:29:09,840 --> 00:29:16,080
or venv. That's what I would use in production.
>> Pypi compile is great. I use that,  

230
00:29:16,080 --> 00:29:25,680
too. A lot of questions came in. We are out 
of time. So, Sebastian, are you would you  

231
00:29:25,680 --> 00:29:31,280
like to head over to the text chat channel 
for a few minutes, to answer some more? 

232
00:29:31,280 --> 00:29:37,120
SEBASTIAN WITOWSKI: Sure.
>> Do jump into the the Curlyboi Theatre text  

233
00:29:37,120 --> 00:29:43,520
chat channel and I will paste the questions over 
there. But, leave when you jump to the text chat,  

234
00:29:43,520 --> 00:29:49,920
the stream for Curlyboi Theatre will keep playing 
up in the top corner, leave that playing because  

235
00:29:49,920 --> 00:29:56,560
the conference closing is coming up in 15 minutes, 
okay, and we don't want anyone to miss that. 

236
00:30:02,080 --> 00:30:05,760
All right. So, thank you, once again, Sebastian.
SEBASTIAN WITOWSKI:  

237
00:30:05,760 --> 00:30:07,680
Thank you so much for having me.
>> I think that was really helpful.  

238
00:30:07,680 --> 00:30:19,360
The chat was on fire. So, thank you.
SEBASTIAN WITOWSKI: Thanks. Bye bye.