py2exe: 排除一个想导入所有部分的包的部分
我正在尝试使用py2exe来打包我的程序,并且想尽量减少使用的第三方库。我希望只包含一个大第三方包中必要的小部分,但我不知道怎么做才能避免在运行时调用这个包的__init__.py
文件,因为它会导入很多我不想要的内容。
下面是我的情况总结:
myscript.py: from BigPackage.SmallSubset import TheOnlyFunctionIReallyNeed
BigPackage/__init__.py: import SmallSubset, HugeUnwantedSubset
BigPackage/SmallSubset.py: import AcceptableDependencies
BigPackage/HugeUnwantedSubset.py: import UnacceptablyHugeDependencies
问题是,即使我成功地包含了BigPackage
的一些部分,但当在运行时调用import BigPackage.SmallSubset
时,BigPackage/__init__.py
会先运行,这样它就会尝试导入那些我不想要的部分,从而导致错误。如果我能让py2exe只包含BigPackage/SmallSubset.py
而不包含BigPackage/__init__.py
,那就好了,但我一直没能让py2exe理解这个想法。我在我的setup.py
文件中尝试了以下几种方法:
import BigPackage # let's try a Deny/Allow approach:
options[ 'py2exe' ][ 'excludes' ].append( 'BigPackage' )
options[ 'py2exe' ][ 'includes' ].append( 'BigPackage.SmallSubset' )
# nope, py2exe fails with 'ImportError: No module named BigPackage' in py2exe/mf.py
...还有:
import BigPackage # this seems less plausible, but worth a try:
options[ 'py2exe' ][ 'excludes' ].append( 'BigPackage.__init__' )
# nope, __init__.pyc still turns up in dist
...还有:
import BigPackage # really getting desperate now:
options[ 'py2exe' ][ 'excludes' ].append( BigPackage.__file__ )
# nope, __init__.pyc still turns up in dist
...但都没有成功。有人知道怎么解决这个问题吗?
2 个回答
0
你想要的这个功能,如果不对BigPackage库进行修改,是不可能实现的。
0
所有的解决方案看起来都不太靠谱(可以看看问题下的评论)。不过,我最后决定不去修改 __init__.py
,而是采用了一个新的方法:我会进去把我需要的特定内容提取出来,然后复制到临时文件中。
import sys, os, shutil
# awkward kludge to include BigPackage.SmallSubset by hand without having to include the rest of BigPackage
src = [ os.path.join( x, 'BigPackage', 'SmallSubset.py' ) for x in sys.path ]
src = [ x for x in src if os.path.isfile( x ) ][ 0 ]
shutil.copyfile( src, 'BigPackageSmallSubset.py' )
import BigPackageSmallSubset
options = { 'py2exe': { 'excludes' : [ 'BigPackage' ], 'includes' : [ 'BigPackageSmallSubset' ], 'compressed' : True, }, }
# setup( ..., options=options, ... )
os.remove( 'BigPackageSmallSubset.py' )
os.remove( 'BigPackageSmallSubset.pyc' )
接着,我让 myscript.py
能够适应可能出现的不同情况:
try: from BigPackage.SmallSubset import TheOnlyFunctionIReallyNeed
except ImportError: from BigPackageSmallSubset import TheOnlyFunctionIReallyNeed