1. 目标
本文讲述了如何通过3步,把Django项目部署在K8S上。
本文适用读者:
了解Django项目的开发。 了解K8S的用途。
2. 具体步骤
把一个Django项目部署在Kubernete环境上,只需以下3步:
接下来我们依次讲述具体步骤。
3. 第一步:创建镜像
假设已有Django项目,并保存在文件夹django_app下,具体结构如下:
django_app
-- apps
-- django_app
---- settings.py
---- urls.py
---- wsgi.py
-- manage.py
-- Dockerfile # 镜像创建文件
-- .dockerignore # 镜像的忽略文件
-- requirement.txt # 依赖包文件
3.1 构建Dockerfile文件
使用Dockfile来创建镜像,内容如下:
FROM python:3.8-slim-bullseye
RUN pip install gunicorn -i https://pypi.tuna.tsinghua.edu.cn/simple
WORKDIR /app
COPY requirements.txt .
RUN pip install -r /app/requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple
COPY django_app/ /app/
EXPOSE 80/tcp
ENTRYPOINT gunicorn -w 4 -b 0.0.0.0:80 django_app.wsgi
从基础镜像python:3.8 开始,安装gunicorn,创建工程目录app,复制requirements文件,接着安装依赖库(使用清华源),然后把项目里的文件都拷贝到工程路径app下,接着暴露80端口,最后使用gunicorn命令启动服务。
注意:由于国内更新pip比较慢,所以在制作镜像的过程中对pip临时更换到了清华源。
3.2 建立.dockerignore文件
项目里有些文件比如pyc等一些临时文件不需要复制到镜像中,我们只需把他们添加到.dockerignore里,就可以避免这些文件被打包到镜像里。
建立.dockerignore文件,内容如下:
*/*.zip
*/*.sh
*/*.pyc
*/__pycache__*
*.zip
*.sh
*.pyc
__pycache__
env/
3.3 构建镜像
运行命令构建镜像:
docker build -t django-example:v1.0 .
注意: 命令的末尾有个.符号
接着我们会看到如下输出:
3.4 验证镜像
我们通过浏览器访问镜像里的服务的方式来验证镜像是否构建成功。
首先,使用运行镜像:
sudo docker run django-example:v1.0
接着,查看容器ID:
sudo docker ps -ls
输出如下:
查看该容器对应的IP:
sudo docker inspect 890200dd1d12
输出如下:
复制IPAddress的输出172.17.0.2到浏览器的地址栏,看看能否访问到服务。
四. 第二步:部署在Kubernetes环境上
Kubernetes 中最小的对象是Pod,它是运行的容器的镜像,一个副本集包含多个Pod,利用副本集对外提供服务。这里我们只需创建一个具有1个的Pod副本集。
4.1 部署副本集
创建django-example_initial.yaml文件:
apiVersion: apps/v1
kind: Deployment
metadata:
name: django-example
labels:
app: django-example
spec:
replicas: 1
selector:
matchLabels:
app: django-example
template:
metadata:
labels:
app: django-example
spec:
containers:
- name: web-app
image: django-example:v1.0
ports:
- containerPort: 80
接着运行命令:
kubectl apply -f django-example_initial.yaml
这样就创建了容器名为web-app的django-example镜像的副本集,副本集中只有1个Pod,并且暴露了80端口给外部。
检查部署是否成功:
kubectl get deploy
如果输出类似如下情况,表示部署成功
4.2 暴露部署程序
部署成功后,我们需要把部署的内容暴露成服务供大家能够使用,通过如下命令完成:
kubectl expose deployment django-example
4.3 访问部署程序
由于服务部署在Kubernetes上,我们需要找到服务映射出的地址,这样才能从外部访问到服务。
输入如下命令:
kubectl get services
看到如下输出:
这个CLUSTER-IP了吧,就是Kubernetes外可以访问的IP。打开浏览器,输入这个IP来验证下吧。
五. 第三步:配置MySQL
项目已经能在Kubernetes部署完成了,但是还不能正常使用数据库,要如何配置数据库呢?
5.1 在镜像中增加环境库
修改下之前的Dockfile:
FROM python:3.8-slim-bullseye
RUN apt update && apt install -y gcc libmariadb-dev-compat # 新增
RUN pip install gunicorn -i https://pypi.tuna.tsinghua.edu.cn/simple
WORKDIR /app
COPY requirements.txt .
RUN pip install -r /app/requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple
COPY django_app/ /app/
CMD sleep 5 # 新增
CMD python manage.py migrate # 新增
EXPOSE 80/tcp
ENTRYPOINT gunicorn -w 4 -b 0.0.0.0:80 django_app.wsgi
我们增加了mysql的依赖,并在镜像构建过程中增加了migrate的过程,之后重新构建镜像。
5.2 在项目中增加环境变量
修改原来settings.py里的MySQL部分:
import os
...
DATABASES = {
'default': {
'ENGINE': "django.db.backends.mysql",
'NAME': 'Test',
'USER': os.environ.get('MYSQL_USER', 'root'),
'PASSWORD': os.environ.get('MYSQL_PASSWORD', 'xxxxx'),
'HOST': '127.0.0.1',
'PORT': '3306',
}
}
...
利用os.environ.get()来获取对应的环境变量名称和数值。
注意: 环境变量里的数据类型都是字符串,我们需要在用到int的地方做转化。
在项目中增加.env文件:
MYSQL_USER=root
MYSQL_PASSWORD=xxxxx
这样settings里的os.environ.get()会读取.env里的环境变量。最后我们还需在Kubernetes把环境变量信息传递给.env文件。我们利用Kubernetes的保密字典来完成这一步。
5.2 通过保密字典设置环境变量
使用kubectl设置保密字典(Secrets)通常是管理Kubernetes集群中敏感信息的一种方法,比如API令牌、数据库密码等。
创建保密字典:
kubectl create secret generic my-secret --from-literal=MYSQL_USER=root --from-literal=MYSQL_PASSWORD=xxxxx
接着,我们要在Pod中使用保密字典,修改下之前创建的django-example_initial.yaml文件,增加环境变量信息:
apiVersion: apps/v1
kind: Deployment
metadata:
name: django-example
labels:
app: django-example
spec:
replicas: 1
selector:
matchLabels:
app: django-example
template:
metadata:
labels:
app: django-example
spec:
containers:
- name: web-app
image: django-example:v1.0
env:
- name: MYSQL_USER
valueFrom:
secretKeyRef:
name: my-secret
key: MYSQL_USER
- name: MYSQL_PASSWORD
valueFrom:
secretKeyRef:
name: my-secret
key: MYSQL_PASSWORD
ports:
- containerPort: 80
好了,按照之前的步骤重新部署下就能成功MySQL了。
6 总结:
本文章通过3步完成了把一个Django项目部署到Kubernetes上。
具体包括: