如何通过命令行向FastAPI应用传参以指定不同.env配置文件
实现指定env配置文件的操作步骤
你可以通过两种方案实现需求,推荐优先使用第一种方案,配置更简单且后续维护成本更低。
方案1:通过systemd环境变量传递配置文件名(推荐)
步骤1:修改FastAPI应用的dotenv加载逻辑
把原来硬编码写死的.env路径,改为优先读取系统环境变量指定的文件,默认保留原来的.env作为 fallback:
import os from dotenv import load_dotenv # 优先读取系统环境变量ENV_FILE指定的配置文件,未传的话默认用.env env_file_path = os.getenv("ENV_FILE", ".env") load_dotenv(env_file_path) # 后续原有FastAPI逻辑保持不变
步骤2:修改两个systemd单元文件
注意两个单元文件需要用不同的命名(比如my_app_prod.service和my_app_dev.service),且监听的socket路径/端口必须不同,避免冲突。
- 生产环境单元文件
my_app_prod.service示例:
[Unit] Description=Gunicorn instance for my_app prod After=network.target [Service] User=nginx Group=nginx WorkingDirectory=/usr/share/nginx/html/my_app/ Environment="PATH=/usr/share/nginx/html/my_app/venv/bin" # 新增该行指定生产环境配置文件 Environment="ENV_FILE=.env.prod" # 注意socket路径和测试环境区分开 ExecStart=/usr/share/nginx/html/my_app/venv/bin/gunicorn --bind unix:/usr/share/nginx/html/my_app/my_app_prod.sock -w 4 -k uvicorn.workers.UvicornWorker app.main:app [Install] WantedBy=multi-user.target
- 测试环境单元文件
my_app_dev.service示例:
[Unit] Description=Gunicorn instance for my_app dev After=network.target [Service] User=nginx Group=nginx WorkingDirectory=/usr/share/nginx/html/my_app/ Environment="PATH=/usr/share/nginx/html/my_app/venv/bin" # 新增该行指定测试环境配置文件 Environment="ENV_FILE=.env.dev" # 注意socket路径和生产环境区分开 ExecStart=/usr/share/nginx/html/my_app/venv/bin/gunicorn --bind unix:/usr/share/nginx/html/my_app/my_app_dev.sock -w 4 -k uvicorn.workers.UvicornWorker app.main:app [Install] WantedBy=multi-user.target
步骤3:生效配置启动服务
# 重载systemd配置 systemctl daemon-reload # 启动两个服务 systemctl start my_app_prod my_app_dev # 如需开机自启执行 systemctl enable my_app_prod my_app_dev
方案2:通过命令行参数传递配置文件名(符合你预想的实现方式)
步骤1:修改FastAPI应用增加命令行参数解析
在应用入口文件中新增参数解析逻辑,接收--env_file_name参数:
import argparse from dotenv import load_dotenv # 解析命令行参数 parser = argparse.ArgumentParser() parser.add_argument("--env_file_name", default=".env", help="指定.env配置文件路径") args = parser.parse_args() # 加载指定的配置文件 load_dotenv(args.env_file_name) # 后续原有FastAPI逻辑保持不变
步骤2:修改systemd单元文件的ExecStart配置
注意参数必须放在app.main:app之后,放在gunicorn自有参数之前会被gunicorn识别为无效参数报错,同时注意两个服务的socket路径/端口要区分开:
- 生产环境ExecStart配置:
ExecStart=/usr/share/nginx/html/my_app/venv/bin/gunicorn --bind unix:/usr/share/nginx/html/my_app/my_app_prod.sock -w 4 -k uvicorn.workers.UvicornWorker app.main:app --env_file_name=".env.prod"
- 测试环境ExecStart配置:
ExecStart=/usr/share/nginx/html/my_app/venv/bin/gunicorn --bind unix:/usr/share/nginx/html/my_app/my_app_dev.sock -w 4 -k uvicorn.workers.UvicornWorker app.main:app --env_file_name=".env.dev"
步骤3:生效配置启动服务
和方案1的第三步操作完全一致。
内容的提问来源于stack exchange,提问作者Mecid X Recebli
相关产品推荐
相关产品推荐

