Python: 始终导入目录中的最后修订版

Python: always import the last revision in the directory

假设我们有以下数据库结构,数据存储在 python 个文件中,准备导入:

data_base/
  foo_data/
      rev_1.py
      rev_2.py
  bar_data/
      rev_1.py
      rev_2.py
      rev_3.py

在我的主脚本中,我想导入文件夹中可用数据的最后 修订版。例如,而不是这样做:

from data_base.foo_data.rev_2 import foofoo
from data_base.bar_data.rev_3 import barbar

我要调用一个方法:

import_from_db(path='data_base.foo_data', attr='foofoo', rev='last')
import_from_db(path='data_base.bar_data', attr='barbar', rev='last')

我可以采用数据库的相对路径并使用 glob.glob 搜索最新修订版,但为此,我应该知道 data_base 文件夹的路径,这会使事情变得复杂(假设 data_base 的父文件夹在 sys.path 中,所以 from data_base.*** import 可以工作)

是否有一种有效的方法可以检索仅知道其中一部分的完整路径 (data_base.foo_data)?其他想法?

我觉得安装最后一个版本比较好

但继续您的流程,您可以在模块上使用 getattr

from data_base import foo_data
i = 0
while True:
    try:
        your_module = getattr(foo_data, f'rev_{i}')
    except AttributeError:
        break
    i += 1
# Now your_module is the latest rev

@JohnDoriaN 的想法使我找到了一个非常简单的解决方案:

import os, glob

def import_from_db(import_path, attr, rev_id=None):
    """
    """
    # Get all the modules/folders names
    dir_list = import_path.split('.')
    
    # Import the last module
    exec(f"from {'.'.join(dir_list[:-1])} import {dir_list[-1]}")
    db_parent = locals()[dir_list[-1]]
    
    # Get an absolute path to corresponding to the db_parent folder
    abs_path = db_parent.__path__._path[0]
    rev_path = os.path.join(abs_path, 'rev_*.py')
    rev_names = [os.path.basename(x) for x in glob.glob(rev_path)]
    
    if rev_id is None:
        revision = rev_names[-1]
    else:
        revision = rev_names[rev_id]
    
    revision = revision.split('.')[0]
    
    # import attribute
    exec(f'from {import_path}.{revision} import {attr}', globals())

一些解释:

  • 显然(我不知道这一点),我们可以将文件夹作为模块导入;这个模块有一个 __path__ 属性(使用内置的 dir 方法找到)。
  • glob.glob 允许我们使用正则表达式来搜索目录中文件所需的模式。
  • 使用不带参数的exec将仅在本地命名空间(方法的命名空间)中导入,因此不会污染全局命名空间。
  • 使用 execglobals() 允许我们在全局命名空间中导入。