From 9e7d3cec55b43162bcd8eec2b91158dd9efe8734 Mon Sep 17 00:00:00 2001 From: Jiewei Qian Date: Wed, 20 Mar 2024 22:45:30 +0000 Subject: [PATCH] metadata: sort discovered files and validation messages Explicitly sorts the discovered metadata file, and defines ordering of validation messages, so the tools will output will be self-consistent. Change-Id: I9b263a16b151c014e5950638f066376469c701df Reviewed-on: https://chromium-review.googlesource.com/c/chromium/tools/depot_tools/+/5379678 Commit-Queue: Jiewei Qian Reviewed-by: Anne Redulla --- metadata/discover.py | 4 ++-- metadata/validate.py | 5 +++-- metadata/validation_result.py | 27 +++++++++++++++++++++++++++ 3 files changed, 32 insertions(+), 4 deletions(-) diff --git a/metadata/discover.py b/metadata/discover.py index b774eae11..dc74f8ea8 100644 --- a/metadata/discover.py +++ b/metadata/discover.py @@ -25,7 +25,7 @@ def find_metadata_files(root: str) -> List[str]: search. Returns: the absolute full paths for all the metadata files within - the root directory. + the root directory, sorted in ascending order. """ metadata_files = [] @@ -35,4 +35,4 @@ def find_metadata_files(root: str) -> List[str]: full_path = os.path.join(root, dirpath, filename) metadata_files.append(full_path) - return metadata_files + return sorted(metadata_files) diff --git a/metadata/validate.py b/metadata/validate.py index 442bd1ea9..a85c8a81e 100644 --- a/metadata/validate.py +++ b/metadata/validate.py @@ -38,7 +38,8 @@ def validate_content(content: str, source_file_dir: str, repo_root_dir: the repository's root directory; this is needed to construct file paths to license files. - Returns: the validation results for the given content. + Returns: the validation results for the given content, sorted based + severity then message. """ results = [] dependencies = metadata.parse.parse_content(content) @@ -50,7 +51,7 @@ def validate_content(content: str, source_file_dir: str, dependency_results = dependency.validate( source_file_dir=source_file_dir, repo_root_dir=repo_root_dir) results.extend(dependency_results) - return results + return sorted(results) def _construct_file_read_error(filepath: str, cause: str) -> vr.ValidationError: diff --git a/metadata/validation_result.py b/metadata/validation_result.py index 59ce5f5c7..bc69744d5 100644 --- a/metadata/validation_result.py +++ b/metadata/validation_result.py @@ -36,6 +36,33 @@ class ValidationResult: def __repr__(self) -> str: return str(self) + # PEP 8 recommends implementing all 6 rich comparisons. + # Here we make use of tuple comparison, and order based on the severity + # (e.g. fatal comes before non-fatal), then the message. + def __lt__(self, other) -> bool: + return (not self._fatal, self._message) < (not other._fatal, + other._message) + + def __le__(self, other) -> bool: + return (not self._fatal, self._message) <= (not other._fatal, + other._message) + + def __gt__(self, other) -> bool: + return (not self._fatal, self._message) > (not other._fatal, + other._message) + + def __ge__(self, other) -> bool: + return (not self._fatal, self._message) >= (not other._fatal, + other._message) + + def __eq__(self, other) -> bool: + return (not self._fatal, self._message) == (not other._fatal, + other._message) + + def __ne__(self, other) -> bool: + return (not self._fatal, self._message) != (not other._fatal, + other._message) + def is_fatal(self) -> bool: return self._fatal