You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用C++构建Python扩展并将依赖.so文件纳入Wheel包

把pybind11绑定依赖的共享库打包进Wheel的实现方案

1. 编译绑定库时设置相对RPATH

编译lib_bindings_ab.so时,添加链接器参数,让它优先在自身所在目录查找lib_a.so和lib_b.so,无需依赖系统路径:

  • 用CMake构建的话,添加配置:
    set_target_properties(lib_bindings_ab PROPERTIES
        BUILD_WITH_INSTALL_RPATH ON
        INSTALL_RPATH "$ORIGIN"
    )
    
  • 直接用g++编译的话:
    g++ -shared -fPIC bindings.cpp -o lib_bindings_ab.so -L./path/to/libs -l_a -l_b -Wl,-rpath='$ORIGIN'
    

2. 调整项目目录结构

将所有.so文件放到Python包的子目录中,示例结构:

my_pybind_project/
├── my_package/
│   ├── __init__.py
│   └── native_libs/
│       ├── lib_a.so
│       ├── lib_b.so
│       └── lib_bindings_ab.so
└── setup.py

在__init__.py中完成库的导入逻辑:

import os
import sys
from ctypes import CDLL

# 获取native_libs目录的绝对路径
lib_dir = os.path.join(os.path.dirname(__file__), "native_libs")

# 预加载依赖库(RPATH配置正确时可省略,添加更稳妥)
CDLL(os.path.join(lib_dir, "lib_a.so"))
CDLL(os.path.join(lib_dir, "lib_b.so"))

# 将库目录加入系统路径,导入绑定库
sys.path.insert(0, lib_dir)
from lib_bindings_ab import *  # 替换为你的绑定库导出内容

3. 配置setup.py打包规则

用setuptools确保所有.so文件被包含进Wheel:

from setuptools import setup, find_packages

setup(
    name="my_package",
    version="0.1.0",
    packages=find_packages(),
    package_data={
        "my_package": ["native_libs/*.so"]
    }
)

4. 构建与验证Wheel

  • 构建Wheel包:
    pip install wheel
    python setup.py bdist_wheel
    
  • 验证内容:解压生成的.whl文件,检查my_package/native_libs/下是否包含所有三个.so文件。
  • 测试安装:在干净环境中执行pip install 生成的wheel文件名,导入包验证功能正常。

额外注意事项

  • Linux平台建议用auditwheel处理Wheel,提升跨发行版兼容性:
    pip install auditwheel
    auditwheel repair dist/my_package-0.1.0-cp310-cp310-linux_x86_64.whl
    
    修复后的Wheel存放在fixed/目录中。
  • 不同平台(Linux、macOS、Windows)的.so/.dylib/.dll文件需分开构建,发布对应平台的Wheel。
  • 若绑定库依赖系统级第三方库(如OpenCV、Boost),仍需用户提前安装,但自定义的lib_a.so/lib_b.so可正常打包。

内容的提问来源于stack exchange,提问作者tenspd137

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 04:12:32