2016-03-15 43 views
2

是否有可能在setup.py中定义条件entry_points?我注意到有可能标签使用extras的入口点,但即使没有该额外功能安装该包,该入口点也可用。有条件的setuptools entry_points

setup(name='my.package', 
     ... 
     extras_require={ 
      'special': [ 
       'dependency1', 
       'dependency2', 
      ], 
     }, 
     ... 
     entry_points=""" 
     [custom_entrypoint] 
     handlername = my.package.special:feature [special] 
     """, 
) 

似乎为custom_entrypoint即使包而没有special特征(pip install my.package[special])安装是可用的。有没有一种简单的方法来获得像这样的工作?

回答

1

入口点写入package.dist-info/entry_points.txt。我建议看看在setup.py系统上安装了哪些软件包,但这可能对此无济于事,因为在安装其他软件包之前dist-info可能会被pip安装;即使你安装了其他软件包,这些入口点也不会奇迹般地出现,除非你运行setup.pymy.package并带有正确的参数。

我建议你重构,以便有一个包名为my.package,另一个可安装包名为my.package.special;后者将具有my.package,dependency1dependency2作为依赖关系和入口点。现在,如果你想安装my.package它会这样做,没有特别的; pip install my.package.special以获得最重要的特殊功能。

+0

我结束了类似的事情。我没有将功能转移到新的软件包中,而是将它保留在相同的位置。我不想将几个软件包的功能移到新的特殊软件包中,因为我将它用作“实验性”功能切换。相反,我创建了一个名为'app.experimental'的特殊包,并将其作为extras_require包含在其他包中。在执行iter_entry_points循环时,我检查入口点是否满足了他们的要求,如果不是它被忽略('entrypoint.require()'将会引发'pkg_resources.DistributionNotFound')。 – Torkel

+1

@Torkel然后请发布您的解决方案作为替代答案,并[接受它](D) –

+0

创建整个Python包以适应“元依赖”的需要是愚蠢的,这正是'extras_require'的意思。 – amcgregor

0

在你的“插件加载”(无论发生什么事,找到切入点,通过名称或通过枚举全套可用的入口点为给定的命名空间),你需要做类似如下:

import pkg_resources 

# Get a reference to an EntryPoint, somehow. 
plug = pkg_resources.get_entry_info('pip', 'console_scripts', 'pip') 

# This is sub-optimal because it raises on the first failure. 
# Can't capture a full list of failed dependencies. 
# plug.require() 

# Instead, we find the individual dependencies. 

failed = [] 

for extra in sorted(plug.extras): 
    if extra not in plug.dist._dep_map: 
     continue # Not actually a valid extras_require dependency? 

    for requirement in i.dist._dep_map[extra]: 
     try: 
      pkg_resources.require(str(requirement)) 
     except pkg_resources.DistributionNotFound: 
      failed.append((plug.name, extra, str(requirement))) 

我们走了;对于给定的插件,您将获得失败的依赖关系列表(或成功时为not failed),列出entry_point插件名称,[foo]额外的标记以及特定的未满足的程序包要求。

这个实例的一个例子来自web.command包的web versions --namespace子命令。注意如何waitressextras_require满足,其中gevent一个被明确指定gevent包丢失:

Sample usage.

不幸的是我实际上并不多依赖entry_point例如方便的显示出来,这一点很重要要注意列为“缺失”的软件包可能并不总是与extras_require的名称相匹配。