New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
getpass.getpass() fails with non-ASCII characters in prompt #65368
Comments
getpass.getpass() fails with non-ASCII characters in prompt. The attached example scripts (for Python 2 and 3) contain non-ASCII unicode prompt (Polish "hasło" == English "password") written in UTF-8. $ ./getpass_test_python2
Traceback (most recent call last):
File "./getpass_test_python2", line 5, in <module>
getpass.getpass(u"Hasło: ")
File "/usr/lib64/python2.7/getpass.py", line 71, in unix_getpass
passwd = _raw_input(prompt, stream, input=input)
File "/usr/lib64/python2.7/getpass.py", line 128, in _raw_input
prompt = str(prompt)
UnicodeEncodeError: 'ascii' codec can't encode character u'\u0142' in position 3: ordinal not in range(128)
$ LC_ALL="en_US.UTF-8" ./getpass_test_python3
Hasło:
$ LC_ALL="C" ./getpass_test_python3
Traceback (most recent call last):
File "./getpass_test_python3", line 5, in <module>
getpass.getpass("Has\u0142o: ")
File "/usr/lib64/python3.4/getpass.py", line 78, in unix_getpass
passwd = _raw_input(prompt, stream, input=input)
File "/usr/lib64/python3.4/getpass.py", line 138, in _raw_input
stream.write(prompt)
UnicodeEncodeError: 'ascii' codec can't encode character '\u0142' in position 3: ordinal not in range(128)
$ |
Here is a patch which stops the breakage in getpass for python3. |
Version 2 of the patch with a test update. |
Updated patch with discovering of currect locale and corresponding test case. |
New patch with actual test case :) |
I don't think this is a bug. Any text output operation can fail when outputs unencodable string. You should use a stream with proper encoding and/or error handler. |
I agree that it is not a bug if the device where the prompt is shown simply does not support the characters; on Unix, this includes cases where the locale does not support the characters. Arfrever: when you say that it fails in Python 3 in a non-UTF-8 locale, which specific locale was that that it failed in? |
$ LC_ALL=en_US.iso88591 ./python -c "print('\u20ac')"
Traceback (most recent call last):
File "<string>", line 1, in <module>
UnicodeEncodeError: 'latin-1' codec can't encode character '\u20ac' in position 0: ordinal not in range(256)
$ LC_ALL=en_US.iso88591 ./python -c "input('\u20ac')"
Traceback (most recent call last):
File "<string>", line 1, in <module>
UnicodeEncodeError: 'latin-1' codec can't encode character '\u20ac' in position 0: ordinal not in range(256)
$ LC_ALL=en_US.iso88591 ./python -c "import getpass; getpass.getpass('\u20ac')"
Traceback (most recent call last):
File "<string>", line 1, in <module>
File "/home/serhiy/py/cpython/Lib/getpass.py", line 78, in unix_getpass
passwd = _raw_input(prompt, stream, input=input)
File "/home/serhiy/py/cpython/Lib/getpass.py", line 138, in _raw_input
stream.write(prompt)
UnicodeEncodeError: 'latin-1' codec can't encode character '\u20ac' in position 0: ordinal not in range(256) |
Martin v. Löwis: In this case, device support non-ASCII characters, but Python's getpass module forgets to properly encode string. Message 215697 contains example with C locale. |
Here is a new patch which uses stream.encoding instead getting the encoding from the locale as suggested by David. It also contains the new test. |
New patchset with updated test, now sending ascii stream into the call as argument. |
Arfrever: If you set the locale to C, the device does *not* (anymore) support the character. The terminal application you are using may, but the "system" does not. It only supports the characters available in the locale, which your character is not. There simply is no way in which Python *could* encode the character. |
New changeset f430fdd1628e by R David Murray in branch '3.4': New changeset 461f5863f2aa by R David Murray in branch 'default': |
Since we don't want the prompting for the password to fail, what we do in the patch is use the replace error handler so that you get as much as could be encoded of the prompt. (Note: this approach was reviewed by both Toshio and Marc Andre.) Thanks for the patch, Kushal. |
Ok. I wish the patch had a comment saying that, or better even a documentation change pointing out that feature. |
Ok, I'll reopen the issue to do that. |
Another patch with docs update and one line code comment. |
New changeset bdde36cd9048 by R David Murray in branch '3.4': New changeset fe532dccf8f6 by R David Murray in branch 'default': |
I decided to tweak the language slightly, Kushal. If this isn't what you were looking for, Martin, let me know. |
Note: these values reflect the state of the issue at the time it was migrated and might not reflect the current state.
Show more details
GitHub fields:
bugs.python.org fields:
The text was updated successfully, but these errors were encountered: