{"record":{"id":"764da9a2e6a93678","repo":"JeffreySu/WeiXinMPSDK","slug":"finance-path-detail","errorCode":null,"errorMessage":"无法加载企业微信 Finance 原生库：{path}。{detail}","messagePattern":"无法加载企业微信 Finance 原生库：(.+?)。(.+?)","errorType":"exception","errorClass":"DllNotFoundException","httpStatus":null,"severity":"critical","filePath":"src/Senparc.Weixin.Work/Senparc.Weixin.Work/AdvancedAPIs/MsgAudit/MsgAuditFinanceNativeApi.cs","lineNumber":380,"sourceCode":"                    \"企业微信 Finance 会话内容存档原生库仅支持 Windows 和 Linux。\");\n            }\n\n            IntPtr linuxHandle;\n            var useLegacy = false;\n            try\n            {\n                linuxHandle = LinuxNative.DlOpen(path, RtldNow);\n            }\n            catch (DllNotFoundException)\n            {\n                useLegacy = true;\n                linuxHandle = LinuxLegacyNative.DlOpen(path, RtldNow);\n            }\n\n            if (linuxHandle == IntPtr.Zero)\n            {\n                var detail = useLegacy ? LinuxLegacyNative.GetError() : LinuxNative.GetError();\n                throw new DllNotFoundException(\n                    $\"无法加载企业微信 Finance 原生库：{path}。{detail}\");\n            }\n\n            return new FinanceLibraryHandle(linuxHandle, false, useLegacy);\n        }\n\n        /// <summary>\n        /// 获取动态库导出函数并转换为指定的 Cdecl 委托。\n        /// </summary>\n        /// <typeparam name=\"TDelegate\">带有 <see cref=\"UnmanagedFunctionPointerAttribute\"/> 的委托类型。</typeparam>\n        /// <param name=\"exportName\">官方 C ABI 导出函数名称。</param>\n        /// <returns>绑定到导出函数的托管委托。</returns>\n        public TDelegate GetDelegate<TDelegate>(string exportName) where TDelegate : Delegate\n        {\n            ThrowIfDisposed();\n            IntPtr symbol;\n            if (_isWindows)\n            {","sourceCodeStart":362,"sourceCodeEnd":398,"githubUrl":"https://github.com/JeffreySu/WeiXinMPSDK/blob/be573f6f94bdbf718dd5f6cdecb137fbc7ff651e/src/Senparc.Weixin.Work/Senparc.Weixin.Work/AdvancedAPIs/MsgAudit/MsgAuditFinanceNativeApi.cs#L362-L398","documentation":"On Linux, dlopen failed to load the WeChat Work Finance shared library: both libdl.so.2 and the legacy libdl.so attempts returned IntPtr.Zero. The wrapper throws DllNotFoundException with the path plus the dlerror() detail string, which names the actual OS-level cause.","triggerScenarios":"Loading the finance .so with a wrong or relative path; the .so has unresolved dependencies (missing libssl/libcrypto versions, missing libcurl); attempting to load an x86 .so into an x64 process; glibc/dl implementation too old.","commonSituations":"Docker linux containers missing the SDK's dependency chain (e.g. OpenSSL 1.1 not installed); publishing only managed dlls without the native .so; alpine/musl images where the glibc-built .so cannot load.","solutions":["Read the dlerror detail in the message — 'No such file or directory' = fix path/publish the .so, 'cannot open shared object file: libssl.so.1.1' = install that dependency.","Verify the .so was published (RuntimeIdentifier linux-x64, native lib copied to output) and use an absolute path.","Check architecture: the .so must match the process (x64). Run `file libWeWorkFinanceSdk.so`.","On alpine/musl images, switch to a glibc-based image (e.g. mcr.microsoft.com/dotnet/aspnet:8.0) or add gcompat."],"exampleFix":"// before\nvar api = MsgAuditFinanceNativeApi.Create(\"libWeWorkFinanceSdk.so\"); // dlopen fails, path not in search dirs\n// after\nvar path = Path.Combine(AppContext.BaseDirectory, \"runtimes\", \"linux-x64\", \"native\", \"libWeWorkFinanceSdk.so\");\nEnvironment.SetEnvironmentVariable(\"LD_LIBRARY_PATH\", Path.GetDirectoryName(path));\nvar api = MsgAuditFinanceNativeApi.Create(path);","handlingStrategy":"try-catch","validationCode":"if (!File.Exists(soPath)) throw new FileNotFoundException(\"Finance .so not published\", soPath);\nif (!RuntimeInformation.ProcessArchitecture.ToString().Contains(\"X64\")) throw new PlatformNotSupportedException(\"x64 required\");","typeGuard":"static bool LinuxLibraryReady(string path) => File.Exists(path) && RuntimeInformation.IsOSPlatform(OSPlatform.Linux);","tryCatchPattern":"try { return FinanceLibraryHandle.Load(path); }\ncatch (DllNotFoundException ex) { logger.LogCritical(ex, \"dlopen failed: {Detail}\", ex.Message); throw; }","preventionTips":["Read the dlerror detail appended to the message — it names the missing dependency.","Publish with RuntimeIdentifier linux-x64 so the .so ships in runtimes/linux-x64/native.","Install the SDK's dependency chain (OpenSSL 1.1, libcurl) in Docker images.","Prefer glibc-based images over alpine for this SDK."],"tags":["native-library","linux","dlopen"],"backgroundTag":"missing-dependency","analyzedSha":"be573f6f94bdbf718dd5f6cdecb137fbc7ff651e","analyzedAt":"2026-09-12T10:01:50.733Z","contentChangedAt":"2026-09-12T10:01:50.733Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}