Password Scoring Kata

A solution with unit tests to the password scoring kata.

Code


def count_special_chars(password):
  return sum(letter in "<>!&*" for letter in password)

def contains_special_chars(password):
  return count_special_chars(password) > 0

def count_digits(password):
  return sum(letter.isdigit() for letter in password)

def contains_digits(password):
  return count_digits(password) > 0

def contains_mixed_case(password):
  upper_case_letters = sum(letter.isupper() for letter in password)
  lower_case_letters = sum(letter.islower() for letter in password)

  return upper_case_letters > 0 and lower_case_letters > 0

def score_password(password):
  points = len(password)

  if contains_mixed_case(password) == False:
    points -= 5

  if contains_digits(password) == False:
    points -= 5

  if contains_special_chars(password) == False:
    points -= 5

  return points

Unit Tests


import unittest

class TestPasswordScoring(unittest.TestCase):

  def test_alpha_only_is_penalised_for_missing_classes(self):
    self.assertEqual(score_password("swordfish"), -6)

  def test_alpha_numeric_is_penalised_for_missing_specials(self):
    self.assertEqual(score_password("sw0rdfish"), -1)

  def test_all_lower_case_is_penalised(self):
    self.assertEqual(score_password("sw0rdf!sh"), 4)

  def test_all_upper_case_is_penalised(self):
    self.assertEqual(score_password("SW0RDF!5H"), 4)

  def test_complex_is_scored_on_length(self):
    self.assertEqual(score_password("Sw0rdf!sH"), 9)

if __name__ == '__main__':
  unittest.main()