dotnet/aspnetcore · error · RuntimeException
Error writing MessagePack data.
Error message
Error writing MessagePack data.
What it means
Wraps MessagePackException/IOException thrown while serializing an outbound message through the Jackson MessagePack ObjectMapper/packer. It is usually caused by an argument type Jackson cannot serialize — no default constructor, circular references, an unsupported type like raw ByteBuffer, or a missing date/time module.
Source
Thrown at src/SignalR/clients/java/signalr/messagepack/src/main/java/com/microsoft/signalr/messagepack/MessagePackHubProtocol.java:189
default:
throw new RuntimeException(String.format("Unexpected message type: %d", messageType.value));
}
int length = message.length;
List<Byte> header = Utils.getLengthHeader(length);
byte[] messageWithHeader = new byte[header.size() + length];
int headerSize = header.size();
// Write the length header, then all of the bytes of the original message
for (int i = 0; i < headerSize; i++) {
messageWithHeader[i] = header.get(i);
}
for (int i = 0; i < length; i++) {
messageWithHeader[i + headerSize] = message[i];
}
return ByteBuffer.wrap(messageWithHeader);
} catch (MessagePackException | IOException ex) {
throw new RuntimeException("Error writing MessagePack data.", ex);
}
}
private HubMessage createInvocationMessage(MessageUnpacker unpacker, InvocationBinder binder, int itemCount, ByteBuffer payload) throws IOException {
Map<String, String> headers = readHeaders(unpacker);
// invocationId may be nil
String invocationId = null;
if (!unpacker.tryUnpackNil()) {
invocationId = unpacker.unpackString();
}
// For MsgPack, we represent an empty invocation ID as an empty string,
// so we need to normalize that to "null", which is what indicates a non-blocking invocation.
if (invocationId == null || invocationId.isEmpty()) {
invocationId = null;
}
View on GitHub (pinned to 294cab2f9b)
Solutions
- Ensure arguments sent to hub methods are plain POJOs serializable by Jackson.
- Register jackson-datatype-jsr310 (and any other needed modules) if sending date/time types.
- Map framework/IO types to simple DTOs (e.g. byte[] instead of ByteBuffer) before sending.
Example fix
// before
hubConnection.send("Upload", someByteBuffer);
// after
hubConnection.send("Upload", someByteBuffer.array()); Defensive patterns
Strategy: validation
Validate before calling
// Java - only send Jackson-serializable POJOs
static boolean isLikelySerializable(Object o) {
return o == null
|| o instanceof String || o instanceof Number || o instanceof Boolean
|| o instanceof java.util.Collection || o instanceof java.util.Map
|| (o.getClass().isArray() && !o.getClass().getComponentType().getName().contains("Buffer"));
} Try / catch
// Java
try {
hubConnection.send("Method", arg).blockingAwait();
} catch (RuntimeException ex) {
if (ex.getMessage() != null && ex.getMessage().contains("writing MessagePack")) {
// replace unserializable arg (ByteBuffer, IO type, etc.) with a plain DTO
}
} Prevention
- Send only plain POJOs that Jackson can serialize (no-arg constructor, accessible fields/getters).
- Register jackson-datatype-jsr310 for date/time types.
- Convert IO/framework types (ByteBuffer, streams) to byte[] or DTOs before sending.
When it happens
Trigger: Passing an object to hubConnection.invoke/send that the MessagePack ObjectMapper cannot serialize; sending IO/framework types or POJOs without accessible constructors/getters.
Common situations: Sending a Java object lacking a no-arg constructor or getters; including unserializable fields (ByteBuffer, InputStream, lambdas); sending java.time types without jackson-datatype-jsr310 registered.
Related errors
- Cannot read message size.
- Messages bigger than 2GB are not supported.
- Incomplete message.
- Invalid message type.
- Invalid headers.
AI-assisted analysis of dotnet/aspnetcore@294cab2f9b (2026-08-06).
Data as JSON: /api/errors/e772f0442dafd4ee.
Report an issue: GitHub.