PdfDing 1.14 Docker Compose 部署指南

在一台 Linux 服务器上用 Docker Compose 从零部署 PdfDing v1.14.1(SQLite 形态),覆盖镜像拉取、目录规划、管理员创建、功能验证与数据持久化运维的完整闭环。

PdfDingPdfDingPDF 处理DockerDocker Compose2026/10/30

PdfDing 1.14 Docker Compose 部署指南

目标:在一台 Linux 服务器上用 Docker Compose 从零部署自托管 PDF 管理平台 PdfDing(v1.14.1,SQLite 形态),完成镜像拉取、目录规划、管理员创建、功能验证、数据持久化与日常运维的完整闭环。全文命令与回显均在真实环境(Linux x86_64 服务器,Docker 29.9.2 + Docker Compose v5.6.1)实测通过,测试日期 2026-10-29。

一、环境信息

本次部署的目标软件与环境如下:

项目值
部署对象PdfDing v1.14.1(Codeberg 仓库当前最新稳定版,安全修复版本)
软件定位自托管 PDF 管理器/阅读器/编辑器(存储、打标签、批注、分享),详细介绍见 《PdfDing 介绍与选型指南》
官方镜像mrmn/pdfding(Docker Hub,amd64 / arm64 双架构)
服务器系统Linux x86_64
DockerServer 29.9.2(存储驱动 overlayfs)
Docker Composev5.6.1(v2 插件形态,docker compose 子命令)
访问方式http://127.0.0.1:8139(实验机本地访问;生产建议置于反向代理之后走 HTTPS)
数据形态SQLite(默认,无需外部数据库服务)
测试日期2026-10-29

💡 版本取证说明:PdfDing 主仓库已于 2026 年迁移至 codeberg.org/mrmn/PdfDing,GitHub 侧(github.com/mrmn2/PdfDing)为只读镜像。最新稳定版以 Codeberg Releases 页面的 releases/latest 重定向为准,本文撰写时指向 tag/v1.14.1。

二、镜像选型说明

2.1 官方镜像与 Tag 策略

PdfDing 官方只发布一个镜像:mrmn/pdfding(注意:不是 pdfding/pdfding,也不是 hrushi20/pdfding,检索 Docker Hub 时容易踩错名字)。镜像基于 python:3.12.15-alpine 构建,以非 root 用户 nonroot(uid/gid 1000)运行,同时提供 amd64 与 arm64 架构,可跑在 x86 服务器与树莓派/NAS 上。

Tag 选择建议:

Tag含义建议
v1.14.1固定版本生产推荐。升级节奏完全自控,回滚只需换回旧 tag
latest跟随最新发布仅测试环境使用;作者发布频繁(月均 1–2 版),latest 可能在无感知间引入行为变化

本次部署锁定 mrmn/pdfding:v1.14.1,拉取后镜像体积 271MB,digest 为 sha256:6ad300bacc1e1995d835ecee0352e1f0e5accade114d907cfc697d20e9ce22c8(2026-10-29 拉取实测)。

2.2 拉取镜像

docker pull mrmn/pdfding:v1.14.1

实测回显:

v1.14.1: Pulling from mrmn/pdfding
Digest: sha256:6ad300bacc1e1995d835ecee0352e1f0e5accade114d907cfc697d20e9ce22c8
Status: Downloaded newer image for mrmn/pdfding:v1.14.1
docker.io/mrmn/pdfding:v1.14.1

⚠️ 镜像加速器排障:若宿主 Docker 配置了带白名单的镜像加速器(如 daocloud 源),拉取非白名单镜像会报 this image in not exist 类错误。本次实验中 pdfding/pdfding(错误名字)与加速器前缀拉取均失败,改回官方全名 mrmn/pdfding 直连 docker.io 后成功。遇到拉取失败先确认镜像名,再检查加速器配置(/etc/docker/daemon.json 的 registry-mirrors)。

三、前置条件

部署前逐项确认:

  1. Docker 与 Compose 可用:
docker version --format 'Server: {{.Server.Version}}'
docker compose version

实测回显:

Server: 29.9.2
Docker Compose version v5.6.1
  1. 宿主端口未占用:容器内固定监听 8000,需要映射一个宿主端口。本文选 8139(可自行更换),先确认未被占用:
ss -ltn | grep 8139 || echo "8139 空闲"

实测回显(部署后复查,出现 LISTEN 即为映射成功):

LISTEN 0  4096  0.0.0.0:8139  0.0.0.0:*
LISTEN 0  4096  [::]:8139     [::]:*
  1. 目录规划:在宿主上规划数据根目录,本文统一使用 /opt/pdfding(请按你的服务器惯例调整),其下三个子目录分别承载数据库、媒体文件与 consume 自动导入目录。

  2. 访问协议决策:PdfDing 的 Cookie 安全标志与 CSRF 策略由环境变量控制。HTTP 直连试运行需显式关闭 CSRF_COOKIE_SECURE/SESSION_COOKIE_SECURE;生产走 HTTPS 时必须保持默认 TRUE。两套取值组合见 §7.2。

四、部署步骤

4.1 创建数据目录并修正属主

官方镜像以 uid/gid 1000(nonroot)运行,bind mount 的宿主目录必须对该 uid 可写,否则启动后上传、consume 导入等写盘操作会失败:

mkdir -p /opt/pdfding/{db,media,consume}
chown -R 1000:1000 /opt/pdfding

💡 chown 1000:1000 是 PdfDing 部署最容易漏掉的一步。宿主上通常没有名为 1000 的用户,属主显示为数字 1000 属正常现象。漏做的典型故障(consume 导入后删不掉源文件)见 §11.2。

4.2 编写 docker-compose.yaml

在 /opt/pdfding 下创建 docker-compose.yaml(以下为本次实测通过的最小可用配置,SECRET_KEY 请替换为你自己的长随机串):

name: pdfding-1.14.1-stack

networks:
  pdfding-net:
    driver: bridge
    ipam:
      config:
        - subnet: 10.89.68.0/24

services:
  pdfding:
    container_name: pdfding-1.14.1
    image: mrmn/pdfding:v1.14.1
    networks:
      - pdfding-net
    volumes:
      - ./db:/home/nonroot/pdfding/db
      - ./media:/home/nonroot/pdfding/media
      - ./consume:/home/nonroot/pdfding/consume
    environment:
      # 访问域名/IP,多个用逗号分隔;同时决定账号邮件里的链接
      - HOST_NAME=127.0.0.1
      # 容器内监听端口,映射到宿主 8139
      - HOST_PORT=8000
      # 会话与 CSRF 签名密钥,务必替换为长随机串
      - SECRET_KEY=please_change_me_to_a_long_random_string
      # HTTP 直连试运行才关闭;生产 HTTPS 必须删除这两行(默认 TRUE)
      - CSRF_COOKIE_SECURE=FALSE
      - SESSION_COOKIE_SECURE=FALSE
      # 演示用:验证邮件打印到容器日志;生产换 SMTP 并参见配置详解篇
      - ACCOUNT_EMAIL_VERIFICATION=TRUE
      - EMAIL_BACKEND=CONSOLE
      - LOG_LEVEL=INFO
      - DEFAULT_THEME=dark
      # consume 自动导入:开启后每 5 分钟扫描一次 consume 目录
      - CONSUME_ENABLE=TRUE
      - CONSUME_TAGS=自动导入
      - CONSUME_SCHEDULE=*/5 * * * *
    ports:
      - "8139:8000"
    restart: unless-stopped

配置要点:

  • name: pdfding-1.14.1-stack:显式指定 Compose 项目名,避免默认取目录名,多套环境并存时互不干扰;
  • 三个 bind mount 对应 PdfDing 仅有的三块持久化数据(§5 详解);
  • 环境变量是 PdfDing 唯一的配置入口,容器内没有可编辑的配置文件,完整变量清单见 《PdfDing 1.14 配置参数详解》。

4.3 启动服务

cd /opt/pdfding
docker compose up -d

实测回显:

[+] Running 2/2
 ✔ Network pdfding-1.14.1-stack_pdfding-net  Created
 ✔ Container pdfding-1.14.1                  Started

4.4 观察启动日志

docker logs pdfding-1.14.1

实测回显(首次启动完整日志):

Operations to perform:
  Apply all migrations: account, auth, contenttypes, mfa, pdf, sessions, socialaccount, users
Running migrations:
  No migrations to apply.
Cleaning up shared PDFs with a deletion date in the past.
[2026-10-29 16:18:45 +0000] [1] [INFO] Starting gunicorn 26.2.0
[2026-10-29 16:18:45 +0000] [1] [INFO] Listening at: http://0.0.0.0:8000 (1)
[2026-10-29 16:18:45 +0000] [1] [INFO] Using worker: gthread
[2026-10-29 16:18:45 +0000] [18] [INFO] Booting worker with pid: 18
[2026-10-29 16:18:46 +0000] [1] [INFO] Control socket listening at /home/nonroot/.gunicorn/gunicorn.ctl
Huey consumer started with 1 thread, PID 17 at 2026-10-29 16:18:47.523736
Scheduler runs every 10 second(s).
Periodic tasks are enabled.
The following commands are available:
+ huey.contrib.djhuey.tasks_backend.djtasks.run
+ pdf.tasks.consume_task

日志揭示了容器的启动序列(由镜像内置 entrypoint.sh 编排):数据库迁移 → 清理过期分享 → 启动 Huey 后台线程(仅当 CONSUME_ENABLE=TRUE)→ Gunicorn 监听 8000。看到 Listening at: http://0.0.0.0:8000 与 Huey consumer started 即代表服务就绪。

4.5 健康检查

curl -s -o /dev/null -w 'healthz: HTTP %{http_code}\n' http://127.0.0.1:8139/healthz
docker compose ps

实测回显:

healthz: HTTP 200

NAME             IMAGE                  COMMAND             SERVICE   CREATED          STATUS          PORTS
pdfding-1.14.1   mrmn/pdfding:v1.14.1   "./entrypoint.sh"   pdfding   19 minutes ago   Up 19 minutes   0.0.0.0:8139->8000/tcp, [::]:8139->8000/tcp

/healthz 返回 200 即服务可用,该端点适合接入负载均衡器或监控探针。浏览器打开 http://127.0.0.1:8139 可见登录页,页脚显示当前版本 v1.14.1。

4.6 创建管理员账号

首次部署没有任何账号。用容器内的 Django 管理命令创建超级管理员(邮件地址即登录用户名):

docker exec \
  -e DJANGO_SUPERUSER_EMAIL=admin@pdfding.local \
  -e DJANGO_SUPERUSER_PASSWORD=q1w2e3r4 \
  pdfding-1.14.1 \
  python pdfding/manage.py createsuperuser --noinput --username admin@pdfding.local

实测回显:

Superuser created successfully.

两点必须注意:

  1. --noinput 模式必须显式携带 --username,否则直接报错 CommandError: You must use --username with --noinput(实测踩坑)。密码以环境变量传入时绕过交互式的「弱口令校验」,生产环境请使用高强度密码;
  2. 本文配置 ACCOUNT_EMAIL_VERIFICATION=TRUE 时,新账号需持有「已验证邮箱」才能登录。命令行创建的超管没有邮箱记录,两种处理任选:改用登录页的 Sign up 走注册流程(验证邮件打印在容器日志里,EMAIL_BACKEND=CONSOLE 时从 docker logs 中取链接);或用容器内 shell 直接补一条已验证邮箱记录(详见 《PdfDing 1.14 常用 CLI 命令与工具详解》 §5)。

4.7 登录并上传首个 PDF

浏览器访问 http://127.0.0.1:8139,以 admin@pdfding.local / q1w2e3r4 登录,登录成功后 302 跳转到首页仪表盘。点击右上角 Add PDF 上传文件:表单中「名称」与「集合(Collection)」为必填项(集合是 v1.9.0 引入的组织维度,默认集合 default 可直接选用),「标签」为可选的逗号分隔字符串。上传成功后列表页即时出现该文件,缩略图、在线阅读、批注、分享等功能即可使用。

至此部署闭环完成。若某一环节失败,直接翻 §11 常见问题对照排障。

五、数据持久化说明

PdfDing 的全部持久化数据都落在 compose 中声明的三个 bind mount 上,理解每个目录的内容是备份与迁移的基础:

挂载(容器内路径)内容重要度
/home/nonroot/pdfding/dbdb.sqlite3(主库:用户、PDF 元数据、标签、分享记录)+ tasks.sqlite3(Huey 任务队列及 shm/wal 文件)核心
/home/nonroot/pdfding/media<用户ID>/default/pdf/(PDF 原文件)、previews/(预览图)、thumbnails/(缩略图)核心
/home/nonroot/pdfding/consumeconsume 自动导入的暂存目录(可放空目录)可选

部署后实测宿主目录结构(/opt/pdfding 下):

db/
├── db.sqlite3        # 主数据库(本文实验库约 430KB)
├── tasks.sqlite3     # Huey 队列
├── tasks.sqlite3-shm
└── tasks.sqlite3-wal
media/
└── 1/default/        # 用户ID=1 的存储空间
    ├── pdf/          # PDF 原文件(文件名保留原名)
    ├── previews/
    └── thumbnails/
consume/

备份策略(按停机窗口从简到繁):

  1. 冷备:docker compose stop 后整体打包 /opt/pdfding(db + media + compose 文件),docker compose start 恢复服务。SQLite 单文件特性让冷备极其可靠,适合个人实例;
  2. 文件级热备:不停服直接拷贝 media/ 与 db/db.sqlite3。SQLite 在写入瞬间拷贝有损坏风险,低写入频率的个人实例可接受,保险做法是用 manage.py shell 内的 SQLite 在线备份 API;
  3. 逻辑导出:python pdfding/manage.py dumpdata 导出 JSON(用法见 CLI 详解篇),配合 media 目录 rsync。

升级:改动 compose 中的 image tag(如 v1.14.1 → v1.15.0),docker compose pull && docker compose up -d,容器重建时启动序列会自动执行 migrate,bind mount 中的数据原样保留。升级前按冷备流程做一次全量备份。

六、环境变量表

下表汇总部署必需与常用的环境变量(值域与默认值来自官方文档站与 v1.14.1 源码 pdfding/settings/prod.py,逐项深入解释见 《PdfDing 1.14 配置参数详解》):

基础(general)

变量默认说明
HOST_NAME无(必填)访问域名/IP,逗号分隔多个;进入 Django ALLOWED_HOSTS 与 CSRF_TRUSTED_ORIGINS,并拼装账号邮件链接
HOST_PORT8000容器内监听端口,一般不动,靠 ports 映射改宿主端口
SECRET_KEY无(必填)会话/CSRF 签名密钥,长随机串;更换后所有登录会话失效
LOG_LEVELERROR日志级别(DEBUG/INFO/WARNING/ERROR)
ACCOUNT_EMAIL_VERIFICATIONTRUE邮箱验证策略;TRUE 强制验证后才可登录
DISABLE_USER_SIGNUPFALSETRUE 关闭自助注册(私有部署建议开启)
WORKERS / THREADS1 / 3Gunicorn worker 数与每 worker 线程数
WORKER_TIMEOUT30请求超时(秒)
DATA_DIR/home/nonroot/pdfding数据根目录,一般不动

安全(security)

变量默认说明
CSRF_COOKIE_SECURETRUECSRF Cookie 仅 HTTPS 传输;HTTP 试运行改 FALSE
SESSION_COOKIE_SECURETRUE会话 Cookie 仅 HTTPS 传输;HTTP 试运行改 FALSE
SECURE_SSL_REDIRECTFALSETRUE 强制 HTTP 301 到 HTTPS
SECURE_HSTS_SECONDS无HSTS 有效期(秒),生产建议 31536000
ACCOUNT_DEFAULT_HTTP_PROTOCOLhttps拼装邮件链接用的协议
MFA_USE_RECOVERY_CODES / MFA_USE_WEBAUTHNTRUE / TRUEMFA 恢复码 / WebAuthn 开关
MFA_TRUST_ENABLED / MFA_TRUST_COOKIE_AGEFALSE / 14「信任此浏览器」开关与天数

邮件(email)

变量默认说明
EMAIL_BACKENDCONSOLECONSOLE(打印到日志,测试用)或 SMTP
SMTP_HOST / SMTP_PORT无 / 587SMTP 服务器与端口
SMTP_USER / SMTP_PASSWORD无认证凭据
SMTP_USE_TLS / SMTP_USE_SSLFALSE二者互斥,只能开一个

数据库(databases)

变量默认说明
DATABASE_TYPESQLITESQLITE 或 POSTGRES;切 PostgreSQL 需增配 POSTGRES_HOST/NAME/USER/PASSWORD/PORT 并改用官方 postgres 编排

consume 自动导入(consumption)

变量默认说明
CONSUME_ENABLEFALSE开启 consume 目录定时导入
CONSUME_SCHEDULE*/5 * * * *扫描周期(cron 表达式)
CONSUME_TAGS无导入文件自动附加的标签(逗号分隔)
CONSUME_SKIP_EXISTINGTRUE同名同大小文件跳过

界面(customization)

变量默认说明
DEFAULT_THEMEdark新用户默认主题:light / dark / system(v1.7.0 起支持;旧变量 DEFAULT_THEME_COLOR 随 v1.13.0 移除主题色功能已失效)

💡 布尔值大小写均可:TRUE/True/true 等价(v1.6.3 起)。

七、配置参数说明

7.1 环境变量是唯一配置入口

PdfDing 没有挂载式配置文件——所有配置都通过容器环境变量注入,由 Django settings 在启动时读取。改配置的固定套路是「改 compose → docker compose up -d 重建容器」,无需进容器手改文件。

7.2 HOST_NAME 的三重作用(实测)

HOST_NAME 是最容易被低估的变量,它同时决定三件事:Django 允许的访问 Host 头、CSRF 信任来源、账号邮件中的链接域名。实测验证:将 HOST_NAME 从 127.0.0.1 改为 pdfding.lab.local 后重建容器,运行时配置随之变化:

改前(HOST_NAME=127.0.0.1):
ALLOWED_HOSTS = ['127.0.0.1']
CSRF_TRUSTED_ORIGINS = ['https://127.0.0.1', 'http://127.0.0.1']

改后(HOST_NAME=pdfding.lab.local):
DEFAULT_THEME = light
ALLOWED_HOSTS = ['pdfding.lab.local']
CSRF_TRUSTED_ORIGINS = ['https://pdfding.lab.local', 'http://pdfding.lab.local']

可见两条规律:ALLOWED_HOSTS 精确等于 HOST_NAME 列表;CSRF_TRUSTED_ORIGINS 自动为每个域名同时补齐 http:// 与 https:// 两条(源码行为,无需手动写协议前缀)。

7.3 HTTP / HTTPS 两套取值组合

场景必配组合
HTTP 直连试运行(本文实验形态)CSRF_COOKIE_SECURE=FALSE + SESSION_COOKIE_SECURE=FALSE
反向代理终结 TLS / 生产两项保持默认 TRUE;若代理强制跳转再加 SECURE_SSL_REDIRECT=TRUE、SECURE_HSTS_SECONDS=31536000、ACCOUNT_DEFAULT_HTTP_PROTOCOL=https

组合错配的典型症状:HTTP 访问时登录后立刻被弹回登录页(Secure Cookie 被浏览器丢弃)、或提交表单报 CSRF verification failed——对照 §11.4 排查。

7.4 运行时查看生效配置

无需重启即可核对容器内当前生效的配置:

# 查看注入的环境变量
docker exec pdfding-1.14.1 env | grep -E 'HOST_NAME|EMAIL_BACKEND|CONSUME'

# 查看经 Django 解析后的运行时配置
docker exec pdfding-1.14.1 python pdfding/manage.py shell -c \
  "from django.conf import settings; print(settings.ALLOWED_HOSTS, settings.EMAIL_BACKEND)"

实测回显:

EMAIL_BACKEND=CONSOLE
HOST_NAME=127.0.0.1

['127.0.0.1'] django.core.mail.backends.console.EmailBackend

八、配置文件挂载

PdfDing 没有可挂载的配置文件,但镜像暴露了三个功能性挂载点,语义务必区分清楚:

  1. /home/nonroot/pdfding/db——数据库目录。SQLite 形态下挂到空目录即可,首次启动自动建库; PostgreSQL 形态下此目录仅存 Huey 队列文件,主数据在 PostgreSQL 中;
  2. /home/nonroot/pdfding/media——文件存储。目录内部按 <用户ID>/default/{pdf,previews,thumbnails} 组织,不要手工往里放文件(绕过数据库的文件不识别、不展示);
  3. /home/nonroot/pdfding/consume——自动导入暂存区,唯一允许「从外部投放文件」的目录。向 consume/<用户ID>/ 放入 PDF,Huey 按 CONSUME_SCHEDULE 周期扫描、入库、打上 CONSUME_TAGS 标签,随后删除源文件。实测流程(向 consume/1/ 投放 second-doc.pdf,5 分钟内):
日志回显:
Importing 1 PDF(s) from the consume directory.
Processed 1 PDF(s) from the consume directory.

结果:PDF 出现在库中,标签为「自动导入」,consume/1/ 下源文件已删除

⚠️ consume 目录属主必须是 uid 1000:以 root 身份投放的文件容器内进程无法删除,会报 PermissionError: [Errno 13](见 §11.2)。扫码枪、网盘同步等外部投递链路务必保证落盘属主正确。

镜像内的应用代码(/home/nonroot/pdfding/ 其余部分)已随镜像烘焙,不支持也不需要挂载覆盖。

九、等价 docker run

不使用 Compose 时,上述部署等价于单条 docker run(与官方 Getting Started 文档的 docker 形态一致,补齐了 consume 挂载与自动导入变量):

docker run --name pdfding-1.14.1 \
    -p 8139:8000 \
    -v /opt/pdfding/db:/home/nonroot/pdfding/db \
    -v /opt/pdfding/media:/home/nonroot/pdfding/media \
    -v /opt/pdfding/consume:/home/nonroot/pdfding/consume \
    -e HOST_NAME=127.0.0.1 \
    -e SECRET_KEY=please_change_me_to_a_long_random_string \
    -e CSRF_COOKIE_SECURE=FALSE -e SESSION_COOKIE_SECURE=FALSE \
    -e ACCOUNT_EMAIL_VERIFICATION=TRUE -e EMAIL_BACKEND=CONSOLE \
    -e CONSUME_ENABLE=TRUE -e CONSUME_TAGS=自动导入 \
    -d \
    mrmn/pdfding:v1.14.1

Compose 形态相对 docker run 的优势:环境变量与挂载清单化、版本可审计、up -d 一键重建、项目级网络隔离。生产环境建议坚持 Compose(需要多容器时再叠加——例如 PostgreSQL 形态由官方 postgres.docker-compose.yaml 提供 app + db 双服务编排)。

十、常用运维命令

以下命令均在部署目录(/opt/pdfding)内执行:

# 服务状态总览
docker compose ps

# 跟踪日志(含账号邮件内容:EMAIL_BACKEND=CONSOLE 时)
docker compose logs -f

# 重启 / 停止 / 启动
docker compose restart
docker compose stop
docker compose start

# 改配置后的标准重建流程
docker compose up -d

# 升级版本(示例)
# 1) 编辑 docker-compose.yaml 将 image tag 改为目标版本
docker compose pull
docker compose up -d
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:8139/healthz

# 进入容器执行管理命令(CLI 全集见 CLI 详解篇)
docker exec pdfding-1.14.1 python pdfding/manage.py --help

# 完全卸载(含网络;数据目录按需保留或删除)
docker compose down
rm -rf /opt/pdfding/db /opt/pdfding/media /opt/pdfding/consume

补充说明:

  • docker compose down 只删容器与网络,不动 bind mount 数据;down -v 额外清理命名卷(本文用 bind mount,无命名卷可清);
  • 容器内管理命令的统一入口是 python pdfding/manage.py <子命令>,常用的建管理员、数据导出、健康自检等命令在 《PdfDing 1.14 常用 CLI 命令与工具详解》 中逐条实测讲解。

十一、常见问题

11.1 镜像拉取失败:名字错误或加速器白名单

症状:docker pull pdfding/pdfding 报 not found;或官方名经加速器拉取报 this image in not exist。 原因:镜像名不是 pdfding/pdfding(正确为 mrmn/pdfding);部分加速器只放行白名单镜像。 处理:使用全名 mrmn/pdfding:v1.14.1 直连拉取;仍失败则临时移除 registry-mirrors 后重试(见 §2.2)。

11.2 consume 导入成功但源文件不消失,日志报 PermissionError

实测日志:

PermissionError: [Errno 13] Permission denied: '/home/nonroot/pdfding/consume/1/second-doc.pdf'

原因:以 root 投放的文件属主为 0,容器内进程(uid 1000)读得了、删不掉。 处理:chown -R 1000:1000 /opt/pdfding/consume,下一轮扫描自动清理并恢复正常导入。数据库目录同理,首次部署时就应整体 chown(§4.1)。

11.3 访问报 400:DisallowedHost

实测日志:

django.core.exceptions.DisallowedHost: Invalid HTTP_HOST header: '127.0.0.1:8139'.
You may need to add '127.0.0.1' to ALLOWED_HOSTS.

原因:访问所用的域名/IP 不在 HOST_NAME 中(实测将 HOST_NAME 改成 pdfding.lab.local 后再以 127.0.0.1 访问即复现,healthz 探测返回 HTTP 400)。 处理:把实际访问的域名/IP(含端口前的主机部分)追加进 HOST_NAME(逗号分隔),docker compose up -d 重建。

11.4 HTTP 访问时无法登录或 CSRF 校验失败

症状:登录后刷新即掉线、或表单提交报 CSRF verification failed。 原因:CSRF_COOKIE_SECURE/SESSION_COOKIE_SECURE 保持默认 TRUE,浏览器在 HTTP 下拒绝回传 Cookie。 处理:HTTP 试运行将两项改为 FALSE(§7.3);生产务必走 HTTPS 并恢复 TRUE。

11.5 注册报「This password is too common.」

原因:登录页自助注册走 django-allauth 的密码强度校验,常见弱口令被拒(实测 q1w2e3r4 在注册页被拦截)。 处理:换强密码;或放弃自助注册,用 createsuperuser --noinput 建号(该路径跳过交互式校验)并配合 DISABLE_USER_SIGNUP=TRUE 收紧入口。

11.6 createsuperuser 报 You must use --username with --noinput

原因:--noinput 非交互模式必须显式提供用户名,用户名即邮箱。 处理:完整命令见 §4.6,凭据用 DJANGO_SUPERUSER_EMAIL/DJANGO_SUPERUSER_PASSWORD 环境变量传入。

11.7 账号密码正确却无法登录

原因:ACCOUNT_EMAIL_VERIFICATION=TRUE 下,未持有已验证邮箱的账号登录被拒。 处理:走注册流程自动发验证邮件(CONSOLE 后端时从 docker logs 里复制验证链接),或由管理员在容器内补已验证邮箱记录(见 CLI 详解篇 §5)。

11.8 容器内 dbshell 报 sqlite3 未安装

实测回显:

CommandError: You appear not to have the "sqlite3" program installed or on your path.

原因:官方镜像为 alpine 精简构建,未带 sqlite3 CLI。 处理:数据库操作改走 manage.py shell 的 ORM;宿主机上装有 sqlite3 时,也可直接只读打开挂载出来的 db/db.sqlite3。

十二、参考链接