-
Notifications
You must be signed in to change notification settings - Fork 1.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
protoc-gen-go: generate MarshalJSON/UnmarshalJSON methods for messages #256
Comments
Ok so what would the generated MarshalJSON method do. |
@awalterschulze: This proposal is about the API, not the implementation. Initially it would probably just call jsonpb. If we find it's worth the extra overhead to generate code (or use some other optimization technique to avoid reflection), it would be easy enough to change the implementation while preserving the same API. |
Ok so encoding/json is going to call the generated MarshalJSON method which is going to call jsonpb which sometimes also calls encoding/json. Some psuedo circular dependency. We hope it doesn't become a loop. Sounds like any easy bug to make. Maybe we can list the differences between encoding/json en jsonpb? Even if its just for the record. I know one reason was the fact that non string keys could not be encoded by encoding/json. But the go1.7 release notes now state the following:
Which means this problem might not be a problem anymore? What are the other differences between encoding/json and jsonpb? |
Differences I'm aware of:
|
Some of these things are solvable:
So what if we start by moving the jsonpb implementation to be closer to the encoding/json implementation. |
I agree that that's a nice goal in principle, and I've retitled the proposal accordingly. I'm not sure whether it's feasible. |
encoding/json
Yes this title is something I can get behind.
|
Yes please, this would solve so many problems that are common: people deserializing with |
Ok, so to sum up this discussion Step 1 would be:
I like this approach, because it gets us 90% there (you can use Step 2 would be to consider code-generating the
|
Note that |
@zombiezen True, but I think the protobuf JSON spec and the Go The
The
|
SGTM. Just wanted to make sure we thought about it. |
I just wanted to add a note: the json StructTag value of "-" isn't checked. |
@morphar Curious, how did you set the JSON struct tag value of "-" on a generated type field? If this is for a dynamic message type, you can implement JSONPBMarshaler/JSONPBUnmarshaler. See https://github.com/golang/protobuf/blob/master/jsonpb/jsonpb_test.go#L767. |
any progress on this? need help? |
Previously, the call to .addReflected(j.Message) was leading to the default Go json.Marshal output for the message struct (since pb messages do not themselves implement json.Marshaler). This meant the various jsonpb.Marshaler config controls were not respected - in particular, enum values were always printed as numbers instead of strings. This change alters the capitalization of ouput field names to the jsonbp camel-case style. The old output was governed by the "legacy" generated json struct tags. - golang/protobuf#189 - golang/protobuf#256
Previously, the call to .addReflected(j.Message) was leading to the default Go json.Marshal output for the message struct (since pb messages do not themselves implement json.Marshaler). This meant the various jsonpb.Marshaler config controls were not respected - in particular, enum values were always printed as numbers instead of strings. This change alters the capitalization of ouput field names to the jsonbp camel-case style. The old output was governed by the "legacy" generated json struct tags. - golang/protobuf#189 - golang/protobuf#256
In case anyone is interested, I implemented protoc-gen-go-jsonpb to generate MarshalJSON/UnmarshalJSON functions for messages. |
encoding/json
Would love
In this case, say we have a backend service that needs to serialise/deserialise only
By having |
Perhaps related, at least as far as decoding enums is concerned: #866 |
Whoops I missed this dup when I reported my issue (#926). My stab is similar to @tnarg above, I didn't see this thread and googling didn't bring anything up. We've now started using this and so far has been working great: https://github.com/mitchellh/protoc-gen-go-json It'd be great to have this sort of functionality built-in. |
Is this waiting on the refactor mentioned in #266 for Anything members of the community can help out with to move this particular set of issues through? Very much would like to see this land in the core pkg. |
Huh, this isn’t such a bad idea. Since we can override JSON marshaling/unmarshalling per message to call into |
Thanks @mitchellh, that package works perfectly! Would love to see this built in as well. |
Is there a status on this? I recently came across this issue when trying to wrap a protobuf generated struct inside another struct that contained other non protobuf generate structs. Now I can't simply use json.Unmarshal/Marshal because the protobuf related struct requires special handling related to the enum type fields. I'd be super happy to have these protobuf structs implement the MarshalJSON and UnmarshalJSON functions with some sane defaults. Please let me know if this is ready to be worked on. |
Thanks, this looks very promising.
James Grunewald
… On Dec 4, 2020, at 8:25 PM, Tamal Saha ***@***.***> wrote:
@jbgrunewald , use https://github.com/mitchellh/protoc-gen-go-json
—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub, or unsubscribe.
|
So what's going on now? It's 2024. |
https://github.com/mfridman/protoc-gen-go-json did the trick very well for me. If found this through the one linked by @tamalsaha , but that turned out to be a fork of @mfridman's work and had been archived in the meantime. The original one appears to be better maintained, and was able to handle optional fields in proto messages. So worth to check out. |
Per #183:
I think
json
usage is pervasive enough that we should revisit this decision. Message types whose JSON encoding diverges from the standardencoding/json
package should provideMarshalJSON
andUnmarshalJSON
methods. Then users could use the standard package without the need to explicitly interact withjsonpb
.Yes, it's possible that would add a few more dependencies for programs that don't strictly need them. To the extent that that's a problem, it's a problem that should be fixed in the compiler and linker: the marginal increase in build and link times due to the extra dependencies seems like it would be miniscule compared to the complexity of interacting with two separate and incompatible packages for JSON encoding (e.g. #248).
The text was updated successfully, but these errors were encountered: