Django постоянно не загружает css при развертывании
Я разворачивал простое приложение django в kubernetes и столкнулся с ошибкой невозможности загрузки css и js. Я несколько раз пытался изменить dockerfile, изменить путь к томам, но так и не смог исправить ситуацию.
Я потратил 1 неделю, но так и не нашел ошибку, может я что-то упустил?
Вот мои файлы и код
main/settings.py
BASE_DIR = Path(__file__).resolve().parent.parent
env.read_env(os.path.join(BASE_DIR, 'main/.env'))
....
STATIC_URL = '/static/'
STATIC_ROOT = '/app/static'
Dockerfile
# Use the official Python image as the base image
ARG ARCH=
FROM ${ARCH}python:3.12-slim as builder
WORKDIR /app
COPY requirements.txt .
RUN pip install --default-timeout=100 --no-cache-dir -r requirements.txt
COPY . .
FROM ${ARCH}python:3.12-slim
WORKDIR /app
COPY --from=builder /app /app
COPY --from=builder /usr/local/lib/python3.12/site-packages /usr/local/lib/python3.12/site-packages
COPY --from=builder /usr/local/bin /usr/local/bin
EXPOSE 8080
ENV PYTHONUNBUFFERED 1
# Specify the command to run your Django app
CMD ["gunicorn", "--workers=3", "--bind=0.0.0.0:8080", "main.wsgi:application" ]
deployment.yaml
apiVersion: v1
kind: PersistentVolume
metadata:
name: static-files-pv
spec:
capacity:
storage: 0.5Gi
accessModes:
- ReadWriteOnce
hostPath:
path: /mnt/static-files
storageClassName: do-block-storage
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: static-files-pvc
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 0.5Gi
storageClassName: do-block-storage
---
apiVersion: v1
kind: ConfigMap
metadata:
name: auth-db-config
data:
DB_NAME: auth
DB_HOST: patroni.default.svc.cluster.local
DB_PORT: "5432"
---
apiVersion: v1
kind: Secret
metadata:
name: auth-db-secret
type: Opaque
data:
DB_USER: Y***************y
DB_PASSWORD: S***************4=
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: auth
spec:
replicas: 1
selector:
matchLabels:
app: auth
template:
metadata:
labels:
app: auth
spec:
containers:
- name: auth
image: xxxx.com/auth/app:latest # my private registry
env:
- name: DB_NAME
valueFrom:
configMapKeyRef:
name: auth-db-config
key: DB_NAME
- name: DB_HOST
valueFrom:
configMapKeyRef:
name: auth-db-config
key: DB_HOST
- name: DB_PORT
valueFrom:
configMapKeyRef:
name: auth-db-config
key: DB_PORT
- name: DB_USER
valueFrom:
secretKeyRef:
name: auth-db-secret
key: DB_USER
- name: DB_PASSWORD
valueFrom:
secretKeyRef:
name: auth-db-secret
key: DB_PASSWORD
ports:
- containerPort: 8080
volumeMounts:
- name: static-files
mountPath: /app/static
volumes:
- name: static-files
persistentVolumeClaim:
claimName: static-files-pvc
imagePullSecrets:
- name: auth
---
apiVersion: v1
kind: Service
metadata:
name: auth
spec:
type: ClusterIP
selector:
app: auth
ports:
- protocol: TCP
port: 80
targetPort: 8080
ingress-nginx.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: web-ingress
annotations:
cert-manager.io/issuer: letsencrypt-nginx
nginx.ingress.kubernetes.io/rewrite-target: /
spec:
ingressClassName: nginx
tls:
- hosts:
- xxxx.com
secretName: letsencrypt-nginx
rules:
- host: xxxx.com
http:
paths:
- path: /static/
pathType: Prefix
backend:
service:
name: auth
port:
number: 80
- path: /
pathType: Prefix
backend:
service:
name: auth
port:
number: 80
Статический файл контейнера существует:
root@auth-7794b4dc86-h7ww4:/app# ls /app/static
admin rest_framework
root@auth-7794b4dc86-h7ww4:/app#
Удалите все ссылки на любые виды томов из этой установки. В спецификации Pod удалите volumes:
и volumeMounts:
, удалите PersistentVolumeClaim и удалите PersistentVolume.
При такой настройке, как у вас, Kubernetes берет содержимое из каталога /mnt/static-files
на хосте каждого узла - возможно, разные файлы на каждом узле, скорее всего, пустой каталог - и затем монтирует его поверх /app/static
в контейнере. Это скрывает любые статические файлы, которые могли быть встроены в образ (надеемся, из строки COPY . .
Dockerfile), которые будут включать ваши базовые Javascript и CSS активы.
Полагаю, вы пытаетесь воспроизвести установку, ориентированную на Docker Compose, которая пытается использовать именованный том Docker для передачи статических файлов в контейнер HTTP-прокси. Это ненадежно даже в Docker (может не работать, если у прокси тоже есть файлы в этом каталоге, будет игнорировать обновления базового образа, работает только с одним типом хранилища). В вашей системе Kubernetes вы используете объект Ingress для передачи HTTP-запросов /static/
вашему контейнеру, который обслуживает свои собственные статические активы, и это часто лучший подход.