我正在关注功能完整的Youtube教程Web应用程序,而应用程序工厂存在问题。根据我的理解,我需要将诸如SECRET_KEY和SQLALCHEMY_DATABASE_URI之类的敏感信息放入环境变量中。在视频中,创建者正在Mac上工作,他打开了.bash_profile文件并添加了以下几行(我将实际值留空):
export SECRET_KEY='....'
export SQLALCHEMY_DATABASE_URI='......'
我正在使用Windows,但无法在计算机中找到.bash_profile文件,因此我转到控制面板并设置了新的环境变量SECRET_KEY和SQLALCHEMY_DATABASE_URI。然后,像在视频中一样,在config.py
中创建此类Configclass Config:
SECRET_KEY = os.environ.get('SECRET_KEY')
SQLALCHEMY_DATABASE_URI = os.environ.get('SQLALCHEMY_DATABASE_URI')
MAIL_SERVER = 'smtp.gmail.com'
MAIL_PORT = 587
MAIL_USE_TLS = True
MAIL_USERNAME = os.environ.get('EMAIL_USER')
MAIL_PASSWORD = os.environ.get('EMAIL_PASSWORD')
然后,我运行了我的应用程序,但出现了一条错误消息“必须使用密钥才能使用CSRF。”,所以我认为我的flask应用程序无法获取我设置的SECRET_KEY或其他环境变量。在我在 init .py中拥有这些配置之前,该应用程序运行良好,但是现在,当我将这些配置移至config.py中的对象内部时,它停止运行。
根据我的理解,export
是创建环境变量的命令,因此我认为在.bash_profile文件中导出这些变量等同于设置环境变量。
为解决我的问题,我尝试通过创建.env文件来遵循本教程(https://blog.miguelgrinberg.com/post/the-flask-mega-tutorial-part-xv-a-better-application-structure)。在命令提示符下,我运行了
pip install python-dotenv
在Config.py中,我添加了
from dotenv import load_dotenv
basedir = os.path.abspath(os.path.dirname(__file__))
load_dotenv(os.path.join(basedir, '.env'))
我以为这会创建一个.env文件,我可以在其中存储环境变量,但是它什么也没做,因此我在目录中看不到任何.env文件。有人可以帮帮我吗 ?我有几个问题:
我需要添加/修复哪些内容才能使应用程序正常工作?
是否设置环境变量并将其导出为相同?如果没有,在设置环境变量后如何导出环境变量,以便我的应用程序可以正常工作?
在.env文件中存储环境变量与在“控制面板”中设置环境变量有何不同?因为当我尝试在Google上搜索“在Windows中编辑.env文件”时,出现了“添加环境变量”之类的结果。
.bash_profile和.env文件有什么区别?我运行了man bash
,它说.bash_profile是The personal initialization file, executed for login shells
,但是我不知道这是否意味着它与.env文件完全不同。
答案 0 :(得分:1)
设置环境变量的问题
从控制面板是用于程序检测
这些变量中的更改需要关闭并重新打开。
但是,当您运行程序时,它会继承环境变量
从其父进程。因此,您也需要关闭它,然后一直进行到explorer.exe
。所以有点棘手。
所以您需要采用其他方法。
您可以为命令行会话设置环境变量
在Windows上使用set
命令
(export
在Windows上不存在。
set "SECRET_KEY=really secret don't tell anyone"
然后检查它是否真的设置了:
echo %SECRET_KEY%
应打印really secret don't tell anyone
。或者,您可以只使用set
命令而不带任何参数,这将打印所有环境变量。
以这种方式设置所有环境变量后,运行您的应用程序:
# app.py
from flask import Flask
import config
app = Flask(__name__)
@app.route('/')
def home():
return 'secret is ' + config.SECRET_KEY
app.run()
# config.py
from os import getenv
SECRET_KEY = getenv('SECRET_KEY', None)
assert SECRET_KEY # make sure app doesn't run without this value
运行它:
python config.py
输出:
really secret don't tell anyone
现在您可以从其他文件中导入config.py
。
要注意的一件事是,一旦关闭该cmd窗口,
这些环境值将未设置。
因此,如果打开新的命令行窗口,则需要重新输入它们。
或者,您可以在“控制面板”中设置值,然后新的cmd窗口会自动继承这些值(类似于.bashrc
文件)。
.env
文件另一种方法是在项目的根文件夹中创建一个.env
文件,
这是一个格式如下的文本文件
SECRET_KEY=really secret dont tell anyone
SQLALCHEMY_DATABASE_URI=sqlite:///app.db
文件夹结构:
.
├── .env
├── config.py
├── app.py
您必须不提交,并且必须这样做
与其他源文件一起共享这些.env
文件。
因为这样在源代码中不对配置进行硬编码有什么意义,对吧?
要导入这些值,您需要对其进行解析并将其注入到应用程序环境中。
对于Python,您可以使用python-dotenv
库。
现在我们可以将config.py
更改为:
# config.py
from os import getenv
from dotenv import load_dotenv
load_dotenv()
SECRET_KEY = getenv('SECRET_KEY', None)
assert SECRET_KEY
# use the key
print(SECRET_KEY)
这将使我们能够从两个.env
文件中加载配置
以及环境变量。
一种常见的模式是使用未填充的键制作一个.env.sample
文件,以提醒管理员正在设置应用程序以填充这些值。
# .env.sample
SECRET_KEY=
SQLALCHEMY_DATABASE_URI=
现在,关于您的问题:
正在设置环境变量并将其导出 相同 ?如果没有,如何导出环境变量 设置环境变量后,我的应用程序可以工作吗?
“导出”环境变量与从控制面板进行设置相同。 两种方法都是从源代码中删除机密的方法。我已经在上面解释了两种方法来使您的应用程序正常工作。
在.env文件中存储环境变量与在“控制面板”中设置环境变量有何不同?因为当我尝试在Google上搜索“在Windows中编辑.env文件”时,会出现诸如“添加环境变量”之类的结果。
在.env
文件中存储环境变量有点容易出错,因为服务器配置错误很小,
您可能会向所有人公开这些秘密。
通过用set
/ export
设置它们,您可以关闭该漏洞(如果黑客设法接管了您的应用程序,则仍然可以获取这些漏洞,因为如果您注意到我们可以使用{{ 1}}函数)。
.bash_profile和.env文件有什么区别?我运行了man bash,它说.bash_profile是为登录shell执行的个人初始化文件,但是我不知道这是否意味着它与.env文件完全不同。
Bash是UNIX系统中流行的shell应用程序。 getenv
是每次您打开终端时都会执行的文件。
因此,当您向其中添加.bashrc
命令时,打开的每个终端都将有效地设置那些环境变量。