PyQt5可执行文件由于缺少DLL而崩溃

时间:2019-04-11 05:56:43

标签: python pyqt5 pyinstaller

我的问题与我使用pyinstaller创建的pyqt5可执行文件有关。我正在使用的唯一命令是:

pyinstaller script.py

我对Pyinstaller的输出消息不太熟悉。因此,我发布这个问题是为了防止其他人帮助我弄清楚缺少的模块或文件是什么。

这是整个Compile输出的副本:

Github - Pyinstaller Output

这是出现的错误的副本。它发生的时间大约是毫秒:

Missing DLLs

任何评论或帮助都将受到赞赏。如果您认为有可能的解决方案,请尝试回答。我相信它值得研究。希望这很简单,并且由于我缺乏知识。

另一个说明,我正在导入/使用模块 ibm_db 和包装器模块 ibm_db_dbi

这是我的规格文件的副本:

# -*- mode: python -*-

block_cipher = None

added_files = [
                (r'C:\Python37\Lib\site-packages\ibm_db_dlls\ibm_db.dll', '.')
              ]

a = Analysis(['InheritMainWindow.py'],
             pathex=['c:\\Python37\\PDFMaker_v3\\Prototype',
                     'C:\\Python37\\Lib\\site-packages\\',
                     'C:\\Python37\\Lib\\site-packages\\sqlalchemy\\connectors\\',
                     'C:\\Python37\\Lib\\site-packages\\clidriver\\',
                     'C:\\Python37\\Lib\\site-packages\\ibm_db_dlls',
                     'C:\\Python37\\Lib\\site-packages\\ibm_db.py'],
             binaries=[('ibm_db.dll', 'ibm_db_dlls')],
             datas=[],
             hiddenimports=['ibm_db', 'ibm_db_dbi'],
             hookspath=[],
             runtime_hooks=[],
             excludes=[],
             win_no_prefer_redirects=False,
             win_private_assemblies=False,
             cipher=block_cipher,
             noarchive=False)
pyz = PYZ(a.pure, a.zipped_data,
             cipher=block_cipher)
exe = EXE(pyz,
          a.scripts,
          [],
          exclude_binaries=True,
          name='InheritMainWindow',
          debug=False,
          bootloader_ignore_signals=False,
          strip=False,
          upx=True,
          console=True )

a.binaries = [x for x in a.binaries if os.path.dirname(x[1]).find("IBM") < 0]
coll = COLLECT(exe,
               a.binaries,
               a.zipfiles,
               a.datas,
               strip=False,
               upx=True,
               name='InheritMainWindow')

请注意,您应该可以通过以下方法重复该问题:

import ibm_db
print('hello!')

在命令提示符下:

pyinstaller hello.py

在dist文件夹中执行exe时,您将得到与上述相同的错误。

以下是我尝试解决此问题的列表:

1)这样在二进制文件中提供完整路径:

binaries=[(r'C:\Python37\Lib\site-packages\ibm_db_dlls\ibm_db.dll', 'ibm_db_dlls')]

这不会导致崩溃仍然发生。而且我已经看到 ibm_db_dlls 文件夹出现在我的 dist 文件夹中。因此正在添加二进制文件,但是只是看不到它。

2)从ibm开发人员论坛: https://developer.ibm.com/answers/questions/448999/python-3-db2-windows-10-problems-and-script-compil/

建议的解决方案是使用--clean选项。我已经在'hello.py'上尝试过此选项,该选项仅在导入ibm_db程序包时就可以作为exe起作用。但是此解决方案不适用于我的主项目。

更正:即使在简单的hello.py示例中,此操作也不起作用。

最终更新:我在下面提供了一个解决方案!

2 个答案:

答案 0 :(得分:2)

所以我解决了这个问题。我希望这应该对很多人有所帮助。解决方案的第一部分是PATHEX列表。我必须更新此列表以指向我系统的所有IBM目录:

# -*- mode: python -*-

block_cipher = None


a = Analysis(['InheritMainWindow.py'],
             pathex=['c:\\Python37\\PDFMaker_v3',
                     'C:\\Python37\\Lib\\site-packages\\ibm_db_dlls',
                     'C:\\Program Files (x86)\\ibm\\gsk8\\lib', 
                     'C:\\Program Files (x86)\\ibm\\gsk8\\bin', 
                     'C:\\Program Files (x86)\\IBM Informix Client SDK\\bin', 
                     'C:\\Program Files (x86)\\IBM\\SQLLIB_01\\BIN', 
                     'C:\\Program Files (x86)\\IBM\\SQLLIB_01\\FUNCTION', 
                     'C:\\Program Files (x86)\\IBM\\SQLLIB_01\\BIN', 
                     'C:\\Program Files (x86)\\IBM\\SQLLIB_01\\FUNCTION', 
                     'C:\\Program Files (x86)\\ibm\\gsk8\\lib', 
                     'C:\\Program Files (x86)\\ibm\\gsk8\\bin', 
                     'C:\\Program Files (x86)\\IBM Informix Client SDK\\bin'],
             binaries=[(r'C:\Python37\Lib\site-packages\ibm_db_dlls\ibm_db.dll', 'ibm_db_dlls')],
             datas=[],
             hiddenimports=[],
             hookspath=[],
             runtime_hooks=[],
             excludes=[],
             win_no_prefer_redirects=False,
             win_private_assemblies=False,
             cipher=block_cipher,
             noarchive=False)
pyz = PYZ(a.pure, a.zipped_data,
             cipher=block_cipher)
exe = EXE(pyz,
          a.scripts,
          [],
          exclude_binaries=True,
          name='InheritMainWindow',
          debug=False,
          bootloader_ignore_signals=False,
          strip=False,
          upx=True,
          console=True )
coll = COLLECT(exe,
               a.binaries,
               a.zipfiles,
               a.datas,
               strip=False,
               upx=True,
               name='InheritMainWindow')

答案的下一部分在弄清楚方面确实很棘手。在imb_db.py文件中找到它:

import os

if 'clidriver' not in os.environ['PATH']:
    os.environ['PATH'] = os.environ['PATH'] + ";" + os.path.join(os.path.abspath(os.path.dirname(__file__)), 'clidriver', 'bin')  
def __bootstrap__():
   global __bootstrap__, __loader__, __file__
   import sys, pkg_resources, imp
   __file__ = pkg_resources.resource_filename(__name__,'ibm_db_dlls\\ibm_db.dll')
   __loader__ = None; del __bootstrap__, __loader__
   imp.load_dynamic(__name__,__file__)
__bootstrap__()

我必须更新路径变量以包含clidriver目录:

C:\Python37\Lib\site-packages\clidriver\bin

imb_db.py应该将其添加到路径中,但是其添加格式或目录错误。这样下一行:

__file__ = pkg_resources.resource_filename(__name__,'ibm_db_dlls\\ibm_db.dll')

最终没有找到.dll文件。因此,在进行了这两次更新之后,该程序将运行并成功连接到远程DB2数据库。

答案 1 :(得分:1)

@RockAndRoleCoder感谢您的提问和回答。我在Windows7 Python3.7 ibm-db 3.0.1中遇到了相同的情况
根据您的提示,我认为原因是exe在clidriver \ bin和ibm_db.dll中找不到* .dll, 并用类似的方法分两步解决

拳头: 与您相同,将clidriver目录添加到系统路径

**\site-packages\clidriver\bin

第二 带参数--add-binary

 Pyinstaller --add-binary **\Lib\site-packages\ibm_db_dlls\ibm_db.dll;.\ibm_db_dlls myproject.py

那就可以了!