简体   繁体   中英

Writing invalid password to a text file

First time programming!!
I've created a password checker that first checks to see if the password is between 6 and 14 characters long. If it isn't, it asks the user to re input a password. Once accepted it, then checks the password strength and outputs whether the password is strong or weak. I am trying to figure out how to record every invalid password attempt to a text file . that records whether it was less than min_length or greater than max_length with date and time and I'm absolutely lost.

I have looked up many sites and tutorials for possible solutions but don't see a possible solution

MIN_PASSWORD_LENGTH = 6
MAX_PASSWORD_LENGTH = 14
password = input("Enter Your Password: ")
password_length = len(password)

while True:
    if password_length < MIN_PASSWORD_LENGTH:
        print("Password Rejected - Password must be between 6 and 14 characters long")
        password = input("Enter your password: ")
   elif password_length > MAX_PASSWORD_LENGTH:
        print("Password Rejected - Password must be between 6 and 14 characters long")
        password = input("Enter your password: ")
    else:
        print("Password Accepted")
        break

special = ['!','@','#','$','%','^','&','*','(',')']
letters_found = 0
digits_found = 0
specials_found = 0
for ch in password:
    if ch.isalpha():
        letters_found = 1
    if ch.isdigit():
        digits_found = 1
    if ch in special:
        specials_found = 1
    if digits_found and letters_found and specials_found:
        break

password_strength = letters_found + digits_found + specials_found
if password_strength >=2:
    message = "Password is Strong!"
else:
    message = ",Password is Weak!"
print("Your Password is",(password_length),"characters long.",(message))

Would like to be able record everytime a user enters an invalid password and record the date time, and the reason why it was invalid in this case less than 6 or greater than 14

I recommend the use of the logging module in Python :

import logging
logging.basicConfig(filename='example.log',level=logging.DEBUG)
logging.debug('This message should go to the log file')
logging.info('So should this')
logging.warning('And this, too')

Add this to your code where you want to log. You can use f-strings to modify these messages and log the password as well.

For a first time programming, this is actually really good code! In python, it is very easy to write text to a file and can be done with a 'with' statement. Because you are also looking to record the date, you can use pythons inbuilt datetime module for this. I don't know exactly the way you want to structure it, since it seems the data is related you could use a relational database like SQLite, but I will keep this simple with a text document. Change your code at the while True to the following:

with open("password_log.txt", 'a') as doc:
    date = datetime.now()
    dateString = datetime.strftime(date, "%m/%d/%Y %H:%M:%S")
    while True:
        if password_length < MIN_PASSWORD_LENGTH:
            doc.write("too short," + dateString + "\n")
            print("Password Rejected - Password must be between 6 and 14 characters long")
            password = input("Enter your password: ")
        elif password_length > MAX_PASSWORD_LENGTH:
            doc.write("too long," + dateString + "\n")
            print("Password Rejected - Password must be between 6 and 14 characters long")
            password = input("Enter your password: ")
        else:
            print("Password Accepted")
            break

Up the very top of your code include from datetime import datetime . Feel free to ask for any clarifications on what this does. This will get it to work at the bare minimum, also storing any logs in a CSV-like format.

This is an improve on NightShade's answer but also a general improve overall. This is your first time coding so congratulations. I'm modifying a few things in your code for readibility, organization, efficiency and also expandability and reusability.

If there's anything you'd like me to explain please ask. Additionally, I modified the way you calculate the strength of the password but it can easily be put back to your original one. EDIT: As other users have suggested, you shouldn't really store passwords. It's okay for an exercise but you should build a habit of protecting passwords. If you intend on creating a login system later on, consider hashing the password, storing it in a secure location and then comparing hashes inputs with the stored hash. It adds some protection.

from datetime import datetime # importing the date module
MIN_PASSWORD_LENGTH = 6
MAX_PASSWORD_LENGTH = 14

# Auxilliary Functions
# Enclosing in functions so that they can be reused, separated and organized

def passCheck(input_password):
    date = datetime.now() 
    # sets the current date and time

    dateString = datetime.strftime(date, "%m/%d/%Y %H:%M:%S") 
    # formats the string to look like m/d/t h:m:s

    if len(input_password) < MIN_PASSWORD_LENGTH:
    # Using text formatting for cleanliness and readibility

        return(f"{dateString} ==> Password is too short: '{input_password}' (length = {len(input_password)})\n") 
    elif len(input_password) > MAX_PASSWORD_LENGTH:
        return(f"{dateString} ==> Password is too long: '{input_password}' (length = {len(input_password)})\n")
    else:
        return 0


def letter_analysis(input_password):
    special = ['!','@','#','$','%','^','&','*','(',')']
    letters_found = 0
    digits_found = 0
    specials_found = 0
    test = 0
    for ch in input_password:
    #Checking for isdigit(), isalpha() etc but adding everytime it finds it. You can change this.

        test = test + 1*ch.isdigit() 
        letters_found += 1 * ch.isalpha()
        digits_found += 1 * ch.isdigit()
        specials_found += 2 * (ch in special) 
        # I would suggest adding 2, for example, as special characters should be valued more

    return((letters_found and digits_found and specials_found, letters_found+digits_found+specials_found))
    #Returning a tuple where first index will be True if letters, digits and specials exist, and second index is the count.
    #Note: The count isn't a True count, since I'm counting special characters twice


## Main function

def main():
    input_password = input("Enter your password: ")
    try:
        with open("password_attempts.txt", "a") as passFile: 
        # Opening text file as append, so that it doesn't erase what's there

            passFile.write(passCheck(input_password)) 
            #Passing it the result of the check function.

        print(passCheck(input_password))
    except TypeError:
        print("Password Accepted") 
        #In case the return is 0, there will be TypeError. This is the case where it's accepted.

    strength = letter_analysis(input_password) 
    #strength now holds the tuple.

    evaluation = strength[0] + strength[1] 
    # Just an example. This is where strength is calculated and directly related to the letter analysis.

    if evaluation > 5:
    # Here you can use your judgement. I said 5 again as an example.
        print(f"Password is strong: '{input_password}' (length/evaluation = {len(input_password)}/{evaluation})")
    else:
        print(f"Password is weak: '{input_password}' (length/evaluation = {len(input_password)}/{evaluation})")
    main()

main()

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM