How can a password input be done in python with printing an asterisk for every character of the user?
See the first answer there :
What's the simplest way of detecting keyboard input in python from the terminal?
Just print stars '*' or anything when a key is pressed.
All credit obviously goes to Phylliida for the research.
You may want to look at how jupyter/ipython implemented this. I'm getting a dot displayed immediately for every character typed using getpass().
I wrote a module to illustrate roughly how you do it platform independently.
#!/usr/bin/python2def _masked_input_unix(prompt="Password: ", mask="*"): pw = "" # save terminal settings fd = sys.stdin.fileno() old = termios.tcgetattr(fd) new = termios.tcgetattr(fd) # setup 'cbreak' mode new[3] = new[3] & ~termios.ECHO new[3] = new[3] & ~termios.ICANON new[6][termios.VMIN] = '\x01' new[6][termios.VTIME] = '\x00' try: termios.tcsetattr(fd, termios.TCSADRAIN, new) print prompt, # Read the password while True: c = sys.stdin.read(1) # submit chars if c == '\r' or c == '\n': sys.stdout.write("%s" % (c)) break # delete chars elif c == '\b' or c == '\x7f': if len(pw) > 0: pw = pw[:-1] sys.stdout.write("%s" % ('\b \b')) # password chars else: pw += c sys.stdout.write("%s" % (mask)) finally: # ensure we reset the terminal termios.tcsetattr(fd, termios.TCSADRAIN, old) return pwdef _masked_input_win(prompt="Password: ", mask='*'): pw = "" while True: c = msvcrt.getch() # submit chars if c == '\r' or c == '\n': while msvcrt.kbhit(): msvcrt.getch() print break elif c == '\x03': raise KeyboardInterrupt # delete chars elif c == '\b' or c == '\x7f': if len(pw) > 0: pw = pw[:-1] msvcrt.putch('\b') msvcrt.putch(' ') msvcrt.putch('\b') # password chars else: pw += c msvcrt.putch(mask) return pw## initialize windows or posix function pointermasked_input = Nonetry: import msvcrt masked_input = _masked_input_winexcept ImportError: import sys, termios masked_input = _masked_input_unixif __name__ == "__main__": p = masked_input() print "Password is:", p
And this works for single-byte encodings. Adding unicode support is non-trivial. I suspect unicode doesn't work well with the getpass
module on Windows. (NOTE: it is not as simple as changing everything to unicode strings and using getwch()
)