【问题标题】:ImportError: DLL load failed - Only when using IBM DB moduleImportError: DLL load failed - 仅在使用 IBM DB 模块时
【发布时间】:2020-08-06 05:38:27
【问题描述】:

在 Python 或 Internet 连接不可用的服务器中将我的 python 文件作为 exe 文件运行时,我观察到“DLL LOAD FAILED 错误消息。我的其他 exe 文件没有任何问题,这个包含 IBM DB 模块的文件是只有一个有问题。

我尝试了这里给出的解决方案:ImportError: DLL load failed: The specified module could not be found -- IBM DB2 - 仍然面临着麻烦。

当我在本地机器(笔记本电脑)上运行同一个 exe 文件时 - 它可以工作,但在服务器中 - 它不工作。

下面是我用来转换exe文件的命令:

pyinstaller -y --additional-hooks-dir=. --hidden-import ibm_db_sa.ibm_db --hidden-import ibm_db_dbi --hidden-import ibm_db --add-binary C:\Python\Python37\Lib\site-packages\ibm_db_dlls\ibm_db.dll;.\ibm_db_dlls --onefile mypythonfile.py

下面是我运行exe文件时的错误信息:

E:\SuspenseReport>mypythonfile.exe
c:\python\python37\lib\site-packages\PyInstaller\loader\pyimod03_importers.py:62
3: MatplotlibDeprecationWarning:
The MATPLOTLIBDATA environment variable was deprecated in Matplotlib 3.1 and wil
l be removed in 3.3.
Traceback (most recent call last):
  File "mypythonfile.py", line 14, in <module>
    import ibm_db
  File "c:\python\python37\lib\site-packages\PyInstaller\loader\pyimod03_importe
rs.py", line 623, in exec_module
  File "site-packages\ibm_db.py", line 10, in <module>
  File "site-packages\ibm_db.py", line 9, in __bootstrap__
  File "imp.py", line 342, in load_dynamic
ImportError: DLL load failed: The specified module could not be found.
[16360] Failed to execute script mypythonfile

版本:

Python Version: 3.7.6
Pyinstaller Version: 3.6
ibm-db Version: 3.0.1
os : Windows

请告知可以采取哪些措施来解决此问题。

【问题讨论】:

    标签: python python-3.x dll db2 pyinstaller


    【解决方案1】:

    我更新了您引用的另一个答案。

    如果您的 python 代码没有明确使用 SQLAlchemy,您不需要将它包含在 pyinstaller 构建命令行中。如果您使用的是 SQLAlchemy,那么您可能需要其他答案中提到的其他钩子。

    当您将 EXE 部署在与构建环境(工作站)不同的主机名(服务器)上时,目标服务器可能尚未安装 Db2 客户端。

    python ibm_db 使用 CLI(调用级接口)来访问 Db2 数据库。 Db2-client 提供了这样一个 CLI 接口。如果您没有任何可用于 ibm_db 的 Db2 客户端,那么 ibm_db 模块将无法加载并且您将看到您的症状。当您安装 ibm_db 时,默认情况下它会在您的工作站上添加一个名为 clidriver 的小型 Db2 客户端(零安装),但 pyinstaller 不会将其包含在您的包中。

    如果服务器尚未安装 Db2-client,并且您不希望单独安装和配置 Db2-client,那么您可以重新构建 pyinstaller 包以包含 python ibm_db 模块默认提供的 clidriver .要重建,您需要在 pyinstaller 中包含额外的命令行选项。

    要包含 clidriver,首先通过命令 pip show ibm_db 找到它的位置,然后找到 Location: 值,并将 \clidriver 值附加到此路径。这是 clidriver 的完全限定路径,例如 c:\path\to\clidriver

    接下来,使用附加选项重新运行之前的 pyinstaller 命令

    --add-data="c:\path\to\clidriver;.\clidriver"

    如果您的 python 代码依赖于外部配置的 DSN(而不是代码中的长连接字符串),并且如果您制作了一个合适的 db2dsdriver.cfg 文件,其中包含这些 DSN 以及每个数据库或 DSN 所需的任何参数,那么您还需要在你的包中包含那个db2dsdriver.cfg 文件。如果您的代码不依赖于外部配置的 DSN,则可能不需要此步骤。如果您愿意,您还可以编写 db2cli 命令行以在服务器上运行以配置 db2dsdriver.cfg 而不是捆绑它。

    如果您需要使用目标服务器主机名上的 odbcad32.exe 可执行文件来配置 Db2 DSN,您还需要在交付 pyinstaller 构建的 EXE 文件后在目标服务器上运行 clidriver setup 命令行db2cli install -setup 以管理员身份从 clidriver\bin 目录执行。如果您不需要在目标主机名上使用odbcad32.exe 之类的 GUI,则可以省略此步骤。

    如果您使用与 Db2 的加密连接(即 SSL/TLS)或基于证书的身份验证,那么您的捆绑包可能还需要包含相关证书和/或密钥库/存储。因此,您的 pyinstaller 版本可能需要其他选项。

    在目标服务器上,将完全限定的 clidriver\bin 目录添加到 PATH 环境变量中可能会很有用。确保包含任何配置文件或数据文件的目录对于需要访问它们的任何用户或组都是可读的。

    此外,请注意,IBM 每年都会更新几次其 clidriver 软件,其中包含安全修复和错误修复以及新功能。测试后,您的 pyinstaller 构建的 EXE 应刷新并重新分发以包含刷新的 clidriver。

    【讨论】:

    • 非常感谢您的详细解释。 CLI 驱动程序的 -add-data 解决了我的问题。再次感谢您的意见。
    猜你喜欢
    • 2020-12-04
    • 2020-07-02
    • 2020-06-30
    • 2015-12-16
    • 2019-08-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多