protobuf icon indicating copy to clipboard operation
protobuf copied to clipboard

WKT serialization is broken with golang/protobuf v1.4.0 and gogoproto_import = false

Open xen0n opened this issue 5 years ago • 2 comments

tl;dr

The following combination is broken:

  • (gogoproto.gogoproto_import) = false in proto files
  • WKTs (google.protobuf.Timestamp and friends) are used
  • github.com/golang/protobuf version >= v1.4.0

WKT fields stop being recognized as such by gogo/protobuf/jsonpb in this case, breaking serialization.

Analysis

With option (gogoproto.gogoproto_import) = false set, WKTs are imported from github.com/golang/protobuf/ptypes packages.

For golang/protobuf >= v1.4.0 (more exactly golang/protobuf@b9f5089fb9d4f7e6d1126161d93549e300c70f50), the XXX_WellKnownType methods on WKT types are gone, but gogo/protobuf/jsonpb is not aware of the protobuf API v2.

https://github.com/gogo/protobuf/blob/5628607bb4c51c3157aacc3a50f0ab707582b805/jsonpb/jsonpb.go#L163-L165

https://github.com/gogo/protobuf/blob/5628607bb4c51c3157aacc3a50f0ab707582b805/jsonpb/jsonpb.go#L206-L207

Notably, one of the affected downstream packages is gogo/gateway, which is mandatory for grpc-gateway users depending on (gogoproto.stdtime) = true fields.

The protobuf API v2 compatibility, as implemented in grpc-gateway, cannot easily be ported to gogo/protobuf. Because golang/protobuf WKT types don't register to the gogo registry, the crucial proto.MessageName() call will return nothing. And the types cannot just be registered in app code either, because the gogo WKTs also have accompanying func init()'s doing the same thing, the names will collide if one does so.

If we don't allow gogo/protobuf/jsonpb to somehow lookup the message type in golang/protobuf registry, which would create a dependency on the latter package, the bug seems impossible to fix without bumping the fork (which I imagine is non-trivial work) or downgrading golang/protobuf (the easiest solution for now).

Any thoughts?

xen0n avatar Apr 24 '20 05:04 xen0n

same problem, any method to solve incompatible with v1.4.0 golang/protobuf ?

FelixSeptem avatar Apr 30 '20 10:04 FelixSeptem

@FelixSeptem First check if you're affected (if you don't use (gogoproto.gogoproto_import) = false or gogo/gateway or gogo/protobuf/jsonpb then you're NOT affected). If you're as unfortunate as me, it seems the only short-term solution is to downgrade. Keeping 1.4.0 version of upstream protobuf seemingly needs updates to gogo/protobuf, which at this point seems unlikely, all maintainers disappeared last year without reason.

xen0n avatar Apr 30 '20 10:04 xen0n