2013-05-23 3 views
5

Я пытаюсь создать систему, требующую ввода пароля. Если он все нижний, верхний или номер, тогда напечатайте слабые, если это два из условий, то это медь, и если все были выполнены, это сильно. Он просто не работает.Проверка силы пароля (как проверить условия)

Слабая и сильная работа, однако среда не работает.

Я не знаю, где я поступил неправильно.

def password(): 

    print ('enter password') 
    print() 
    print() 
    print ('the password must be at least 6, and no more than 12 characters long') 
    print() 

    password = input ('type your password ....') 


    weak = 'weak' 
    med = 'medium' 
    strong = 'strong' 

    if len(password) >12: 
     print ('password is too long It must be between 6 and 12 characters') 

    elif len(password) <6: 
     print ('password is too short It must be between 6 and 12 characters') 


    elif len(password) >=6 and len(password) <= 12: 
     print ('password ok') 

     if password.lower()== password or password.upper()==password or password.isalnum()==password: 
      print ('password is', weak) 

     elif password.lower()== password and password.upper()==password or password.isalnum()==password: 
      print ('password is', med) 

     else: 
      password.lower()== password and password.upper()==password and password.isalnum()==password 
      print ('password is', strong) 
+1

AFAIK isalnum() возвращает логическое значение, так что никогда не будет равным пароль – pypat

ответ

4

password.isalnum() возвращает логическое значение, так password.isalnum()==password будет всегда быть False.

Просто опустить ==password часть:

if password.lower()== password or password.upper()==password or password.isalnum(): 
    # ... 

Далее, он может никогда быть как все верхние и нижние, или все верхние и номера или все ниже и все числа, так что второе условие (среда) невозможно. Возможно, вам стоит искать наличие примерно прописных, строчных и цифр вместо этого?

Однако, первая проблема. Вы тестируете, если пароль alphanumeric, состоящий только из символов и/или цифр. Если вы хотите проверить только цифры, используйте .isdigit().

Возможно, вам понравится string methods. Есть удобные .islower() и .isupper() доступные методы, которые вы можете попробовать, например:

>>> 'abc'.islower() 
True 
>>> 'abc123'.islower() 
True 
>>> 'Abc123'.islower() 
False 
>>> 'ABC'.isupper() 
True 
>>> 'ABC123'.isupper() 
True 
>>> 'Abc123'.isupper() 
False 

Это быстрее и компактнее, что использование password.upper() == password следующее испытает то же самое:

if password.isupper() or password.islower() or password.isdigit(): 
    # very weak indeed 

Следующий трюк, который вы хотите изучить, - это перебрать строку, чтобы вы могли тестировать отдельные символы:

>>> [c.isdigit() for c in 'abc123'] 
[False, False, False, True, True, True] 

I е вы объединить, что с помощью функции any(), вы можете проверить, есть ли некоторые символы, которые являются числами:

>>> any(c.isdigit() for c in 'abc123') 
True 
>>> any(c.isdigit() for c in 'abc') 
False 

Я думаю, что вы найдете эти приемы удобно при тестировании сильных паролей.

2

Вот ремейк того, что Вы писали:

import re 

def password(): 
    print ('Enter a password\n\nThe password must be between 6 and 12 characters.\n') 

    while True: 
     password = input('Password: ... ') 
     if 6 <= len(password) < 12: 
      break 
     print ('The password must be between 6 and 12 characters.\n') 

    password_scores = {0:'Horrible', 1:'Weak', 2:'Medium', 3:'Strong'} 
    password_strength = dict.fromkeys(['has_upper', 'has_lower', 'has_num'], False) 
    if re.search(r'[A-Z]', password): 
     password_strength['has_upper'] = True 
    if re.search(r'[a-z]', password): 
     password_strength['has_lower'] = True 
    if re.search(r'[0-9]', password): 
     password_strength['has_num'] = True 

    score = len([b for b in password_strength.values() if b]) 

    print ('Password is %s' % password_scores[score]) 

Выход (образец):

>>> password() 
Enter a password 

The password must be between 6 and 12 characters. 

Password: ... ghgG234 
Password is Strong 
+0

я работаю с Python 3 – user2412839

+0

коммутаторе 'raw_input' в' input' и вы хорошо идти, и визы Versa при использовании python 2. (Я уже отредактировал свой ответ, так что должно быть хорошо идти) –

1

Я также искал какой-то силы пароля исследовать функцию, и нашли много наполовину обработанное предложение. Я собрал свою собственную функцию, основанную на ней.

надежда помочь

def get_pw_strength(pw): 

    s_lc = set(['a', 'c', 'b', 'e', 'd', 'g', 'f', 'i', 'h', 'k', 'j', 'm', 'l', 'o', 'n', 'q', 'p', 's', 'r', 'u', 't', 'w', 'v', 'y', 'x', 'z']) 
    s_uc = set(['A', 'C', 'B', 'E', 'D', 'G', 'F', 'I', 'H', 'K', 'J', 'M', 'L', 'O', 'N', 'Q', 'P', 'S', 'R', 'U', 'T', 'W', 'V', 'Y', 'X', 'Z']) 
    s_dg = set(['1', '0', '3', '2', '5', '4', '7', '6', '9', '8']) 
    s_sp = set(['+', ',', '.', '-', '?', ':', '_', '(', ')', '*', '/', ';', '+', '!']) 
    pw_s = 0 
    pw_steps = (5, 8, 12) 

    pw_l = len(pw) 
    if (pw_l < 4): 
     return 0 
    for l in pw_steps : 
     if (pw_l > l): 
      pw_s += 1 
      #print "length over ", l," giving point", pw_s 

    c_lc = c_uc = c_dg = c_sp = 0 
    for c in pw : 
     if (c in s_lc) : 
      c_lc += 1 
     if (c in s_uc) : 
      c_uc += 1 
     if (c in s_dg) : 
      c_dg += 1 
     if (c in s_sp) : 
      c_sp += 1 
    if (c_lc + c_uc + c_dg + c_sp <> pw_l): 
     #print c_lc, c_uc, c_dg, c_sp, pw_l 
     #raise Exception "Forbidden chracter" 
     return -1 
    charset = 0 
    if (c_lc) : 
     pw_s += 1 
     charset = len(s_lc) 
    if (c_uc) : 
     pw_s += 1 
     charset = len(s_uc) 
    if (c_dg) : 
     pw_s += 1 
     charset = len(s_dg) 
    if (c_sp) : 
     pw_s += 2 
     charset = len(s_sp) 
    entropy = log(pow(charset,pw_l),2) 

    return pw_s, entropy 
12

Hola
Лучший подход использует поиск по регулярному выражению
Вот функция Я в настоящее время использую

def password_check(password): 
    """ 
    Verify the strength of 'password' 
    Returns a dict indicating the wrong criteria 
    A password is considered strong if: 
     8 characters length or more 
     1 digit or more 
     1 symbol or more 
     1 uppercase letter or more 
     1 lowercase letter or more 
    """ 

    # calculating the length 
    length_error = len(password) < 8 

    # searching for digits 
    digit_error = re.search(r"\d", password) is None 

    # searching for uppercase 
    uppercase_error = re.search(r"[A-Z]", password) is None 

    # searching for lowercase 
    lowercase_error = re.search(r"[a-z]", password) is None 

    # searching for symbols 
    symbol_error = re.search(r"[ !#$%&'()*+,-./[\\\]^_`{|}~"+r'"]', password) is None 

    # overall result 
    password_ok = not (length_error or digit_error or uppercase_error or lowercase_error or symbol_error) 

    return { 
     'password_ok' : password_ok, 
     'length_error' : length_error, 
     'digit_error' : digit_error, 
     'uppercase_error' : uppercase_error, 
     'lowercase_error' : lowercase_error, 
     'symbol_error' : symbol_error, 
    } 

EDIT:
парование предложение о Лукаш представляет собой обновление для проверки состояния особого символа

symbol_error = re.search(r"\W", password) is None 
+0

Для символа_error есть способ использовать '\ W * \ s'? Выделение символов не кажется эффективным. Например, список, который вы предоставляете, отсутствует, <, > и многие другие. – Lukasz

+0

Спасибо за ваш комментарий Лукаш. Поиск символов может быть упрощен с использованием специальной последовательности \ W. Нет необходимости включать \ s, потому что пространство уже включено в \ W. Таким образом, код для «поиска символов» должен быть изменен на: symbol_error = re.search (r "\ W", password) is None – ePi272314

Смежные вопросы