将秘密(密码)存储在单独的文件中

问题描述 投票:0回答:5

存储 Python 脚本的应用程序机密(密码、访问令牌)的最简单方法是什么?我以为这会是一个像 Ruby 中那样的

*.yml
文件,但令人惊讶的是我发现事实并非如此。那么到底是什么呢?最简单的解决方案是什么?

我想将它们放在一个单独的文件中,因为这样我就无法将该文件推送到 GitHub 存储库。

python configuration settings
5个回答
117
投票

我认为将凭据存储在另一个 *py 文件中是最安全的选择。然后只需导入它即可。例子看起来像这样

配置.py

username = "xy"
password = "abcd"

主.py

import config
login(config.username, config.password)

18
投票

我正在处理完全相同的问题,实际上最终得到了与kecer建议的相同的解决方案。由于我需要在数十个脚本中使用它,因此我创建了自己的库。让我与您分享这个解决方案。

credlib.py——处理凭证的通用库

class credential: def __init__(self, hostname, username, password): self.hostname = hostname self.username = username self.password = password

mycredentials.py——我的本地文件,用于存储所有凭据

from credlib import credential sys_prod = credential("srv01", "user", "pass") sys_stg = credential("srv02", "user", "pass") sys_db = credential("db01", "userdb", "passdb")

mysystemlib.py -- 这是访问我的系统的通用库(支持新凭证系统和旧凭证系统)

from credlib import credential def system_login(*args): # this is new function definition #def system_login(hostname, username, password): # this was previous function definition if len(args) == 1 and isinstance(args[0], credential): hostname = args[0].hostname username = args[0].username password = args[0].password elif len(args) == 3: hostname = args[0] username = args[1] password = args[2] else: raise ValueError('Invalid arguments') do_login(hostname, username, password) # this is original system login call

main.py——结合凭证和系统库的主脚本

from mycredentials import sys_stg, sys_db import mysystemlib ... mysystemlib.system_login(sys_stg)
请注意,旧的主机名/用户名/密码方式仍然有效,因此不会影响旧脚本:

mysystemlib.system_login("srv02", "user", "pass")
这有很多好处:

    我们所有的 Python 脚本都使用相同的凭证系统
  • 带密码的文件是分开的(文件可以有更严格的权限)
  • 文件不存储在我们的 git 存储库中(通过
  • .gitignore
     排除),以便我们的 python 脚本/库可以与其他人共享而无需暴露凭据(每个人都在本地文件中定义自己的凭据)
  • 如果需要更改密码,我们仅在一个地方进行

13
投票
我个人更喜欢使用 yaml 文件和 pyyaml 库。 此处的文档:

https://pyyaml.org/wiki/PyYAMLDocumentation

创建

.gitignore

规则非常快速且轻松,并且犯错误的可能性为零。您可以在类似 Linux / UNIX 的系统上使用 echo 添加规则:

echo -e '*.yaml\n*.yml' >> .gitignore
下面是从阅读器同一文件夹/位置的设置 .yaml 文件中检索设置的示例。

代码片段:

#!/usr/bin/env python3 import yaml from pathlib import Path def get_settings(): full_file_path = Path(__file__).parent.joinpath('settings.yaml') with open(full_file_path) as settings: settings_data = yaml.load(settings, Loader=yaml.Loader) return settings_data
    

2
投票
在这里回答可能有点晚了,但我仍然想分享我认为更容易做并且也不需要太多编码的方式。

使用 ini 文件来存储你的秘密,如下所示:

[section_name] key1 = value1 key2 = value2
然后使用 

configparser 库读取 ini 文件并从中提取不同的值。

除此之外,如果您只有几个变量需要使用,那么我认为使用 .env 文件也应该有效。

在上述两种方法中,您只需在 .gitignore 文件中添加 *.ini 或 *.env 即可确保您的机密不会被偷偷上传到 github 上。


0
投票
请不要依赖 gitignore 将文件保留在您的存储库之外。 很容易犯错误,突然之间,您的密码变成纯文本,全世界都可以看到(如果是公共存储库)。 然后,当您意识到这一点时,您将删除该文件 - 但可能没有意识到历史记录仍然保留着它。 您也可能忘记更改密码,因此,如果有人在您删除密码之前已经获得了密码,您仍然容易受到攻击。 至少,对它们进行加密。 您仍然存在在哪里存储解密密钥的问题,但至少多了一层保护(隐匿性安全)。

操作系统环境变量在某些方面更好,但也不是很安全。 系统管理员可以看到它们,任何能够运行命令的人都可以执行“env”命令来获取所有它们。 由于这个原因(以及其他原因),运行远程命令对于不良行为者来说始终是一个很高的奖励。

如果您的组织有企业密码管理器,那就是显而易见的答案。 如果没有,也许创建一个免费的 AWS 帐户并使用他们的“Secrets Manager”服务(或 Microsoft 或 Google - 他们都有这种能力并且被认为非常安全)。

只是有点题外话,不要把秘密放在命令行上。 当进程运行时,“ps”命令将显示秘密。 进程停止后,有“history”命令。

© www.soinside.com 2019 - 2024. All rights reserved.