Решение на Регулярни изрази от Никола Димитров

Обратно към всички решения

Към профила на Никола Димитров

Резултати

  • 7 точки от тестове
  • 0 бонус точки
  • 7 точки общо
  • 29 успешни тест(а)
  • 10 неуспешни тест(а)

Код

import re
import functools
PATTERNS = {
"HOSTNAME": r"(?P<hostname>\b([0-9A-Za-z]([0-9A-Za-z]|[0-9A-Za-z\-]{1,61}[0-9A-Za-z])\.)" + # (Sub)domains
r"+([A-Za-z]{2,3}(\.[A-Za-z]{2})?)\b)", # TLD
"EMAIL_ACCOUNT": r"(?P<account>\b[0-9A-Za-z][0-9A-Za-z_\-\.\+]{0,200})\b",
"BYTE": r"(\b0|[1-9][0-9]?|1[0-9][0-9]|2([0-4][0-9]|5[0-5]))\b",
"DATE": r"\b[0-9]{4}-(0[1-9]|1[0-2])-([1-9]|[1-2][0-9]|3[01])\b",
"TIME": r"\b([01][0-9]|2[0-3]):([0-5][0-9]):([0-5][0-9])\b",
"FLOAT": r"-?(0|[1-9]\d*)(\.\d+)?",
"INT": r"-?(0|[1-9]\d*)",
"PHONE": r"((?P<l_prefix>0(?!0))|(?P<g_prefix>(00|\+)[1-9][0-9]{0,2}))(?P<main>([ \(\)\-]{0,2}\d){6,11})"
}
PATTERNS["EMAIL"] = PATTERNS["EMAIL_ACCOUNT"] + "@" + PATTERNS["HOSTNAME"]
# An IP is 4 bytes
PATTERNS["IP"] = r"\b" + r"\.".join([PATTERNS["BYTE"]] * 4) + r"\b"
# Remove the requirements for word break
PATTERNS["DATETIME"] = PATTERNS["DATE"][:-2] + r"( |T)" + PATTERNS["TIME"][2:]
class Validations:
def __validate(patternName, string):
return bool(re.match("^{0}$".format(PATTERNS[patternName]), string))
is_email = functools.partial(__validate, "EMAIL")
is_phone = functools.partial(__validate, "PHONE")
is_hostname = functools.partial(__validate, "HOSTNAME")
is_ip_address = functools.partial(__validate, "IP")
is_number = functools.partial(__validate, "FLOAT")
is_integer = functools.partial(__validate, "INT")
is_date = functools.partial(__validate, "DATE")
is_time = functools.partial(__validate, "TIME")
is_datetime = functools.partial(__validate, "DATETIME")
class PrivacyFilter:
EMAIL_PLACEHOLDER = "[EMAIL]"
PHONE_PLACEHOLDER = "[PHONE]"
FILTERED_PLACEHOLDER = "[FILTERED]"
MIN_USER_LENGTH = 6
def __init__(self, text):
self.text = text
self.preserve_phone_country_code = False
self.preserve_email_hostname = False
self.partially_preserve_email_username = False
def __phone_filter(self, match):
if self.preserve_phone_country_code and match.group("g_prefix"):
return "{0} {1}".format(match.group("g_prefix"),
PrivacyFilter.FILTERED_PLACEHOLDER)
return PrivacyFilter.PHONE_PLACEHOLDER
def __email_filter(self, match):
if self.partially_preserve_email_username:
user = match.group("account")
user = user[0:3] * (len(user) >= PrivacyFilter.MIN_USER_LENGTH)
return "{0}{1}@{2}".format(user,
PrivacyFilter.FILTERED_PLACEHOLDER,
match.group("hostname"))
if self.preserve_email_hostname:
return "{0}@{1}".format(PrivacyFilter.FILTERED_PLACEHOLDER,
match.group("hostname"))
return PrivacyFilter.EMAIL_PLACEHOLDER
def filtered(self):
filtered = re.sub(PATTERNS["EMAIL"], self.__email_filter, self.text)
filtered = re.sub(PATTERNS["PHONE"], self.__phone_filter, filtered)
return filtered

Лог от изпълнението

....F..F....F.F.F.....FF..FF....F......
======================================================================
FAIL: test_does_not_filter_invalid_phone_numbers (test.PrivacyFilterTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 86, in test_does_not_filter_invalid_phone_numbers
    self.assertEqual(filtered, solution.PrivacyFilter(text).filtered())
AssertionError: 'Reach me at: 0885123' != 'Reach me at: [PHONE]'
- Reach me at: 0885123
+ Reach me at: [PHONE]


======================================================================
FAIL: test_obfuscates_more_complicated_emails (test.PrivacyFilterTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 37, in test_obfuscates_more_complicated_emails
    self.assertEqual(filtered, solution.PrivacyFilter(text).filtered())
AssertionError: '[EMAIL]' != 'larodi@x.com'
- [EMAIL]
+ larodi@x.com


======================================================================
FAIL: test_allows_huge_years_in_date_validation (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 246, in test_allows_huge_years_in_date_validation
    self.assertTrue(solution.Validations.is_date('9999-01-01'))
AssertionError: False is not true

======================================================================
FAIL: test_allows_zero_years_in_date_validation (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 243, in test_allows_zero_years_in_date_validation
    self.assertTrue(solution.Validations.is_date('0000-01-01'))
AssertionError: False is not true

======================================================================
FAIL: test_can_validate_more_complex_phone_numbers (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 160, in test_can_validate_more_complex_phone_numbers
    self.assertIs(solution.Validations.is_phone(phone), valid)
AssertionError: True is not False

======================================================================
FAIL: test_handles_multiline_strings_in_IP_validation_properly (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 189, in test_handles_multiline_strings_in_IP_validation_properly
    self.assertFalse(solution.Validations.is_ip_address("8.8.8.8\n"))
AssertionError: True is not false

======================================================================
FAIL: test_handles_multiline_strings_in_hostname_validation_properly (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 179, in test_handles_multiline_strings_in_hostname_validation_properly
    self.assertFalse(solution.Validations.is_hostname("foo.com\n"))
AssertionError: True is not false

======================================================================
FAIL: test_handles_newlines_in_date_validation (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 259, in test_handles_newlines_in_date_validation
    self.assertFalse(solution.Validations.is_date("2012-11-19\n"))
AssertionError: True is not false

======================================================================
FAIL: test_handles_newlines_in_time_and_datetime_validation (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 288, in test_handles_newlines_in_time_and_datetime_validation
    self.assertFalse(solution.Validations.is_time("12:01:01\n"))
AssertionError: True is not false

======================================================================
FAIL: test_validates_hostnames (test.ValidationsTest)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "lib/language/python/runner.py", line 60, in thread
    raise it.exc_info[1]
  File "lib/language/python/runner.py", line 48, in run
    self.result = func(*args, **kwargs)
  File "/tmp/d20140513-11348-6stcdy/test.py", line 169, in test_validates_hostnames
    self.assertTrue(solution.Validations.is_hostname('1.2.3.4.xip.io'))
AssertionError: False is not true

----------------------------------------------------------------------
Ran 39 tests in 0.051s

FAILED (failures=10)

История (2 версии и 1 коментар)

Никола обнови решението на 19.04.2014 03:46 (преди около 10 години)

+import re
+import functools
+
+PATTERNS = {
+ "HOSTNAME": r"(?P<hostname>\b([0-9A-Za-z]([0-9A-Za-z]|[0-9A-Za-z\-]{1,61}[0-9A-Za-z])\.)" + # (Sub)domains
+ r"+([A-Za-z]{2,3}(\.[A-Za-z]{2})?)\b)", # TLD
+ "EMAIL_ACCOUNT": r"(?P<account>\b[0-9A-Za-z][0-9A-Za-z_\-\.\+]{0,200})\b",
+ "BYTE": r"(\b0|[1-9][0-9]?|1[0-9][0-9]|2([0-4][0-9]|5[0-5]))\b",
+ "DATE": r"\b[0-9]{4}-(0[1-9]|1[0-2])-([1-9]|[1-2][0-9]|3[01])\b",
+ "TIME": r"\b([01][0-9]|2[0-3]):([0-5][0-9]):([0-5][0-9])\b",
+ "FLOAT": r"-?(0|[1-9]\d*)(\.\d+)?\b",
+ "INT": r"-?(0|[1-9]\d*)",
+ "PHONE": r"((?P<l_prefix>0(?!0))|(?P<g_prefix>(00|\+)[1-9][0-9]{0,2}))(?P<main>([ \(\)\-]{0,2}\d){6,11})"
+ }
+
+PATTERNS["EMAIL"] = PATTERNS["EMAIL_ACCOUNT"] + "@" + PATTERNS["HOSTNAME"]
+# An IP is 4 bytes
+PATTERNS["IP"] = r"\b" + r"\.".join([PATTERNS["BYTE"]] * 4) + r"\b"
+# Remove the requirements for word break
+PATTERNS["DATETIME"] = PATTERNS["DATE"][:-2] + r"( |T)" + PATTERNS["TIME"][:2]
+
+class Validations:
+
+ def __validate(patternName, string):
+ return bool(re.match("^{0}$".format(PATTERNS[patternName]), string))
+
+ is_email = functools.partial(__validate, "EMAIL")
+ is_phone = functools.partial(__validate, "PHONE")
+ is_hostname = functools.partial(__validate, "HOSTNAME")
+ is_ip_address = functools.partial(__validate, "IP")
+ is_number = functools.partial(__validate, "FLOAT")
+ is_integer = functools.partial(__validate, "INT")
+ is_date = functools.partial(__validate, "DATE")
+ is_time = functools.partial(__validate, "TIME")
+ is_datetime = functools.partial(__validate, "DATETIME")
+
+
+class PrivacyFilter:
+ EMAIL_PLACEHOLDER = "[EMAIL]"
+ PHONE_PLACEHOLDER = "[PHONE]"
+ FILTERED_PLACEHOLDER = "[FILTERED]"
+ MIN_USER_LENGTH = 6
+
+ def __init__(self, text):
+ self.text = text
+ self.preserve_phone_country_code = False
+ self.preserve_email_hostname = False
+ self.partially_preserve_email_username = False
+
+ def __phone_filter(self, match):
+ if self.preserve_phone_country_code and match.group("g_prefix"):
+ return "{0} {1}".format(match.group("g_prefix"),
+ PrivacyFilter.FILTERED_PLACEHOLDER)
+ return PrivacyFilter.PHONE_PLACEHOLDER
+
+ def __email_filter(self, match):
+ if self.partially_preserve_email_username:
+ user = match.group("account")
+ user = user[0:3] * (len(user) >= PrivacyFilter.MIN_USER_LENGTH)
+ return "{0}{1}@{2}".format(user,
+ PrivacyFilter.FILTERED_PLACEHOLDER,
+ match.group("hostname"))
+
+ if self.preserve_email_hostname:
+ return "{0}@{1}".format(PrivacyFilter.FILTERED_PLACEHOLDER,
+ match.group("hostname"))
+ return PrivacyFilter.EMAIL_PLACEHOLDER
+
+ def filtered(self):
+ filtered = re.sub(PATTERNS["EMAIL"], self.__email_filter, self.text)
+ filtered = re.sub(PATTERNS["PHONE"], self.__phone_filter, filtered)
+ return filtered

Никола обнови решението на 23.04.2014 01:17 (преди около 10 години)

import re
import functools
PATTERNS = {
"HOSTNAME": r"(?P<hostname>\b([0-9A-Za-z]([0-9A-Za-z]|[0-9A-Za-z\-]{1,61}[0-9A-Za-z])\.)" + # (Sub)domains
r"+([A-Za-z]{2,3}(\.[A-Za-z]{2})?)\b)", # TLD
"EMAIL_ACCOUNT": r"(?P<account>\b[0-9A-Za-z][0-9A-Za-z_\-\.\+]{0,200})\b",
"BYTE": r"(\b0|[1-9][0-9]?|1[0-9][0-9]|2([0-4][0-9]|5[0-5]))\b",
"DATE": r"\b[0-9]{4}-(0[1-9]|1[0-2])-([1-9]|[1-2][0-9]|3[01])\b",
"TIME": r"\b([01][0-9]|2[0-3]):([0-5][0-9]):([0-5][0-9])\b",
- "FLOAT": r"-?(0|[1-9]\d*)(\.\d+)?\b",
+ "FLOAT": r"-?(0|[1-9]\d*)(\.\d+)?",
"INT": r"-?(0|[1-9]\d*)",
"PHONE": r"((?P<l_prefix>0(?!0))|(?P<g_prefix>(00|\+)[1-9][0-9]{0,2}))(?P<main>([ \(\)\-]{0,2}\d){6,11})"
}
PATTERNS["EMAIL"] = PATTERNS["EMAIL_ACCOUNT"] + "@" + PATTERNS["HOSTNAME"]
# An IP is 4 bytes
PATTERNS["IP"] = r"\b" + r"\.".join([PATTERNS["BYTE"]] * 4) + r"\b"
# Remove the requirements for word break
-PATTERNS["DATETIME"] = PATTERNS["DATE"][:-2] + r"( |T)" + PATTERNS["TIME"][:2]
+PATTERNS["DATETIME"] = PATTERNS["DATE"][:-2] + r"( |T)" + PATTERNS["TIME"][2:]
class Validations:
def __validate(patternName, string):
return bool(re.match("^{0}$".format(PATTERNS[patternName]), string))
is_email = functools.partial(__validate, "EMAIL")
is_phone = functools.partial(__validate, "PHONE")
is_hostname = functools.partial(__validate, "HOSTNAME")
is_ip_address = functools.partial(__validate, "IP")
is_number = functools.partial(__validate, "FLOAT")
is_integer = functools.partial(__validate, "INT")
is_date = functools.partial(__validate, "DATE")
is_time = functools.partial(__validate, "TIME")
is_datetime = functools.partial(__validate, "DATETIME")
class PrivacyFilter:
EMAIL_PLACEHOLDER = "[EMAIL]"
PHONE_PLACEHOLDER = "[PHONE]"
FILTERED_PLACEHOLDER = "[FILTERED]"
MIN_USER_LENGTH = 6
def __init__(self, text):
self.text = text
self.preserve_phone_country_code = False
self.preserve_email_hostname = False
self.partially_preserve_email_username = False
def __phone_filter(self, match):
if self.preserve_phone_country_code and match.group("g_prefix"):
return "{0} {1}".format(match.group("g_prefix"),
PrivacyFilter.FILTERED_PLACEHOLDER)
return PrivacyFilter.PHONE_PLACEHOLDER
def __email_filter(self, match):
if self.partially_preserve_email_username:
user = match.group("account")
user = user[0:3] * (len(user) >= PrivacyFilter.MIN_USER_LENGTH)
return "{0}{1}@{2}".format(user,
PrivacyFilter.FILTERED_PLACEHOLDER,
match.group("hostname"))
if self.preserve_email_hostname:
return "{0}@{1}".format(PrivacyFilter.FILTERED_PLACEHOLDER,
match.group("hostname"))
return PrivacyFilter.EMAIL_PLACEHOLDER
def filtered(self):
filtered = re.sub(PATTERNS["EMAIL"], self.__email_filter, self.text)
filtered = re.sub(PATTERNS["PHONE"], self.__phone_filter, filtered)
return filtered