2013-04-10 37 views
1

我们的主应用程序有一些额外的功能,用户可以启用。这些功能都在他们自己的目录中。这些功能可能需要额外的依赖性。我正在考虑将那些文件放在requires.txt文件中。在运行时,如果功能会中断,我们希望让人们知道。我目前正在考虑这样的事情:python:如何在运行时检查额外的需求?

def checkfeature(feature): 
    everything_okay = True 
    f = pkg_resources.resource_stream(feature, "requires.txt") 
    with f: 
    for r in pkg_resources.parse_requirements(f): 
     if pkg_resources.working_set.find(r) is None: 
     print "%r not found, please install, otherwise this feature does not work" % (r,) 
     everything_okay = False 
    return everything_okay 

这是正确的,pythonic的做事方式?这有意义吗?

小更新: 为什么这么复杂,不只是try: import ... except ImportError: ...像一个答案建议:

  1. 我们的插件可能有一堆依赖。创建如下所示的实际代码非常冗长。
  2. 一些插件可能需要特定版本的软件包。测试需要使用专门的测试或者使用pkg_resources。所以这就是我上面的想法使用pkg_resources的原因。
  3. 我们想运行可以运行的插件的单元测试。在单元测试中处理ImportError并不好。有一个can_we_unit_test_this_plugin(plugin)函数使事情变得更容易。

第二次更新:extra_require怎么样setup.py

  1. 人们错过安装这些经常。好吧,不好的借口。
  2. 我的愿景是,setup.py直接从上面提到requires.txt加载extra_require在个别功能的个别子目录。但这确实是下一步。

回答

4

一般情况下,你只是试图进口的依赖,并妥善地处理ImportError例外:

try: 
    import dependency 
except ImportError: 
    # dependency missing, issue a warning 
    import warnings 
    warnings.warn('dependency not found, please install to enable xyz feature') 

你可以在你的extras_require参赛名单这种依赖setuptools的基础setup.py脚本。 pip,easy_installzc.buildout都可以处理安装这些附加功能。见Declaring “Extras” (optional features with their own dependencies)

如果您有这些条件,您可以使用extras_require条目列出最低版本要求。是的,用户可能已经安装了旧版本的依赖项。我只是清楚地记录了需求。真的,测试功能,而不是版本。如果您需要更新的版本,因为已添加某个API方法?测试该方法而不是版本。

但是,它听起来好像你可能要打包的插件,独立包代替,然后列出extras_require那些。我会用entry points来注册和枚举这些插件。那样你不是需要测试进口的包,你只需要枚举注册的入口点。每个插件都列出了它们自己的依赖关系,并拥有自己的单元测试。

+0

好的,我应该补充说,我们可能需要特定版本的特定软件包。我应该补充说,我们希望事先知道一个功能是否可行。因为这是启用该功能的单元测试的一种方式。我会尽快改进我的问题。 – Elrond 2013-04-10 14:09:36

+0

我还在我的问题上附加了一个关于'extra_require'的注释。我将这看作是故事的另一部分。关于功能检查:是的,这通常是一件好事,但有时可能会非常难看。特别是,如果你遇到特定版本的复杂错误。另请注意:上述检查功能不是检查的唯一方法。有问题的功能可以自行添加到该功能。 – Elrond 2013-04-10 14:26:50

+0

@Elrond:expanded;我想,你想把插件分成单独的包。 – 2013-04-10 14:46:35

相关问题