VictoriaMetrics/VictoriaMetrics · error
cannot unmarshal value
Error message
cannot unmarshal value
What it means
Raised at lib/protoparser/datadogv2/parser.go:258 when Point field 1 (double value) in a DataDog v2 series payload cannot be read: FieldContext.Double() returned false because the field's wire type is not fixed64 (the protobuf encoding of double). The point, and thus the request, is rejected.
Source
Thrown at lib/protoparser/datadogv2/parser.go:258
func (pt *Point) unmarshalProtobuf(src []byte) (err error) {
// message Point {
// double value = 1;
// int64 timestamp = 2;
// }
//
// See https://github.com/DataDog/agent-payload/blob/d7c5dcc63970d0e19678a342e7718448dd777062/proto/metrics/agent_payload.proto
var fc easyproto.FieldContext
for len(src) > 0 {
src, err = fc.NextField(src)
if err != nil {
return fmt.Errorf("cannot unmarshal next field: %w", err)
}
switch fc.FieldNum {
case 1:
value, ok := fc.Double()
if !ok {
return fmt.Errorf("cannot unmarshal value")
}
pt.Value = value
case 2:
timestamp, ok := fc.Int64()
if !ok {
return fmt.Errorf("cannot unmarshal timestamp")
}
pt.Timestamp = timestamp
}
}
return nil
}
// Resource is series resource from DataDog POST request to /api/v2/series
//
// See https://docs.datadoghq.com/api/latest/metrics/#submit-metrics
type Resource struct {
Name string `json:"name"`View on GitHub (pinned to 5079fb58f1)
Solutions
- Verify field 1 of the Point message is wire type 1 (fixed64) via protoc --decode_raw.
- Fix the sender to declare `double value = 1;` in the Point proto and regenerate the encoder.
- Update the sending SDK/agent to the official agent-payload version.
- Log the wrapped inner error and reject the offending series rather than accepting zero values.
Example fix
// before: value written as varint float bits
buf = appendVarint(buf, math.Float64bits(v))
// after: declare double in proto so it is fixed64-encoded
// message Point { double value = 1; int64 timestamp = 2; }
proto.Marshal(&pb.Point{Value: v, Timestamp: ts}) Defensive patterns
Strategy: validation
Validate before calling
// Point.value must be a double (fixed64, wire type 1):
// protoc --decode_raw < point.bin => "1: 0x4059000000000000"
if math.IsNaN(value) || math.IsInf(value, 0) {
// still encodable, but ensure it goes through proto.Marshal, not hand-rolled encoding
_ = proto.Marshal(&pb.Point{Value: value, Timestamp: ts})
} Try / catch
if err := datadogv2.UnmarshalProtobuf(&req, body); err != nil {
if strings.Contains(err.Error(), "cannot unmarshal value") {
log.Printf("point value encoded with wrong wire type: %v", err)
}
http.Error(w, "bad point value", http.StatusBadRequest)
return
} Prevention
- Declare point value as `double` in the proto so it is fixed64-encoded; avoid varint float encodings.
- Use generated protobuf marshalers exclusively for Point messages.
- Round-trip test every Point encoding change in CI.
- Keep agent-payload proto revisions in sync between sender and VictoriaMetrics.
When it happens
Trigger: A Point submessage encodes value (field 1) as varint/fixed32/length-delimited instead of fixed64, or the field data is truncated before 8 bytes.
Common situations: Hand-rolled encoders writing float values as varints; clients built against a proto where value was declared as a different type; corrupt payloads after queueing/retry pipelines.
Related errors
- cannot read resource data
- cannot unmarshal source_type_name
- cannot unmarshal tag
- cannot unmarshal timestamp
- cannot unmarshal type
AI-assisted analysis of VictoriaMetrics/VictoriaMetrics@5079fb58f1 (2026-09-03).
Data as JSON: /api/errors/63d93935abd41bfa.
Report an issue: GitHub.