JeffreySu/WeiXinMPSDK · error · InvalidOperationException

Finance SDK 返回了无效的 长度: 。

Error message

Finance SDK 返回了无效的 {bufferName} 长度:{length}。

What it means

ReadBytes guards every buffer returned by the WeChat Work (企业微信) Finance SDK. When the SDK reports a negative buffer length (for the outindexbuf or media data buffer), the wrapper cannot safely allocate a byte array, so it throws InvalidOperationException naming the offending buffer. A negative length means the native SDK violated its contract or the caller passed a struct pointer from a failed/unfinished operation.

Solutions

  1. Verify the loaded libWeWorkFinanceSdk library matches the process architecture (x64 vs x86).
  2. Ensure GetMediaData returned 0 (success) and IsMediaDataFinished is true before reading data buffers.
  3. Re-create the MediaData object and retry the media download; a transient SDK failure can poison the struct.
  4. Check that your SDK version matches the one the wrapper was built against.

Example fix

// before
var bytes = financeApi.GetMediaBytes(mediaData); // throws if datalen < 0
// after
if (!financeApi.IsMediaDataFinished(mediaData))
{
    throw new TimeoutException("media download not finished");
}
var bytes = financeApi.GetMediaBytes(mediaData);
Defensive patterns

Strategy: validation

Validate before calling

int len = GetDataLen(mediaData);
if (len < 0) throw new InvalidOperationException("Finance SDK returned invalid data length");

Type guard

static bool HasValidBuffer(IntPtr ptr, int len) => len >= 0 && (len == 0 || ptr != IntPtr.Zero);

Try / catch

try { var bytes = api.GetMediaBytes(mediaData); }
catch (InvalidOperationException ex) { logger.LogError(ex, "Finance SDK buffer invalid"); /* retry download */ }

Prevention

When it happens

Trigger: Calling GetChatData/GetMediaData via GetMediaBytes or GetIndexBufBytes when the SDK fills MediaData.outindexbuflen / MediaData.datalen with a negative int (SDK internal failure, uninitialized MediaData, or ABI mismatch from a wrong-architecture library).

Common situations: Running an x86 SDK dll on x64 process (or vice versa) so struct fields misalign; reading media data before GetMediaData finished; passing a default(IntPtr)-based MediaData after a failed call.

Understand the failure class

Background: "invalid response format", "malformed payload", "missing data field": when an API returns 200 but the response shape is wrong — this error's family across 23 libraries.

Related errors


AI-assisted analysis of JeffreySu/WeiXinMPSDK@be573f6f94 (2026-09-12). Data as JSON: /api/errors/edf5ffda8a502659. Report an issue: GitHub.

Appendix: source

Thrown at src/Senparc.Weixin.Work/Senparc.Weixin.Work/AdvancedAPIs/MsgAudit/MsgAuditFinanceNativeApi.cs:250

                return LinuxLibraryName;
            }

            throw new PlatformNotSupportedException(
                "企业微信官方未提供当前操作系统可用的 Finance 会话内容存档原生库。" +
                "请在 Windows 或 Linux 上运行,并在 LibraryPath 中指定对应的官方库。");
        }

        private static string ReadUtf8(IntPtr pointer, int length, string bufferName)
        {
            var bytes = ReadBytes(pointer, length, bufferName);
            return bytes.Length == 0 ? string.Empty : Encoding.UTF8.GetString(bytes);
        }

        private static byte[] ReadBytes(IntPtr pointer, int length, string bufferName)
        {
            if (length < 0)
            {
                throw new InvalidOperationException($"Finance SDK 返回了无效的 {bufferName} 长度:{length}。");
            }

            if (length == 0)
            {
                return Array.Empty<byte>();
            }

            if (pointer == IntPtr.Zero)
            {
                throw new InvalidOperationException($"Finance SDK 返回的 {bufferName} 指针为空,但长度为 {length}。");
            }

            var bytes = new byte[length];
            Marshal.Copy(pointer, bytes, 0, length);
            return bytes;
        }

        [UnmanagedFunctionPointer(CallingConvention.Cdecl)]

View on GitHub (pinned to be573f6f94)