☰
DjangoBlog Kubernetes 部署实战:基于 local-storage 与 Ingress 的云原生博客服务栈搭建指南
2026/9/28 2:23:53 网站建设 项目流程
  • 后端
  • 前端
  • CMS

【免费下载链接】DjangoBlog

🍺基于Django的博客系统

项目地址:https://gitcode.com/gh_mirrors/dj/DjangoBlog
点击查看免费下载

本文基于 DjangoBlog 仓库 docs/k8s.md 编写,围绕仓库自带的 deploy/k8s 目录下整套 YAML 配置,从架构设计、环境准备、持久化存储到服务编排与外部暴露,逐步讲解如何在 Kubernetes 集群上部署一套包含 DjangoBlog 应用、Nginx、MySQL、Redis 与 Elasticsearch 的完整博客服务栈。读完本文,你将掌握本地 PV 的静态绑定方式、ConfigMap 驱动的环境变量注入、Deployment 健康探针与 Ingress 流量入口的配置方法,并能在首次运行后完成数据库初始化与管理员账号创建。

架构概览:微服务化的云原生部署

DjangoBlog 的 Kubernetes 部署采用微服务化的云原生架构,每个核心服务都以独立的Deployment运行,整体资源组织遵循如下原则:

  • 核心组件:DjangoBlog 应用、Nginx、MySQL(db)、Redis、Elasticsearch 五个核心服务各自作为一个独立Deployment运行,互不耦合。
  • 配置管理:Nginx 的配置文件与 Django 应用的环境变量通过ConfigMap统一管理;文档明确提示,敏感信息(如数据库密码、Secret Key)建议改用Secret管理,避免明文暴露在 ConfigMap 中。
  • 服务发现:所有服务都通过ClusterIP类型的Service在集群内部暴露,服务之间通过 Kubernetes 服务名(如db、redis、djangoblog)直接通信,无需感知 Pod IP 变化。
  • 外部访问:使用Ingress资源将外部 HTTP 流量路由到 Nginx 服务,Nginx 作为整个博客应用的统一入口,对外暴露 80 端口。
  • 数据持久化:采用基于节点本地路径的local-storage方案。需要预先在指定 K8s 节点上手动创建存储目录,并通过PersistentVolume(PV)与PersistentVolumeClaim(PVC)进行静态绑定。

这一架构的全部编排细节都沉淀在 deploy/k8s 目录下 7 个 YAML 文件中,下文将按部署步骤逐一解读。

1. 环境准备

在开始部署前,请确认以下前提条件:

  • 一个正在运行的 Kubernetes 集群(任意发行版均可,配置对 K8s 版本依赖不大,deployment.yaml使用apps/v1,gateway.yaml使用networking.k8s.io/v1);
  • kubectl命令行工具已安装并能够连接到目标集群;
  • 集群中已安装并配置好Nginx Ingress Controller(Ingress 规则依赖它实现流量路由);
  • 对集群中的一个节点(默认是master节点,见 pv.yaml 中nodeAffinity的取值)拥有文件系统访问权限,以便创建本地存储目录。

2. 部署步骤

步骤 1:创建命名空间

建议将 DjangoBlog 相关的所有资源部署在独立的命名空间中,便于统一管理与后续清理:

# 创建一个名为 djangoblog 的命名空间 kubectl create namespace djangoblog

后续所有kubectl apply的 YAML 中,metadata.namespace均写为djangoblog,因此该命名空间必须先于其他资源创建。

步骤 2:配置持久化存储(local-storage 静态绑定)

本方案使用Local Persistent Volume,存储目录必须预先在物理节点上创建。默认情况下,四个 PV 全部绑定在master节点,对应目录如下:

存储用途PV 名称节点路径容量
MySQL 数据local-pv-db/mnt/local-storage-db10Gi
DjangoBlog 静态文件local-pv-djangoblog/mnt/local-storage-djangoblog5Gi
站点资源文件local-pv-resource/mnt/resource/5Gi
Elasticsearch 数据local-pv-elasticsearch/mnt/local-storage-elasticsearch5Gi

先登录节点创建目录:

# 登录到您的 master 节点 ssh user@master-node # 创建所需的存储目录 sudo mkdir -p /mnt/local-storage-db sudo mkdir -p /mnt/local-storage-djangoblog sudo mkdir -p /mnt/resource/ sudo mkdir -p /mnt/local-storage-elasticsearch # 退出节点 exit

注意:若希望将数据存储在其他节点或使用不同路径,必须同步修改 pv.yaml 中每个 PV 的nodeAffinity(kubernetes.io/hostname的values)和local.path两处配置,否则 Pod 会因调度节点与 PV 所在节点不匹配而无法挂载。

创建目录后,依次应用存储相关配置:

# 应用 StorageClass kubectl apply -f deploy/k8s/storageclass.yaml # 应用 PersistentVolume (PV) kubectl apply -f deploy/k8s/pv.yaml # 应用 PersistentVolumeClaim (PVC) kubectl apply -f deploy/k8s/pvc.yaml

三个文件的分工从源码中可以清晰看到:

  • storageclass.yaml 定义了名为local-storage的 StorageClass,provisioner为kubernetes.io/no-provisioner(即本地存储不提供动态供给,PV 必须由管理员预先创建),并带有storageclass.kubernetes.io/is-default-class: "true"注解,声明其为默认存储类。
  • pv.yaml 中每个 PV 都设置了storageClassName: local-storage、persistentVolumeReclaimPolicy: Retain(删除 PVC 后 PV 保留,防止误删数据)以及volumeMode: Filesystem、accessModes: ReadWriteOnce。
  • pvc.yaml 中每个 PVC 通过volumeName字段显式指定绑定到哪个 PV(如db-pvc绑定local-pv-db),这是静态绑定的关键:PVC 的storageClassName、accessModes与容量请求必须与对应 PV 匹配。

步骤 3:配置应用(ConfigMap 环境变量注入)

部署应用前,需要编辑 configmap.yaml,修改其中的敏感信息与个性化配置。该文件实际包含两个 ConfigMap:

(1)web-nginx-config:以多数据项的形式内嵌了 Nginx 主配置nginx.conf、站点配置djangoblog.conf、资源站点配置resource.lylinux.net.conf及缓存规则lylinux.resource.conf。其中djangoblog.conf定义了博客的对外虚拟主机:/static/直接别名到/code/djangoblog/collectedstatic/,其余请求通过proxy_pass http://djangoblog:8000;反向代理到 Django 应用 Service;同时为robots.txt、ads.txt、favicon.ico、搜索引擎验证文件等提供了独立的静态定位规则。

(2)djangoblog-env:以键值对形式注入 Django 与 MySQL 的运行环境变量,这些变量与 djangoblog/settings.py 中的os.environ.get(...)读取逻辑一一对应:

变量含义settings.py 中的使用
DJANGO_DEBUGDjango 调试模式开关("False")控制 DEBUG 及模板调试
DJANGO_SECRET_KEYDjango 签名密钥由 settings.py 读取,用于 session、csrf 等安全签名
DJANGO_MYSQL_DATABASE/DJANGO_MYSQL_USER/DJANGO_MYSQL_PASSWORDMySQL 库名 / 用户 / 密码对应 settings.py 中 DATABASES 配置
DJANGO_MYSQL_HOST/DJANGO_MYSQL_PORTMySQL 服务地址 / 端口(db/3306)同上,HOST 为集群内 Service 名db
DJANGO_REDIS_URLRedis 地址(redis:6379)由 settings.py 拼装成redis://redis:6379作为缓存 LOCATION
MYSQL_ROOT_PASSWORD/MYSQL_DATABASE/MYSQL_PASSWORDMySQL 容器自身的初始化参数供 mysql 镜像初始化数据库与 root 密码

强烈建议修改以下字段:

  • DJANGO_SECRET_KEY:修改为一个随机且复杂的字符串(仓库中为k8s-test-secret-key-12345678,仅作演示,绝不可直接用于生产);
  • DJANGO_MYSQL_PASSWORD和MYSQL_ROOT_PASSWORD:替换为自定义的强数据库密码,且两处需保持一致。

修改后应用配置:

# 编辑 ConfigMap 文件 vim deploy/k8s/configmap.yaml # 应用配置 kubectl apply -f deploy/k8s/configmap.yaml

另外可以观察到,DjangoBlog 的 Elasticsearch 集成同样通过环境变量驱动(见 settings.py 中的DJANGO_ELASTICSEARCH_HOST、ELASTICSEARCH_USERNAME、ELASTICSEARCH_PASSWORD、ELASTICSEARCH_CA_CERTS等),若需要为 ES 启用认证,可自行在 ConfigMap 中补充对应变量。

步骤 4:部署应用服务栈(Deployment 与 Service)

现在部署所有核心服务:

# 部署 Deployments (DjangoBlog, MySQL, Redis, Nginx, ES) kubectl apply -f deploy/k8s/deployment.yaml # 部署 Services (为 Deployments 创建内部访问端点) kubectl apply -f deploy/k8s/service.yaml

deployment.yaml中共定义 5 个 Deployment,值得关注的工程细节有:

  • djangoblog:镜像liangliangyy/djangoblog:latest,replicas: 3(应用层支持水平扩容),通过envFrom.configMapRef整体注入djangoblog-env环境变量;同时挂载djangoblog-pvc(collectedstatic)与resource-pvc(/resource)两个数据卷。
  • 健康探针:DjangoBlog 与 Elasticsearch 均配置了readinessProbe与livenessProbe,对/health/(Django)与/(ES,9200 端口)发起 HTTP 探测。其中/health/对应 djangoblog/urls.py 中内置的health_check视图,该接口以JsonResponse返回{"status": "healthy", "timestamp": ...},正是为容器编排探针设计的轻量健康检查端点。
  • db(MySQL):通过exec方式执行mysqladmin ping完成就绪与存活探测;数据目录/var/lib/mysql挂载db-pvc。
  • nginx:镜像nginx:latest,将web-nginx-config这个 ConfigMap 的多个数据项通过subPath分别挂载为/etc/nginx/nginx.conf、/etc/nginx/conf.d/default.conf等配置文件,实现“配置即代码”。
  • elasticsearch:镜像为liangliangyy/elasticsearch-analysis-ik:8.6.1(内置 IK 中文分词插件),通过环境变量设置discovery.type=single-node、ES_JAVA_OPTS=-Xms256m -Xmx256m、xpack.security.enabled=false等,数据目录挂载elasticsearch-pvc。
  • 资源配额:各容器均声明requests(如cpu: 10m、memory: 100Mi)与limits(应用与数据库类容器为cpu: "2"、memory: 2Gi,Redis 为cpu: 200m),便于集群调度与资源隔离。

service.yaml为 5 个 Deployment 各创建一个ClusterIPService,端口映射分别为djangoblog:8000、nginx:80、redis:6379、db:3306、elasticsearch:9200。selector通过app标签(如app: djangoblog)关联对应 Pod,集群内各服务即可通过服务名互相访问——这正是 ConfigMap 中DJANGO_MYSQL_HOST=db、DJANGO_REDIS_URL=redis:6379能被正确解析的底层机制。

部署需要一些时间,可实时观察 Pod 状态:

kubectl get pods -n djangoblog -w

直到所有 Pod 的 STATUS 变为Running(注意:DjangoBlog 与 MySQL 由于探针initialDelaySeconds为 60/30 秒,就绪需要一定时间)。

步骤 5:暴露应用到外部(Ingress)

通过 Ingress 规则将外部流量引导至 Nginx 服务:

# 应用 Ingress 规则 kubectl apply -f deploy/k8s/gateway.yaml

gateway.yaml 定义的 Ingress 资源要点如下:

  • ingressClassName: nginx,指定由集群中的 Nginx Ingress Controller 处理;
  • 单条规则将所有路径/(pathType: Prefix)转发到nginxService 的 80 端口;
  • 由此 Nginx 成为博客的统一入口:外部流量 → Ingress Controller → Nginx Service → Nginx Pod(反代到djangoblog:8000)。

部署完成后,获取 Ingress Controller 的外部访问地址:

kubectl get ingress -n djangoblog

将输出中的 ADDRESS(Ingress Controller 的 IP 或域名)填入本地浏览器或 DNS 解析即可访问博客首页。

步骤 6:首次运行的初始化操作

与 Docker Compose 部署类似,首次运行需要进入 DjangoBlog 应用的 Pod 执行数据库迁移、创建管理员等初始化操作。需要说明的是,仓库的 deploy/entrypoint.sh 在容器启动时已经自动执行了makemigrations、migrate、collectstatic --noinput、compress --force、build_index、compilemessages等命令,并最终以 gunicorn(--worker-class gevent)拉起应用;因此进入 Pod 后只需完成数据初始化与账号创建:

# 首先,获取 djangoblog pod 的名称 kubectl get pods -n djangoblog | grep djangoblog # 进入其中一个 Pod (将 [pod-name] 替换为上一步获取到的名称) kubectl exec -it [pod-name] -n djangoblog -- bash # 在 Pod 内部执行以下命令: # 创建超级管理员账户 (请按照提示操作) python manage.py createsuperuser # (可选) 创建测试数据 python manage.py create_testdata # (可选,如果启用了 ES) 创建索引 python manage.py rebuild_index # 退出 Pod exit

其中create_testdata与rebuild_index分别对应仓库 blog/management/commands 目录下的create_testdata.py与build_index.py管理命令;若你的部署未启用 Elasticsearch 索引,rebuild_index可跳过。

部署完成后的验证与运维提示

至此,DjangoBlog 已成功部署在 Kubernetes 集群上。可进一步做如下验证与运维操作:

  • 服务健康检查:直接访问任一 djangoblog Pod 的http://<pod-ip>:8000/health/,应返回{"status": "healthy", ...}的 JSON;该端点同时被 Deployment 探针持续监控,服务异常时 K8s 会自动重启或摘除流量。
  • 查看资源状态:kubectl get deploy,svc,pv,pvc,ingress -n djangoblog可一览所有资源;kubectl logs -n djangoblog <pod-name>用于排查 gunicorn 与应用日志。
  • 扩容与更新:由于应用镜像固定为liangliangyy/djangoblog:latest且imagePullPolicy: Always,可通过修改replicas或更新镜像完成滚动发布;配置变更只需修改 ConfigMap 后重新kubectl apply并滚动重启相关 Deployment。
  • 生产加固建议:将DJANGO_SECRET_KEY、MYSQL_ROOT_PASSWORD等敏感字段迁移至Secret并以secretKeyRef注入;同时建议为 Ingress 配置 TLS 证书(将server_name、443 监听等补充到 Nginx 配置与 Ingresstls段),并依据实际业务量调整各容器的资源limits。

小结

本文完整梳理了 DjangoBlog 在 Kubernetes 上的部署全流程:从 local-storage 本地 PV 的静态绑定、ConfigMap 驱动的环境变量与 Nginx 配置注入,到五大服务的 Deployment/Service 编排、健康探针设计与 Ingress 统一入口,最后完成首次运行的数据初始化。整套方案以 deploy/k8s 目录下的 YAML 文件为单一事实来源,既可整体kubectl apply一键部署,也可按需修改后复用,是理解“应用 + 中间件”云原生编排的完整实战样例。所有配置文件、入口脚本与健康检查接口均可在当前仓库中直接查阅与复用。

  • 后端
  • 前端
  • CMS

【免费下载链接】DjangoBlog

🍺基于Django的博客系统

项目地址:https://gitcode.com/gh_mirrors/dj/DjangoBlog
点击查看免费下载

相关推荐

上一篇:cc-mirror完全指南:如何创建隔离的Claude Code变体与自定义AI提供商
下一篇:llama-68m模型性能测试:CPU与昇腾NPU推理速度对比

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询