From 9bab5a7907ef69f815ae2cf9f05d1642888b9a49 Mon Sep 17 00:00:00 2001 From: Jinglei Ren Date: Sun, 20 Aug 2023 21:57:41 +0800 Subject: [PATCH] Replace get_path method with get_files method - Changed the order of branches in Namespace class to ascending. - Added a check for None in is_valid_name method. - Updated the list_names method to check if a path is a directory. - Updated tests to reflect these changes in the Namespace class. --- devchat/namespace.py | 33 +++++++++++++++++++++------------ tests/test_namespace.py | 33 +++++++++++++++++++++++++-------- 2 files changed, 46 insertions(+), 20 deletions(-) diff --git a/devchat/namespace.py b/devchat/namespace.py index 0eafcace..b5b5d052 100644 --- a/devchat/namespace.py +++ b/devchat/namespace.py @@ -8,10 +8,10 @@ def __init__(self, root_path: str, branches: List[str] = None): """ :param root_path: The root path of the namespace. - :param branches: The hidden branches with descending order of priority. + :param branches: The hidden branches with ascending order of priority. """ self.root_path = root_path - self.branches = branches if branches else ['usr', 'org', 'sys'] + self.branches = branches if branches else ['sys', 'org', 'usr'] @staticmethod def is_valid_name(name: str) -> bool: @@ -26,25 +26,35 @@ def is_valid_name(name: str) -> bool: :return: True if the name is valid, False otherwise. """ # The regular expression pattern for a valid name + if name is None: + return False pattern = r'^$|^(?!.*\.\.)[a-zA-Z0-9_-]+(\.[a-zA-Z0-9_-]+)*$' return bool(re.match(pattern, name)) - def get_path(self, name: str) -> Optional[str]: + def get_files(self, name: str) -> Optional[List[str]]: """ :param name: The command name in the namespace. - :return: The relative path of the command directory. + :return: The full paths of the files in the command directory. """ - if not name: + if not self.is_valid_name(name): return None # Convert the dot-separated name to a path path = os.path.join(*name.split('.')) + files = {} + path_found = False for branch in self.branches: full_path = os.path.join(self.root_path, branch, path) - if os.path.exists(full_path): - # If it exists, return the branch/path part - return os.path.join(branch, path) + if os.path.isdir(full_path): + # If it exists and is a directory, get the files + path_found = True + for file in os.listdir(full_path): + files[file] = os.path.join(full_path, file) # If no existing path is found, return None - return None + if not path_found: + return None + # If path is found but no files exist, return an empty list + # Sort the files in alphabetical order before returning + return sorted(files.values()) if files else [] def list_names(self, name: str = '', recursive: bool = False) -> Optional[List[str]]: """ @@ -59,10 +69,9 @@ def list_names(self, name: str = '', recursive: bool = False) -> Optional[List[s found = False for branch in self.branches: full_path = os.path.join(self.root_path, branch, path) - if os.path.exists(full_path): + if os.path.isdir(full_path): found = True - if os.path.isdir(full_path): - self._add_dirnames_to_commands(full_path, name, commands) + self._add_dirnames_to_commands(full_path, name, commands) if recursive: self._add_recursive_dirnames_to_commands(full_path, name, commands) return sorted(commands) if found else None diff --git a/tests/test_namespace.py b/tests/test_namespace.py index 4000e14a..709b7958 100644 --- a/tests/test_namespace.py +++ b/tests/test_namespace.py @@ -29,28 +29,45 @@ def test_is_valid_name(): assert Namespace.is_valid_name('a>b') is False -def test_get_path(tmp_path): +def test_get_files(tmp_path): # Create a Namespace instance with the temporary directory as the root path namespace = Namespace(str(tmp_path)) # Test case 1: a path that exists # Create a file in the 'usr' branch os.makedirs(os.path.join(tmp_path, 'usr', 'a', 'b', 'c'), exist_ok=True) - assert namespace.get_path('a.b.c') == os.path.join('usr', 'a', 'b', 'c') + file_path = os.path.join(tmp_path, 'usr', 'a', 'b', 'c', 'file1.txt') + with open(file_path, 'w', encoding='utf-8') as file: + file.write('test') + assert namespace.get_files('a.b.c') == [file_path] # Test case 2: a path that doesn't exist - assert namespace.get_path('d.e.f') is None + assert namespace.get_files('d.e.f') is None - # Test case 3: a path that exists in a later branch + # Test case 3: a path exists but has no files + os.makedirs(os.path.join(tmp_path, 'org', 'd', 'e', 'f'), exist_ok=True) + assert namespace.get_files('d.e.f') == [] + + # Test case 4: a path that exists in a later branch # Create a file in the 'sys' branch + os.makedirs(os.path.join(tmp_path, 'usr', 'g', 'h', 'i'), exist_ok=True) os.makedirs(os.path.join(tmp_path, 'sys', 'g', 'h', 'i'), exist_ok=True) - assert namespace.get_path('g.h.i') == os.path.join('sys', 'g', 'h', 'i') + file_path = os.path.join(tmp_path, 'sys', 'g', 'h', 'i', 'file2.txt') + with open(file_path, 'w', encoding='utf-8') as file: + file.write('test') + assert namespace.get_files('g.h.i') == [file_path] - # Test case 4: a path in 'usr' overwrites the same in 'sys' + # Test case 5: a path in 'usr' overwrites the same in 'sys' # Create the same file in the 'usr' and 'sys' branches os.makedirs(os.path.join(tmp_path, 'usr', 'j', 'k', 'l'), exist_ok=True) + usr_file_path = os.path.join(tmp_path, 'usr', 'j', 'k', 'l', 'file3.txt') os.makedirs(os.path.join(tmp_path, 'sys', 'j', 'k', 'l'), exist_ok=True) - assert namespace.get_path('j.k.l') == os.path.join('usr', 'j', 'k', 'l') + sys_file_path = os.path.join(tmp_path, 'sys', 'j', 'k', 'l', 'file3.txt') + with open(usr_file_path, 'w', encoding='utf-8') as file: + file.write('test') + with open(sys_file_path, 'w', encoding='utf-8') as file: + file.write('test') + assert namespace.get_files('j.k.l') == [usr_file_path] def test_list_names(tmp_path): @@ -74,7 +91,7 @@ def test_list_names(tmp_path): # Test listing commands when there are no commands commands = namespace.list_names('a.e') - assert not commands + assert len(commands) == 0 # Test listing commands of the root commands = namespace.list_names()