diff --git a/src/attributecode/model.py b/src/attributecode/model.py index dc34e9b4..a08b9ec2 100644 --- a/src/attributecode/model.py +++ b/src/attributecode/model.py @@ -35,6 +35,7 @@ import posixpath from posixpath import dirname import re +import six import sys if sys.version_info[0] < 3: # Python 2 @@ -1033,6 +1034,54 @@ def load_dict(self, fields_dict, base_dir, running_inventory=False, self.errors = errors return errors + def is_equals_with_small_text_differences(self, verus_about_object): + """ + Compare 2 ABOUT objects. + Return True if only small text difference such as extra space or + lists have the same value but in different order. False otherwise. + """ + for field in self.all_fields(): + not_exist_in_verus_about_object = True + for verus_field in verus_about_object.all_fields(): + if verus_field.name == field.name: + not_exist_in_verus_about_object = False + # Check the type of the value and stripped all the + # whitespaces in the value + # Use the six package to catch string type for both python2.x and python3.x + if isinstance(field.value, six.string_types): + field_stripped_value = util.strip_all_whitespaces_to_lowercase(field.value) + verus_field_stripped_value = util.strip_all_whitespaces_to_lowercase(verus_field.value) + if not verus_field_stripped_value == field_stripped_value: + return False + elif isinstance(field.value, list): + field_stripped_value = [] + verus_field_stripped_value = [] + for value in field.value: + field_stripped_value.append(util.strip_all_whitespaces_to_lowercase(value)) + for verus_value in verus_field.value: + verus_field_stripped_value.append(util.strip_all_whitespaces_to_lowercase(verus_value)) + # Compare the lists value and ignore the order + if not sorted(field_stripped_value) == sorted(verus_field_stripped_value): + return False + elif isinstance(field.value, dict): + field_stripped_value_dict = {} + verus_field_stripped_value_dict = {} + if field.value: + for field_dict_name in field.value: + field_stripped_value_dict[field.name] = util.strip_all_whitespaces_to_lowercase(field.value[field_dict_name]) + for verus_field_dict_name in verus_field.value: + verus_field_stripped_value_dict[verus_field.name] = util.strip_all_whitespaces_to_lowercase(verus_field.value[verus_field_dict_name]) + # Compare the value of the 2 dictionary after stripped all + # whitespaces in value + if not field_stripped_value_dict == verus_field_stripped_value_dict: + return False + else: + if not verus_field.value == field.value: + return False + if not_exist_in_verus_about_object: + return False + return True + def dumps(self, with_absent=False, with_empty=True): """ Return self as a formatted ABOUT string. diff --git a/src/attributecode/util.py b/src/attributecode/util.py index 39bb49f7..d8dc5516 100644 --- a/src/attributecode/util.py +++ b/src/attributecode/util.py @@ -543,4 +543,8 @@ def update_severity_level_about_resource_path_not_exist_error(errors): #continue else: updated_errors.append(err) - return updated_errors \ No newline at end of file + return updated_errors + + +def strip_all_whitespaces_to_lowercase(value): + return "".join(value.lower().split()) \ No newline at end of file diff --git a/tests/test_model.py b/tests/test_model.py index eaea504f..3d7d1a62 100644 --- a/tests/test_model.py +++ b/tests/test_model.py @@ -578,13 +578,12 @@ def test_About_equals(self): b = model.About(test_file, about_file_path='complete/about.ABOUT') assert a == b - def FAILING_test_About_equals_with_small_text_differences(self): + def test_About_equals_with_small_text_differences(self): test_file = get_test_loc('equal/complete2/about.ABOUT') a = model.About(test_file, about_file_path='complete2/about.ABOUT') test_file2 = get_test_loc('equal/complete/about.ABOUT') b = model.About(test_file2, about_file_path='complete/about.ABOUT') - assert a.dumps(True) == b.dumps(True) - assert a == b + assert a.is_equals_with_small_text_differences(b) def test_About_dumps_does_not_transform_strings_in_lists(self): test_file = get_test_loc('dumps/complete2/about.ABOUT') diff --git a/tests/test_util.py b/tests/test_util.py index 181ee878..86dec887 100644 --- a/tests/test_util.py +++ b/tests/test_util.py @@ -444,3 +444,9 @@ def test_update_severity_level_about_resource_path_not_exist_error(self): input_err = [Error(ERROR, 'Field about_resource_path: test.tar.gz does not exist')] expected_err = [Error(INFO, 'Field about_resource_path: test.tar.gz does not exist')] assert util.update_severity_level_about_resource_path_not_exist_error(input_err) == expected_err + + def test_strip_all_whitespaces_to_lowercase(self): + input = 'This is a test' + expected = 'thisisatest' + result = util.strip_all_whitespaces_to_lowercase(input) + assert expected == result \ No newline at end of file diff --git a/tests/testdata/equal/complete/about.ABOUT b/tests/testdata/equal/complete/about.ABOUT index f8e7e519..21fb5d2f 100644 --- a/tests/testdata/equal/complete/about.ABOUT +++ b/tests/testdata/equal/complete/about.ABOUT @@ -24,4 +24,4 @@ license_file: apache-2.0.LICENSE copyright: Copyright (c) 2013-2014 nexB Inc. notice_file: NOTICE -attribute: y \ No newline at end of file +attribute: yes \ No newline at end of file