# 正念 APP(后端) 本目录为正念 APP 的后端服务(FastAPI),负责: - 提供业务 API(情绪文案/卡片、用户配置、推送配置等) - 支撑定时任务(推送、内容刷新等) - 对接数据库与缓存(MySQL / Redis) > 说明:当前 `server/` 目录仅包含说明文档,尚未初始化具体代码与依赖文件。本文档按“推荐工程形态”编写,等代码落地后只需把入口模块名与配置字段名对齐即可。 ## 技术栈 - Python + FastAPI - SQLAlchemy(建议 2.x,异步)+ MySQL 8.0 - Alembic(数据库迁移) - Celery + Redis(任务调度/定时推送) - Pydantic v2(数据校验)+ pydantic-settings(环境配置) - pytest(测试) ## 本地开发 ### 1. 环境要求 - Python:3.11+ - MySQL:8.0+ ### 2. 创建虚拟环境 在 `server/` 目录下: ```bash python -m venv .venv source .venv/bin/activate python -m pip install -U pip ``` ### 3. 安装依赖 - 方式 :`requirements.txt`(示例) ```bash pip install -r requirements.txt ``` ## 配置(dev / prod) 推荐使用 `.env.dev` 与 `.env.prod`,由 `pydantic-settings` 读取。 ### 1. 环境变量示例 在 `server/` 下创建 `.env.dev`(示例字段,可按代码中的 Settings 字段名调整): ```dotenv # 运行环境 APP_ENV=dev APP_NAME=mindfulness-server APP_HOST=0.0.0.0 APP_PORT=8000 # 数据库(推荐用统一的 DATABASE_URL,或拆分为 MYSQL_*) DATABASE_URL=mysql+aiomysql://<用户名>:<密码>@:3306/mindfulness_dev?charset=utf8mb4 # MYSQL_HOST=127.0.0.1 # MYSQL_PORT=3306 # MYSQL_USER=root # MYSQL_PASSWORD=password # MYSQL_DB=mindfulness_dev # Redis(缓存/任务队列) REDIS_URL=redis://dev_user:devpassword@127.0.0.1:6379/0 最大的存储限制是256 请尽量少使用 # Celery(建议先只用 broker;如需结果存储请务必设置 TTL) CELERY_BROKER_URL=redis://dev_user:devpassword@127.0.0.1:6379/0 # CELERY_RESULT_BACKEND=redis://dev_user:devpassword@127.0.0.1:6379/0 # 推送/第三方(按实际接入补充) # PUSH_PROVIDER=expo # EXPO_ACCESS_TOKEN= ``` `.env.prod` 同理,替换为生产环境地址与密钥即可。 ### 1.1 MySQL 命名与 dev/pro 区分(约定) - **生产库(prod)**:`mindfulness` - **开发库(dev)**:`mindfulness_dev` 建议: - **库名/表名/字段名**:统一小写 + 下划线(snake_case) - **字符集**:统一 `utf8mb4` `.env.dev` 指向 `mindfulness_dev`,`.env.prod` 指向 `mindfulness`: ```dotenv # prod 示例 DATABASE_URL=mysql+aiomysql://<用户名>:<密码>@:3306/mindfulness?charset=utf8mb4 ``` ### 1.2 Redis:通过 ACL 限制 dev/pro 前缀访问 只启动 **一个 Redis 服务**,用 **ACL + key 前缀**隔离环境数据: ```text # Dev 用户,只能访问 dev:* 前缀 user dev_user on >devpassword ~dev:* +@all # Pro 用户,只能访问 pro:* 前缀 user pro_user on >propassword ~pro:* +@all ``` 连接串示例(dev/pro 使用不同账号): ```dotenv # dev REDIS_URL=redis://dev_user:devpassword@127.0.0.1:6379/0 CELERY_BROKER_URL=redis://dev_user:devpassword@127.0.0.1:6379/0 # prod # REDIS_URL=redis://pro_user:propassword@127.0.0.1:6379/0 # CELERY_BROKER_URL=redis://pro_user:propassword@127.0.0.1:6379/0 ``` 重要约定: - **应用写入 Redis 的 key 必须带前缀**:dev 环境使用 `dev:`,prod 环境使用 `pro:` - **Celery 队列/键也建议带环境前缀**(例如队列名 `dev:push` / `pro:push`),避免同机多环境混用时相互影响 ### 2. 配置加载约定(建议) - 通过 `APP_ENV` 决定加载 `.env.dev` 或 `.env.prod` - 代码中使用 `pydantic-settings` 定义 `Settings`,并集中在 `app/core/config.py`(仅建议命名) ## 启动服务(FastAPI) > 下方入口模块名为示例:假设你的 FastAPI 实例位于 `app/main.py` 中的 `app` 变量。若实际路径不同,请自行替换。 ```bash uvicorn app.main:app --host 0.0.0.0 --port 8000 --reload ``` 启动后可访问: - OpenAPI 文档:`/docs` - ReDoc:`/redoc` ## 数据库迁移(Alembic) > 若你采用 Alembic:建议把迁移脚本放在 `server/alembic/`,并在 `alembic.ini` 中配置数据库连接(或从环境变量读取)。 常用命令(示例): ```bash alembic revision --autogenerate -m "初始化表结构" alembic upgrade head ``` ## 任务调度(Celery + Redis) > 下方入口模块名为示例:假设 Celery 实例位于 `app/worker.py` 中的 `celery_app` 变量。若实际路径不同,请自行替换。 启动 Worker(处理异步任务): ```bash celery -A app.worker:celery_app worker -l info ``` 启动 Beat(定时任务调度,若你使用 celery beat): ```bash celery -A app.worker:celery_app beat -l info ``` ## 运行测试(pytest) ```bash pytest -q ``` ## 推荐目录结构(建议) > 仅为建议,便于后续协作与扩展。 ```text server/ app/ main.py # FastAPI 入口(app = FastAPI()) core/ config.py # Settings(pydantic-settings) logging.py db/ session.py # 数据库会话/引擎 models/ # ORM 模型 migrations/ # (如不使用默认 alembic 目录,可自定义) api/ v1/ routes/ tasks/ push.py # 推送相关任务 worker.py # Celery 入口(celery_app = Celery(...)) tests/ README.md ``` ## 常见问题 - **MySQL 连接报错/字符集问题**:建议统一使用 `utf8mb4`,并在连接串中带上 `charset=utf8mb4`。 - **Celery 无法连接 Redis**:检查 `CELERY_BROKER_URL` 与 Redis 是否可达、端口是否开放。