0

This is what I've done till now. And when it goes wrong it doesn't print 'Not Okay'. I'm still not able to figure out how to check special chars.

#!/usr/bin/python

def passw_check():
    passin = raw_input("Enter the password")

    if len(passin) == 8:       # checking total length of password
        if sum(map(str.isupper, passin))== 2: #check 2 upper chars
            if sum(map(str.islower, passin))== 2:  #check 2 lower chars
                if sum(map(str.isdigit, passin))== 4:  #check 2 digits chars
                    print 'Passwords Okay'
                else: 
                    print 'Not Okay!'

passw_check()
jedwards
  • 29,432
  • 3
  • 65
  • 92
sunp
  • 21
  • 6
  • 1
    Well, your else is only associated with your final IF. You need to be clear in your question whether you have two problems or one. – Bill Woodger Apr 04 '15 at 15:05
  • Then, should it be in indented with first IF, because/if they are nested? Yes you are right my if-else loop is not working correctly. – sunp Apr 04 '15 at 15:08
  • I hope you're [not actually trying to apply](http://stackoverflow.com/questions/98768/should-i-impose-a-maximum-length-on-passwords) those [password restrictions](http://security.stackexchange.com/questions/33470/what-technical-reasons-are-there-to-have-low-maximum-password-lengths) on a real public system. – Ilmari Karonen Apr 04 '15 at 15:15
  • @llmari karonen, It will only make things safer on internet, isn't it? Not really, its for my personal script only! hey! – sunp Apr 04 '15 at 15:25

3 Answers3

1

Only the innermost if has an else-branch. Use and to check all conditions at once:

def passw_check():
    passin = raw_input("Enter the password")

    if (len(passin) == 8 and       # checking total length of password
        sum(map(str.isupper, passin)) == 2 and #check 2 upper chars
        sum(map(str.islower, passin)) == 2 and  #check 2 lower chars
        sum(map(str.isdigit, passin))== 4):  #check 2 digits chars
        print 'Passwords Okay'
    else: 
        print 'Not Okay!'
    return passin

passw = passw_check()
Daniel
  • 42,087
  • 4
  • 55
  • 81
1

I'd probably do something like:

#!/usr/bin/python
import string

def validate(s):
    def is_punc(c): return c in string.punctuation
    if len(s) != 8:                   return False
    if sum(map(str.isupper, s)) != 2: return False
    if sum(map(str.islower, s)) != 2: return False
    if sum(map(str.isdigit, s)) != 2: return False
    if sum(map(is_punc, s))     != 2: return False
    # Note of the tests have been violated, return True
    return True


def passw_check():
    passin = raw_input("Enter the password: ")

    if validate(passin):
        print 'Passwords Okay'
    else:
        print 'Not Okay!'

passw_check()

Here, the validate function is very clear and the logic is easy to understand.

Also note, you say you only want 2 numeric characters, but the test in your code checks for 4. I changed this to 2 to fit your problem description, just a heads up.

Edit Added string.punctuation test instead of just assuming the non-alphanum characters are "special" -- this may be unnecessary/undesired if you want to accept things like whitespace / don't want to depend on the system's locale.

jedwards
  • 29,432
  • 3
  • 65
  • 92
  • This give error in script:Enter the password: UI((98kk Traceback (most recent call last): File "new.py", line 22, in passw_check() File "new.py", line 17, in passw_check if validate(passin): File "new.py", line 10, in validate if sum(map(is_punc, s)) != 2: return False File "new.py", line 5, in is_punc def is_punc(c): return c in string.punctuation NameError: global name 'string' is not defined – sunp Apr 04 '15 at 15:21
  • @sunnyp. a previous edit of the answer omitted the `import string` at the top, try it again with that line. – jedwards Apr 04 '15 at 15:22
  • yep it was 'import string' that was missing. Now working perfectly. Thanks. – sunp Apr 04 '15 at 15:30
1

You could use regex, this should validate that the passin has 2 lower, 2 upper, 2 digits and 2 specials (you can change:

import re, string
def passw_check(passin):
    lower = "(?=.*[a-z].*[a-z])"
    upper = "(?=.*[A-Z].*[A-Z])"
    digit = "(?=.*[0-9].*[0-9])"
    special = "(?=.*[{0}].*[{0}])".format(re.escape(string.punctuation))
    return re.match("^.*{}{}{}{}.*$".format(lower, upper, digit, special), passin)

check = passw_check(raw_input("Enter the password"))
print("Password Okay" if check else "Not Okay!")
AChampion
  • 29,683
  • 4
  • 59
  • 75