# proto: cannot parse invalid wire-format data

- **ID:** `go/proto-unmarshal-cannot-parse-invalid-wire-format`
- **Domain:** go
- **Category:** data_error
- **Verification:** ai_generated
- **Fix Rate:** 80%

## Root Cause

proto.Unmarshal received bytes that are not valid protobuf wire format for the target message type. Typical causes: the payload is JSON/plain text, it was truncated, it's a different message type, or a length-delimited field has a corrupt varint length prefix.

## Version Compatibility

| Version | Status | Introduced | Deprecated |
|---------|--------|------------|------------|
| google.golang.org/protobuf 1.28+ | active | — | — |

## Workarounds

1. **** (85% success)
   ```
   Validate and log the raw bytes before unmarshaling, and confirm the wire type matches:

if len(data) == 0 { return errors.New("empty payload") }
if err := proto.Unmarshal(data, msg); err != nil {
    log.Printf("unmarshal failed, first 32 bytes: %x", data[:min(32,len(data))])
    return fmt.Errorf("bad proto payload: %w", err)
}
   ```
2. **** (80% success)
   ```
   Ensure the sender and receiver use the same generated message and that framing (length prefix) is stripped correctly, e.g. with a length-delimited reader:

r := protoio.NewDelimitedReader(conn, 1<<20)
msg := &pb.Foo{}
if err := r.ReadMsg(msg); err != nil { return err }
   ```

## Dead Ends

- **** — Wire-format parsing is deterministic; identical bytes always fail identically. Retrying wastes CPU and never succeeds. (98% fail)
- **** — If the bytes are binary protobuf, protojson will reject them; if they are JSON, the original proto.Unmarshal was simply the wrong parser choice — the fix is picking the right one, not blindly swapping. (75% fail)
