-
Notifications
You must be signed in to change notification settings - Fork 21
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
How to piecemeal stream write/encode a single json object? #23
Comments
If the |
Perhaps instead of being able to clone the Or perhaps there is a better way to accomplish this? A great example of the problem: Here is the library I have written, based off of |
I was attempting something similar and also found the jsontext api quite awkward to use. There's no efficient way to encode parts that are reused later, so you store a slice of |
@seankhliao, could you provide a concrete example of what you're trying to do? Thanks! |
I started with trying to convert my slog json handler to use jsontext. The current code is https://github.com/seankhliao/mono/blob/92d6c1a99aa152ab5312372b996128e2446bd3d2/jsonlog/jsonlog.go which works on appending to I started with a bottom up translation, with my first snag being this block. For the other cases I had replaced When I ignored the problem to think about the rest of the code, I realized I couldn't give the underlying writer |
At this level of optimization, I think manually crafting JSON with It's possible that we could add API to make An API that would probably help is a (as an aside, I suspect you probably also want an option that does a best-effort marshal where it emits valid JSON even if there is an error) |
BTW, is this a bug? Did you instead perhaps intend to do: case json.MarshalerV1:
b, _ := v.MarshalJSON()
h.buf, _ = append(h.buf, b) since |
I see, And yes, that's a bug. |
BTW, have you seen https://pkg.go.dev/github.com/orsinium-labs/jsony? It uses a structured representation that might be perfect for your use-case. The nature of the structured representation for JSON arrays and objects means that it doesn't have to waste effort maintaining push-down automaton to validate the JSON grammar. |
That's new to me, I'll take it for a spin |
I'm going to to close this as "won't fix". For extreme performance, nothing will faster than manually crafting JSON with a series of For more structured representation that still marshals quickly, then something like the There's a fundamental tradeoff between flexibility and performance. The |
I would like to piecemeal construct a single json object or array.
Ideally, I would like to be able to clone the Encoder at any point, so that I can have multiple versions of the partially finished json.
The main use case right now, is a slog.Handler that will be able to partially write the json as attributes are added, so that it doesn't need to fully marshal all of the attributes every time (similar to the built-in slog handlers, but using this json v2 library so I can take advantage of the new encoder options like SpaceAfterComma).
Example attempt:
Right now, I am encountering a few problems:
The values are being parsed twice.
In the example above, I am using the regular
json.Marshal(...)
to turn anany
into ajsontext.Value
, then writing that value to the encoder.When writing to the encoder, it automatically re-parses the []byte value to confirm it is valid json. This is unneeded and a performance penalty.
I don't see a way to clone the Encoder.
There isn't a method to create a new encoder with an existing buffer or any of the encoder's state set.
If I choose to replace the encoder with a simple buffer, I would lose out on all the encoder's guarantees and the jsontext.Options available, or have to re-implement them myself.
Is there an existing better way to do this?
If not, could we discuss what api additions or changes would be needed to allow this use case?
The text was updated successfully, but these errors were encountered: