0

I want to request a plaintext password when the user tries to close the script.

This is my code so far, the unrelated parts are hidden.

import signal
from time import sleep

_password = "iAmAdmin"


def _close(args):
    """Close the application."""
    if input("Preparing to close application.\n"
             "Please provide authentication password: ") == _password:
        print("Password correct. Application closing.")
        exit()
    else:
        print("Invalid password. Program will continue in 5 seconds.")
        sleep(5)


# Signal handler.
def sighandler(sig, frame):
    _close(None)


# Initiate the interface.
if __name__ == "__main__":
    signal.signal(signal.SIGINT, sighandler)
    clear()  # Function to clear the terminal.
    start()  # Display beginning help message.
    loop()  # An infinite loop requesting input and running functions.

When this script is run, and CTRL+C is pressed, this is the result:

Traceback (most recent call last):
  File "interface.py", line 96, in <module>
Preparing to close application.
Please provide authentication password:

And if SIGINT is sent again during this it closes silently. It should be ignored until the user inputs the correct password.

If the user does type the correct password, the application crashes:

Traceback (most recent call last):
  File "interface.py", line 96, in <module>
Preparing to close application.
Please provide authentication password: password
Invalid password. Program will continue in 5 seconds.
    loop()
  File "interface.py", line 67, in loop
    cmd = input(_prompt)
EOFError

Clearly there's something I'm missing. What is it?

Edit: By request, here is the code in the loop() function (contains line 67).

# All interface functionality below.
def loop():
    """Infinite loop that handles all interface commands."""
    while True:
        cmd = input(_prompt)  # Line 67.
        cmd, args = cmd.lower().split(" ", 1) if " " in cmd else (cmd, None)

        if cmd == "help":
            _help(cmds, args)
        elif cmd in cmds:
            cmds[cmd](args)
        else:
            print("Unrecognized command:", cmd, "\nType \"help\" for a list of commands.")

            suggestions = _suggest(cmds, cmd)

            if suggestions:
                print("\nDid you mean \"" + suggestions[0] + "\"?")

                if len(suggestions) > 1:
                    print("Similar commands:", ", ".join(suggestions[-1:]))
Jacob Birkett
  • 1,927
  • 3
  • 24
  • 49

1 Answers1

1
from getpass import getpass
from time import sleep
from os import system, name as os_name


def clear():
    system("cls") if os_name == "nt" else system("clear")


def close():
    try:
        clear()
        password = getpass("Please provide authentication password to close the application.")
        if password == "admin":
            print("Password correct. Closing application now.\n")
            exit()
        else:
            print("Password incorrect. Application continues in 5 seconds.")
            sleep(5)
    except (KeyboardInterrupt, EOFError):
        close()


def loop():
    while True:
        cmd = input("> ")
        if cmd == "close":
            close()
        else:
            print("Hello World!")


def main():
    clear()
    try:
        loop()
    except (KeyboardInterrupt, EOFError):
        close()
        main()


if __name__ == "__main__":
    main()
xaav
  • 7,876
  • 9
  • 30
  • 47