.NET 6.0跨EXE调用C#类库报SqlClient平台不支持异常
根本原因
这是典型的.NET 依赖传递拷贝缺失导致的加载错误,和SqlClient本身的平台兼容性无关:
你直接在控制台程序运行类库时,控制台作为直接启动项目,会通过NuGet还原逻辑把System.Data.SqlClient/Microsoft.Data.SqlClient/OleDb相关的所有平台特定实现DLL全部拷贝到输出目录,运行时能加载到正确的实现文件,所以不会报错。
当你通过独立exe间接调用类库DLL时,VS编译默认不会把类库的未被主程序直接引用的传递依赖拷贝到exe的输出目录,运行时只会加载到这些库的公开接口占位程序集,找不到对应平台的具体实现代码,就会抛出PlatformNotSupportedException。
修复步骤
按优先级从高到低尝试,每一步做完都重新编译验证:
- 优先废弃老旧的
System.Data.SqlClient,这个库已经停止维护,在.NET 5+平台本身就存在大量适配bug,统一替换为官方维护的Microsoft.Data.SqlClient,类库和主exe项目安装的SqlClient、System.Data.OleDb版本必须完全一致,避免版本冲突。 - 在调用类库的主exe项目中,通过NuGet直接安装和类库同版本的
Microsoft.Data.SqlClient、System.Data.OleDb包,不要仅添加类库DLL的文件引用。编译后检查exe输出目录,确认根目录存在上述两个DLL,且runtimes文件夹下包含对应运行架构(win-x64/win-x86)的平台实现文件。 - 如果不想在主exe项目加额外的NuGet引用,就修改类库项目的csproj配置,在
<PropertyGroup>节点下添加配置,强制编译时把类库的所有依赖拷贝到类库输出目录:
<CopyLocalLockFileAssemblies>true</CopyLocalLockFileAssemblies>
- 检查两个项目的目标框架配置(TFM)必须完全匹配,不要一个是纯跨平台的
net6.0,另一个是带Windows特定绑定的net6.0-windows,TFM不匹配会导致NuGet还原时拉取错误版本的依赖。 - 如果你是通过反射动态加载类库DLL(比如用
Assembly.LoadFile),请替换为Assembly.LoadFrom,必要时注册AppDomain.CurrentDomain.AssemblyResolve事件,手动从类库所在目录加载缺失的依赖,避免运行时只在exe根目录找文件。
验证标准
重新编译后,主exe输出目录满足以下两个条件即可正常运行:
- 根目录存在版本匹配的
Microsoft.Data.SqlClient.dll、System.Data.OleDb.dll runtimes目录下存在对应系统架构的SqlClient原生实现DLL
内容的提问来源于stack exchange,提问作者hbib
相关产品推荐
相关产品推荐

