确定路径在类构造函数中是否有效

时间:2019-04-15 01:42:23

标签: python-3.x path directory

在不违反constructor should do work的指导原则的前提下,我需要确定所提供的字符串(destination_directory)是否为有效路径,然后再在构造函数中进行分配。

它不必存在,但是提供的字符串必须是有效的,即没有无效的符号或非法字符。我的项目只能在Windows上运行,不能在Linux上运行。

我查看了this页,但答案似乎尝试打开目录以测试提供的字符串是否有效。

我也尝试了os.path.isabs(path),但它没有提供我需要的结果。例如,它说T:\\\\Pictures是一条绝对路径,虽然可能是正确的,但\\\\应该表示该路径无效。

实现我想要的目标是否有一种清晰的方法?

def __init__(self, destination_directory: str)
    self._validate_path(path=destination_directory)
    self.destination_directory = destination_directory

def _validate_path(self, path)
    # code to validate path should go here.

2 个答案:

答案 0 :(得分:1)

我们现在对路径进行一些说明,它至少包含一个驱动器号和子目录。

我们在目录中也有关于what symbols are not的规则。我们也知道驱动器号包含一个字符。

我们没有使类的用户传递完整的路径,而是对其进行了细分,仅允许目录名称使用有效字符串,而驱动器仅允许使用一个字母。一切都经过验证后,我们可以使用os模块来构建路径。

这是我构造Folder类的方法:

class Folder:

    def __init__(self, *subdirectories, root_drive):
        self._validate_drive_letter(letter = root_drive)
        self._validate_path(path=subdirectories)

        self._root_drive = root_drive
        self._subdirectories = subdirectories

    def _validate_drive_letter(self, letter):
        if not letter or len(letter) > 2 or not letter.isalpha():
            raise ValueError("Drive letter is invalid")

    def _validate_path(self, path):
        self._forbidden_characters = ["<", ">", ":", "/", '"', "|", "?", "*", '\\']
        for character in path:
            for item in character:
                if item in self._forbidden_characters:
                    raise ValueError("Directory cannot contain invalid characters")

    def construct_full_path(self) -> str:
        # use the os module and constructor parameters to build a valid path

    def __str__(self) -> str:
        return f"Drive Letter: {self._root_drive} Subdirectories: {self._subdirectories}"

主要

def main():

    try:

        portable_drive = Folder("Pictures", "Landscape", root_drive="R") # Valid
        # Using the construct_full_path() function, the returned string would be:
        # R:\Pictures\Landscape
        # Notice the user doesn't provide the : or the \, the class will do it.

        vacation_pictures = Folder("Vac??tion", root_drive="T") # Will raise ValueError
        # If we fix the error and call construct_full_path() we will get T:\Vacation 

    except ValueError as error:
        print(error)
    else:
        print(portable_drive)
        print(vacation_pictures)


if __name__ == "__main__":
    main()

这可能不是最好的方法,但它可以工作。我知道嵌套的for循环很糟糕,但是我没有看到其他任何方法来验证string的各个字符。

答案 1 :(得分:0)

一种regex解决方案:

import re

windows_path_regex = re.compile(r"""
\A
(?:(?:[a-z]:|\\\\[a-z0-9_.$\●-]+\\[a-z0-9_.$\●-]+)\\|  # Drive
   \\?[^\\/:*?"<>|\r\n]+\\?)                           # Relative path
(?:[^\\/:*?"<>|\r\n]+\\)*                              # Folder
[^\\/:*?"<>|\r\n]*                                     # File
\Z
""", re.VERBOSE|re.I)
d = windows_path_regex .match(r"\test\txt.txt")
print(bool(d))

请注意,\是有效路径,而/不是有效路径。

我以8.18. Validate Windows Paths作为参考。