【问题标题】:Make a unique filesystem path, without any real file创建一个唯一的文件系统路径,没有任何真实文件
【发布时间】:2016-02-15 07:01:47
【问题描述】:

程序应该如何生成唯一的文件系统路径并且创建 文件系统条目?

tempfile.mktemp 函数是 strongly deprecated,这是正确的,因为它使程序容易受到不安全文件创建的影响。

在某些代码(例如单元测试)中,我调用 tempfile.mktemp 来 为我不想的文件系统条目生成唯一路径 存在于真实的文件系统中。在这种情况下,文件系统安全 担心是无关紧要的,因为没有文件。

该功能的弃用仍然是一个问题,因为我不 想要代码让每一个认真的读者都需要决定是否 代码有问题。相反,代码应该避免被正确弃用 API。

API 函数也很容易在某个时间点消失 未来,因为它已被明确且强烈地弃用。

tempfile 提供的其他功能根本不需要避免接触文件系统,只是为了获得唯一的路径。

所以我一般同意 tempfile.mktemp 的弃用,但图书馆似乎没有为此目的提供替代品。

我应该使用什么标准库函数来生成 tempfile.mktemp-like 独特的路径,并且不会创建一个真实的文件 走那条路?

【问题讨论】:

    标签: python temporary-files deprecation-warning


    【解决方案1】:

    AFAIK 没有这样的标准函数,它会生成唯一的名称,但不会创建文件。 看一下“mktemp”函数的内部实现,自己创建一个...

    以下是您可能感兴趣的代码:

    class _RandomNameSequence:
        """An instance of _RandomNameSequence generates an endless
        sequence of unpredictable strings which can safely be incorporated
        into file names.  Each string is six characters long.  Multiple
        threads can safely use the same instance at the same time.
    
        _RandomNameSequence is an iterator."""
    
        characters = "abcdefghijklmnopqrstuvwxyz0123456789_"
    
        @property
        def rng(self):
            cur_pid = _os.getpid()
            if cur_pid != getattr(self, '_rng_pid', None):
                self._rng = _Random()
                self._rng_pid = cur_pid
            return self._rng
    
        def __iter__(self):
            return self
    
        def __next__(self):
            c = self.characters
            choose = self.rng.choice
            letters = [choose(c) for dummy in range(8)]
            return ''.join(letters)
    

    【讨论】:

    • 谢谢。我将向 Python 标准库维护者提出一个问题,为此公开一个公共 API。
    • @bignose 存在公共 API,它被称为 tempfile.mktemp。 :) 也许维护者会接受将名称更改为不承担熟悉 POSIX mktemp 负担的建议,这同样被弃用?
    【解决方案2】:

    这是一个与编程问题一样的代码维护问题。这是解决它的一种选择:

    • 围绕tempfile.mktemp 创建一个包装函数,其描述性名称与您的域相匹配(例如create_database_path_name 中的某些内容)
    • 在实现中,在 tempfile.mktemp 调用上方写一条评论,解释为什么它被仔细权衡,并认为这种用法是安全的,尽管已弃用。

    第一步确保已弃用函数的调用仅包含在一个位置。第二步确保有一个地方有据可查,以供将来的代码审查。

    如果不推荐使用的功能从模块中消失,您只有一个地方需要修复,例如通过复制原始实现。

    【讨论】:

      【解决方案3】:

      mktemp 弃用的原因与您无关,因为您不打算制作该文件。它会生成随机文件名,这就是您想要的。如果您担心审稿人不理解这一点,那么简单的评论就可以了。或者,您可以使用base64.b64encode(os.urandom(20)).decode('ascii') 之类的名称创建自己的文件名,而不会冒犯他们微妙的感受。

      【讨论】:

      • 代码中的注释未解决有关删除已弃用 API 的问题。
      • @bignose - 它没有被弃用,只是警告它将来可能会被弃用。 OP 总是可以退回到生成他自己的随机名称......但这也说明了为什么“不使用”的表演很愚蠢。您应该知道问题并在适当的时候使用。许多程序使用众所周知的中间文件名,当预先打开的文件不合适时,mktemp 会受益。
      • @tdelaney 我同意你说的每一个字,除了开头的句子; tempfile.mktemp 不幸的是真的是 deprecated since version 2.3。为了强调这一点,它甚至被列在一个可怕的“已弃用的函数和变量部分”下。
      猜你喜欢
      • 2023-02-20
      • 1970-01-01
      • 1970-01-01
      • 2013-07-25
      • 2013-08-09
      • 1970-01-01
      • 2014-11-16
      • 2018-09-16
      • 2017-03-27
      相关资源
      最近更新 更多