I heard that it would be convenient to put all the tools I made into a container, so I decided to start using Docker, which I had been interested in for a long time. This time, I will make a web server made with python flask into a container so that I can manage the web server just by starting and stopping the container.
Click here for the environment used
$ cat /etc/redhat-release
Red Hat Enterprise Linux release 8.2 (Ootpa)
$ docker --version
Docker version 19.03.12, build 48a66213fe
containerd.io
does not exist. In my case [here](https://vexpose.blog/2020/04/02/installation-of-docker-fails-on-centos-8-with-error-package-containerd-io-1-2- 10-3-2-el7-x86-64-is-excluded /) was able to solve it safely, so for reference.First, let's briefly summarize how to use Docker (how to make a container). There are 4 steps to create a Docker container.
Personally, I think the first thing I don't really understand is creating a Dockerfile. So, the first step is to create a simple python script inside the container, and the second step is to improve it to run the flask web server.
The first step is to run the next myapp.py
inside the container.
myapp.py
print("hello Docker!")
First, prepare an image that will be the execution environment for python3. Search for python3 series images registered in Docker Hub.
$ sudo docker search python3
NAME DESCRIPTION STARS OFFICIAL AUTOMATED
rackspacedot/python37 11
sellpy/python3-jupyter-sklearn python3-jupyter-sklearn 5 [OK]
openwhisk/python3action Apache OpenWhisk runtime for Python 3 Actions 5
sellpy/python3-jupyter-sklearn-java python3-jupyter-sklearn-java 2 [OK]
quoinedev/python3.6-pandas-alpine Python 3.7 on alpine with numpy and pandas i… 2
(Omitted)
This time we will use rackspacedot / python37
, which has the most STARS. Let's pull this.
$ sudo docker pull rackspacedot/python37
rackspacedot / python37
is also a Docker image, so you can check it with docker images
after pulling.
$ sudo docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
rackspacedot/python37 latest 3d51361ee118 7 weeks ago 1.06GB
If you have this image, you can use python in the container, so if you add other necessary parts (such as script placement) based on this, it's OK.
Then create a file named Dockerfile
.
FROM rackspacedot/python37
WORKDIR /usr/local/script
COPY myapp.py .
CMD python myapp.py
To briefly explain,
FROM rackspacedot/python37
--This is the part that specifies the base image. Specify the image you just pulled.WORKDIR /usr/local/script
-** Specifies the ** working directory within the container. It doesn't matter if it's different from the directory you're in now.COPY myapp.py .
--Copy myapp.py to the directory specified by the second argument in the container. This time, it is specified by .
, so it will be copied to the directory specified by WORKDIR
.CMD python myapp.py
--This command is executed when the container is started.The files prepared so far are as follows.
$ ls -l
total 8
-rw-r--r--. 1 user developer 146 Sep 11 16:39 Dockerfile
-rw-r--r--. 1 user developer 173 Sep 11 17:04 myapp.py
Now that we have created a Dockerfile, we will build the image → start the container. First, build the image.
$ sudo docker build -t myapp:test .
The -t name: tag
sets the name and tag of the image (it can be different from the script name). .
Specifies the path of the directory where the Dockerfile is located.
If you get Successfully built hash value
, the image is generated and you can check it with docker images
.
$ sudo docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
myapp test e577339515a7 10 seconds ago 1.06GB
rackspacedot/python37 latest 3d51361ee118 7 weeks ago 1.06GB
Now that the image is created, create and start the container.
$ sudo docker run myapp:test
hello Docker!
I was able to successfully run the python script in the container.
The container started here remains, so you can run it again with the same command. You can also see the container created with docker ps -a
.
Now that you can run python scripts inside the container, let's create a server in flask as the second step.
Rewrite myapp.py
as follows:
from flask import Flask
app = Flask("myapp")
@app.route("/")
def main():
return "hello Docker!!"
if __name__ == "__main__":
app.run(host="0.0.0.0", port=8080)
For the time being, I reduced the number of !
To 2 so that you can see the change.
Let's make this usable as a web server in the container.
Since we are using flask, we need to install flask inside the container. pip is included in
rackspacedot / python37by default, so add the part that
pip install` to the Dockerfile when building the image.
FROM rackspacedot/python37
RUN pip install flask
RUN useradd docker
USER docker
WORKDIR /usr/local/script
COPY myapp.py .
CMD python myapp.py
To explain the added amount,
RUN pip install flask
--Install flask inside the container.RUN useradd docker / USER docker
--Add a user named docker
and perform subsequent operations as the docker
user.
――It works without this time, but I added it for security reasons.Since the file was rewritten, rebuild the image → start the container. First of all, from rebuilding.
$ sudo docker build -t myapp .
Since we omitted the tag this time, the tag latest
is automatically assigned. Let's check with docker images
.
$ sudo docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
myapp latest 6c747be5d597 3 seconds ago 1.06GB
myapp test e577339515a7 50 minutes ago 1.06GB
rackspacedot/python37 latest 3d51361ee118 7 weeks ago 1.06GB
Now let's start the container. Since it is a web server, I am adding options.
$ sudo docker run -d -p 8080:8080 myapp
Although it is a port number, it is written as -p reception port number: number on the container side
. The receiving port number can be any number, but the number on the container side should be the number specified in myapp.py
in the container (8080 in this case).
If it starts without any problem, you can check the running container with docker ps
.
$ sudo docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
00d1ab6fc24a myapp "/bin/sh -c 'python …" 3 seconds ago Up 2 seconds 0.0.0.0:8080->8080/tcp thirsty_mccarthy
Let's actually access it.
$ curl http://localhost:8080
hello Docker!!
Sounds good. This completes the containerization of the web server. If you want to stop the container
$ sudo docker stop thirsty_mccarthy
If you want to restart after stopping
$ sudo docker start thirsty_mccarthy
For thirsty_mccarthy
, specify the container name (the one displayed in NAME
when docker ps
is executed). If you start it with docker start
, it will automatically run on the port you specified during docker run
.
Also, if you make it into a container, you can run it in another environment immediately by building the image → starting the container, which is very convenient.
That's all for this time. If Docker Compose can execute multiple containers with a single command, the range will expand further, so I think I will study this as well.
Recommended Posts