How to containerize Python applications with Docker

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hi everyone i'm patrick welcome to my talk getting started with docker and python how to dockerize python scripts and python apps so this talk is perfect for you if you have no or little experience with docker or if you want to pick up a few best practices how to dockerize a python script and what we do today is we look at two different examples so in the first one we have a simple python script that needs some additional dependencies and then we learn how we can put this into a docker container and in the second example we create a python web app so for this we also use a virtual environment when we develop this so this is a pretty standard use case if you work with python and then we learn how we can dockerize this whole application so yeah this is more like a follow along tutorial rather than just a presentation so if you have docker installed on your machine already then you can follow me here and first of all a few sentences about me so my name is patrick loeber and i'm a developer advocate at assembly ai you may also know me already from my youtube channel which is the name python engineer and you can find me on twitter with the handle at python underscore engineer so assembly ai is a deep learning company and we create a speech-to-text api and we use docker for pretty much everything so all our services are dockerized and we also use docker for local development so this is pretty cool and i'm super excited to be here so let's get started um first of all a few sentences about docker so i'm assuming you already know what docker is but just in case so docker is a tool that lets you put your application into a container and these containers allows you to package up the application with all the parts that it needs so all the libraries and dependencies and then we can deploy this as one package and when someone else wants to use this then she or he doesn't have to worry about installing all the dependencies first and can simply use the whole docker container right away so this is pretty cool and in order to install this you can go to the official homepage docker.com and then look for the docker desktop and install this this will also install the command line um tool so yeah this is all we need to get started and in my case i'm using visual studio code as the editor so i also recommend to install the official docker extension so if you search for docker this should be the first result this will just give you things like auto completion or debugging support and just makes your life a little bit easier so yeah go ahead and install this as well and now let's create our first um example so let's create a new directory and in here let's create a new file main dot pi and then in the terminal i also want to cd into this directory and i already prepared the code so you can find this on github the link will be in the description below and yeah so let's simply copy the whole code from the main dot pi file so what this file is doing this will scrape the imdb top 250 movie charts and then randomly selects a movie for you and for this we use two third-party libraries so the first one is requests and the other one is beautiful soup so we need to install these and yeah we do this in a moment with our docker file so one more thing i want to mention here that in this code um i have a wild true loop that is waiting for user input so for now i have a break statement here so it doesn't get to this part so but we will also learn in a moment how we can deal with user input in a docker container but for now this is without the user input and yeah so the first thing we do with if we want to containerize or dockerize our python app is that we need a docker file so let's create a docker file and this doesn't have any extension so simply docker file and you see we already have the logo here so visual studio code knows that this belongs to docker and now is a brief explanation so we have to differentiate between three things the first one is the um docker file then we have the docker image and then we have the con container so and by the way we can use comments like this in a docker file so a docker file is a blueprint for building images a docker image is a template for running containers and the container is then your your running process with your application in it so yeah first we need the docker file so our temp not our template our blueprint for creating the image so the first thing we do is we specify a base image and you see we already get auto completion here or auto suggestions so from and then in my case i use a python base image so i say python and then colon and then you can specify the specific tag you want so in my case i want python 3.9 and by the way if you want to look for other official python images then you can simply search for python docker and in my case this is the first result so this is available in the docker hub so if we click on this then yeah here you see all the different available tags that you can pull and yeah so maybe one thing to mention is that sometimes you see tags with the name slim or alpine so these are more minimal packages that you use if you have for example size constraints so you want to keep your whole package or container small but usually the recommendation is if you don't have any constraints then just use the normal python base image so yeah this is the first thing we do and now we want to add our file into the container so we do this with the add command so we say at and then you see we get source and destination so the source is main dot pi and the destination is simply a dot so this will just be in the base folder in our container and now the next thing to do is we want to install the third party libraries so we can do this with the run command and now the command is pip install and then requests and beautiful beautiful soup for so this is like you would enter it in a terminal so yeah we want to run this and install this and now the last thing is the command that will be executed when the container is started and in this basically we want to say python main.pi and run our python script but this will be a comma separated list so the first string is simply python and then the second one is the first parameter so this is dot slash so in the same directory main dot pi and yeah this is all that we need so now we can go back to the terminal and yeah of course we need docker installed so you can check this with docker dash v and then you see the docker version and now we want to build our docker image so after we have specified our docker file we can use the docker build command and then minus t and give it a tag or a name so in this case i say python imdb and then the directory is simply a dot so in the current directory and now we can hit enter and this will build our docker image so yeah this is already done in my case because i did this before for you it may take a few minutes even if you do this the first time but yeah and one important thing to also note here is that this will you may also see this in the locks step one then step two and step three so this will run from top to bottom and then execute all the commands in our docker file so yeah the order is important here and yeah so now we have our image so now we can run this so now we say docker run and then the name was python imdb and then let's see if this works so yeah we get a movie suggestion like it's done in the script so yeah this works so now we dockerized our first python script so congratulations and now one more thing i want to show you so if i comment this out then we have this as a while true loop so here we have the while true loop that is waiting for the user input if we want another movie or not so um now um we changed our files now we have to rebuild this so now let's again say docker build and then our image and in this case yeah it took a few seconds so now if we run it like this i think this will crash so let's see what happens um [Music] it looks a bit weird but it's running so let's enter something um but yeah actually it does not work so now since we have user input what we have to do is we have to specify additional arguments so we say minus i for interactive and minus t for a pseudo terminal basically and yeah so now let's run it like this and yeah then we don't see any errors so now we can say a wife or we want to continue and then we get another movie and if we say no then it will stop the container so yeah this works and yeah this is our first example so let's go on and let's go to the second example so let's create a new folder example two and in here let's again um actually let's create another folder in here and we call this the app folder and then in here we want our main dot pi file and then in the terminal let's cd into the example to folder so now we see we have the app folder and in here we now in the base of this we again want our docker file so docker file like this and now for the app we want to create a simple web app so for this we in this example we use fast api but the code is basically the very same if you want to use flask um or very similar actually so yeah what we um want to do here is we have to install fast api and we also need uvicorn as our asgi server so for this i want to create a virtual environment so let's do this in here with python 3-m v and v-n and now this will create a virtual environment in here so you already see this and then we can activate it with dot vm slash bin slash activate so the command is slightly different on windows but i'm sure you can find this out for yourself so yeah so now this is activated and now we installed the requirements that we want so we say pip install fast api and uv cord these are the two libraries we need to install and hit enter so yeah so now we have this and now let's create our app.pi file or our main.pi file so here i'm simply copying the example code from the official fast api docs so it's this one and oh sorry i copied it in the docker file this is wrong of course so we need this main dot pi file so in here so here we simply we create our app instance and then we define function and decorate this with app.get and then we have another route with another endpoint and yeah so let's save this and now we can already run this and in order to run this so you could do this in the code and say for example you import uv corn and then say uv corn dot run but we can also do this in the terminal so we say uv corn and then the folder or the path to the file so this is the app folder and then the main file and then colon and then this app is the app instance in our file so now if we run this then this should work already so yeah now it says uvicorn running at local host port um 8 000 so let's click on this and go to this route and then we get hello world and also if we go to i think i think it was slash items and then a number then we get the other one so yeah this is working so let's say ctrl c and quit this again and now we want to dockerize this so again we need our docker file and then again we say from python and then the same base image 3.9 and now i want to do it a little bit different so um first of all i create a working directory so we say work dir and then we call this code so this will basically create another directory in the base directory of the container and you will see later how this looks like so later we actually go into the container in the terminal and see at all look at all the different files so yeah we specify the work directory then the next thing we want to do is we want to copy and install all the requirements from our virtual environment so first of all we need this so in the terminal we can say pip freeze and then the grader sign and then requirements.txt so this will put all the dependencies that we just installed in a file and now we want to copy this so now we say copy and then the source will be dot slash re choir mens dot txt and the destination will be you see i already get the auto completion slash code slash requirements dot txt and now we want to run this again so we say run and then pip install and now i want to show you one best practice so you say dash dash and then we say no cash dash there and then you could optionally also use dash u for or sorry it's called dash dash up great if you want to upgrade packages and then we say slash code slash requirements dot txt so what this will do this is specific to the pip installation command and this will basically tell pip to not use a cache and then this allows to the docker cache to work better so this can save you a lot of time when you rebuild your images so yeah this is a great best practice to keep in mind to use this option with your pip installation command then let's copy the app directory so we say copy slash app into code slash app and now um one more thing i just noticed i need to say pip install dash r requirements.txt of course and then as last thing we need our command so here again we want to say uvicorn and then run the main.pie so here we say as a list and here uv corn and then we want the same command that we have here in our history app dot main colon app so if we run it like this then it actually doesn't work and you will see um why it doesn't work in a moment but i will leave it like this and now we can build our image but before we do this i actually want to show you one more best practice and this is to use a docker ignore file so in here we say dot docker ignore this is similar to a dot git ignore file so this will ignore certain files or folders that should not end up in your container for example here we created this virtual environment but we actually don't need this in our container so we don't want to copy this whole directory so let's write some file names and folders into this docker ignore and i also already prepared this so you can find this on github as well in the example too and in here for example you see i have the pi cache then i have some endings like this then i have the nth and vn folders for virtual environments and some more files so let's copy and paste this so this may not be exhaustive but this is a good starting point for python applications and yeah so we use this docker ignore file and now we can say docker build minus t and then fast api tutorial and a colon for the current directory so let's build this and yeah so this is already done so now we can say docker run fast api tutorial and let's see what happens so we see in the terminal that this is running at localhost port 8000 but if we go to this address then we actually see that our browser can't connect to the server so this is actually not yet working so we have to change a few things so first of all let's quit the docker container again and now in our docker file we have to specify a few additional arguments where we want to run our server so we have to say minus minus host and this will be 0.0.0.0 so this is basically a placeholder address that will listen to all ip addresses on the local machine so this will basically be our local host and yeah so we basically have to use this whenever we want to run a server from within a docker containers this is the same for flask for example and yeah and the next argument is the minus minus port argument so we have to specify a port and let's use port 80 for example and now we can build this again and then we can run it but we also have to specify the port and map this from the container to the outside so we do this by saying minus p and then we map the part here also to our port on the outside so 80 colon 80 and now if we run this then um [Music] we get an error and this is because i think i've already had this from a previous tutorial so let's quickly have a look here so yeah let's um stop this and delete this so i will show you this again in a moment so um let's clear this and try this again so yeah so now it's running and you see this is at zero zero zero zero port 80 but actually we can now go to localhost port 80 again and now if we refresh the site then we see the server response hello world so now this is working and we successfully dockerized our web application so yeah now one more thing i want to show you um let's um say ctrl c and shut this down again so one more argument that we can use is the minus d argument and this will run the container in the background and then we also can give it a name and say my fast api container and now if we hit enter then we see we immediately get our console back and if we go to the address and refresh this then this is still up and running so yeah so now we can actually open our docker desktop and in here you should also now find your container with this name my fast api container and yeah so this works and now one more cool thing um is that if we click on this cli then we can actually get a terminal inside the container so let's do this and by the way if you want to do this manually you can do this with this command docker exact minus it and then you need to know the name and by the way if we open another um console window and say docker ps then here we get the docker id starting with 923 so this is the same as this one and then slash bin slash sh so now we are inside the docker container and now for example if i say ls then you see we get app and requirements so now we are inside the working directory that we specified here and if we didn't do this um then we end up in the base directory of our container so if we go one directory up cd dot dot and then say ls then we would be here so here you see all the different folders in your linux container and we also see the code directory so this is where our application is and then again we can cd into this and then we see our application so yeah this is what the working directory is doing and yeah so that's all i wanted to show you in the second example i hope you really enjoyed this tutorial or this talk and if you have any questions then let us know in the comments or the chat below and then i hope you have a great day
Info
Channel: Docker
Views: 49,517
Rating: undefined out of 5
Keywords: docker, containers
Id: 0UG2x2iWerk
Channel Id: undefined
Length: 26min 8sec (1568 seconds)
Published: Fri Apr 01 2022
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.