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

含RavenDB的Python脚本转EXE后运行报错OSError: could not get source code

解决RavenDB打包EXE时的OSError: could not get source code问题

问题场景

将包含RavenDB数据库操作的Python脚本通过PyInstaller、cx_Freeze或Auto PY to EXE工具打包为EXE文件后,打包过程显示成功,但运行生成的EXE时触发以下错误:

OSError: could not get source code
[2212] Failed to execute script 'main' due to unhandled exception

涉及的Python脚本代码如下:

from ravendb import DocumentStore

URLS = "http://127.0.0.1:8080/"
DB_NAME = "sa"
store = DocumentStore(urls=URLS, database=DB_NAME)
store.initialize()
class Foo(object):
   def __init__(self, name, key = None):
       self.name = name
       self.key = key

class FooBar(object):
    def __init__(self, name, foo):
        self.name = name
        self.foo = foo

with store.open_session() as session:
    foo = Foo("PyRyDB")
    session.store(foo)
    session.save_changes()

原因分析

RavenDB的Python客户端在序列化自定义类时,会尝试动态读取类的源代码生成序列化元数据,但打包工具会将Python代码编译为字节码并压缩,导致客户端无法获取到源码,从而触发该错误。

解决方法

方法一:代码层面禁用源码依赖

直接修改脚本,通过配置RavenDB的序列化约定或给自定义类添加标识,避免客户端读取源码:

from ravendb import DocumentStore

URLS = "http://127.0.0.1:8080/"
DB_NAME = "sa"
store = DocumentStore(urls=URLS, database=DB_NAME)

# 方案1:修改序列化约定,跳过源码获取
store.conventions.find_collection_name_for_type = lambda t: t.__name__
# 可选:添加更多序列化配置,确保兼容性
store.conventions.should_save_enums_as_integers = True

# 方案2:给自定义类添加序列化标识(二选一即可)
Foo.__raven_class__ = "Foo"
FooBar.__raven_class__ = "FooBar"

store.initialize()

class Foo(object):
   def __init__(self, name, key = None):
       self.name = name
       self.key = key

class FooBar(object):
    def __init__(self, name, foo):
        self.name = name
        self.foo = foo

with store.open_session() as session:
    foo = Foo("PyRyDB")
    session.store(foo)
    session.save_changes()

方法二:针对不同打包工具的配置调整

针对PyInstaller

使用以下命令打包,显式收集RavenDB的所有依赖并保留必要文件:

pyinstaller --onefile --collect-all ravendb --hidden-import ravendb.documents --hidden-import ravendb.documents.session your_script.py
  • --collect-all ravendb:确保RavenDB的所有相关文件都被打包进去
  • --hidden-import:显式指定RavenDB的子模块,避免打包时遗漏

针对cx_Freeze

修改setup.py配置文件,包含RavenDB的所有依赖包:

from cx_Freeze import setup, Executable

executables = [Executable("your_script.py")]

setup(
    name="RavenDBApp",
    version="1.0",
    description="Application with RavenDB integration",
    executables=executables,
    options={
        "build_exe": {
            "packages": ["ravendb", "ravendb.documents", "ravendb.documents.session"],
            "includes": ["your_script"]
        }
    }
)

然后运行python setup.py build完成打包。

针对Auto PY to EXE

  1. 加载你的Python脚本后,切换到Hidden Imports标签,添加以下模块:
    • ravendb
    • ravendb.documents
    • ravendb.documents.session
  2. 切换到Additional Files标签,添加RavenDB的安装目录(一般在Python安装路径\Lib\site-packages\ravendb)
  3. 保持其他默认配置,点击Convert .py to .exe完成打包

内容的提问来源于stack exchange,提问作者Sajad.Y

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.21 12:07:03