15.5. getpass — 安全的密码输入

未匹配的标注

目标:提示用户输入值,通常是密码,而不会在控制台上显示它们的值。

许多需要通过终端与用户交互的程序需要像用户询问密码但又不能在屏幕上显示用户输入的字符。getpass 模块提供了安全处理此类密码提示的简便方式

示例

getpass() 函数打印一个提示符,然后读取用户输入直到按下回车。输入值以字符串返回给调用者。

getpass_defaults.py

import getpass

try:
    p = getpass.getpass()
except Exception as err:
    print('ERROR:', err)
else:
    print('You entered:', p)

如果没有指明,默认提示符为“Password:”。

$ python3 getpass_defaults.py

Password:
You entered: sekret

提示符可以改变为任何所需的值。

getpass_prompt.py

import getpass

p = getpass.getpass(prompt='What is your favorite color? ')
if p.lower() == 'blue':
    print('Right.  Off you go.')
else:
    print('Auuuuugh!')

一些程序为了提供更好的安全性,要求输入通行码(pass phrase)而不是一个简单的密码。

$ python3 getpass_prompt.py

What is your favorite color?
Right.  Off you go.

$ python3 getpass_prompt.py

What is your favorite color?
Auuuuugh!

默认情况下,getpass() 使用 sys.stdout 来打印提示符。如果程序想在 sys.stdout 上产生有用的输出,把提示符发送到其他流比如 sys.stderr 是更好的办法。

getpass_stream.py

import getpass
import sys

p = getpass.getpass(stream=sys.stderr)
print('You entered:', p)

使用 sys.stderr 作为提示符显示流可以在输出被重定向(到管道或文本)而不会看到密码提示符。用户输入的值还是不会被显示在屏幕上。

$ python3 getpass_stream.py >/dev/null

Password:

在非终端种使用 GetPass

在 Unix 下 getpass() 总是需要一个可以通过 termios 控制的终端,这样它才能控制不显示密码。着意味着它不能读取从非终端流重定向到标准输入的值。不过 getpass 会尝试获取进程的的 tty,如果能访问则不会报错。

$ echo "not sekret" | python3 getpass_defaults.py

Password:
You entered: sekret

使用哪种方法,取决于调用者如何检测输入流是否为一个 tty,以及在哪种情况下使用备选方案。

getpass_noterminal.py

import getpass
import sys

if sys.stdin.isatty():
    p = getpass.getpass('Using getpass: ')
else:
    print('Using readline')
    p = sys.stdin.readline().rstrip()

print('Read: ', p)

有 tty:

$ python3 ./getpass_noterminal.py

Using getpass:
Read:  sekret

没有 tty:

$ echo "sekret" | python3 ./getpass_noterminal.py

Using readline
Read:  sekret

参见

本文章首发在 LearnKu.com 网站上。

本译文仅用于学习和交流目的,转载请务必注明文章译者、出处、和本文链接
我们的翻译工作遵照 CC 协议,如果我们的工作有侵犯到您的权益,请及时联系我们。

原文地址:https://learnku.com/docs/pymotw/getpass-...

译文地址:https://learnku.com/docs/pymotw/getpass-...

上一篇 下一篇
讨论数量: 0
发起讨论 只看当前版本


暂无话题~