-
Notifications
You must be signed in to change notification settings - Fork 636
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
Serializer to get the raw json value of a key? #1058
Comments
Please, check out Json Elements: https://github.com/Kotlin/kotlinx.serialization/blob/master/docs/json.md#json-elements |
If I understood correctly, you want to save some part of JSON to a |
Yes, exactly. I want to defer parsing for parts of the document. JsonElement is not a good fit because it still parses and creates objects. So the cpu/memory benefits of lazy parsing are lost. How does kotlin.serialization handle ignores unknown keys when deserializing into an object? Are the keys skipped during or after parsing? (I'm wondering what the cpu/allocation overhead is in cases where keys are ultimately ignored) |
The unknown keys are skipped without parsing (tokenizing only). However, the skipped string is not saved anywhere, so it requires some additional amount of work to support such a feature |
The feature seems like a reasonable addition, tho it still has some open questions.
Could you please elaborate on your use-case here? Because "put all unknown keys in a separate String property with valid JSON string" and "Treat specifically marked property not as simple String, but as a valid JSON encoded in String" are completely different approaches.
I wonder if there exist benchmarks (or maybe you have a relevant story to add?) to ensure that the performance boost is significant here. Because even without allocations of JsonElement, parser still has to 1) parse the JSON and extract the relevant sub-object 2) ensure that the whole sub-object is a valid JSON. And the second part is probably the slowest in the whole JSON decoding process, so I'm really interested in knowing how big is the performance improvement here. |
Most of the users only use its stable methods and should not implement it directly, while we still want to have an opportunity to evolve it in the future, add new methods etc. E.g. the potential future addition could be 'decodeRawJson(): String' method for #1058
This is what I'm interested in and what is implemented by the other examples I provided. I have one specific key in my json that contains a huge json subtree, with thousands of objects and several layers of nesting. I don't want to these create thousands of objects per json parse because it leads to severe GC pressure on many Android devices. |
Most of the users only use its stable methods and should not implement it directly, while we still want to have an opportunity to evolve it in the future, add new methods etc. E.g. the potential future addition could be 'decodeRawJson(): String' method for #1058
Thanks for the clarification and your input! It's not something we are going to do right now (at least until 1.1.0 version), but thanks to your feedback, I've left the possibility to add this functionality in a backwards-compatible way both for custom serializers and regular JSON usages. Design idea: instead of using |
@qwwdfsad If this functionality were something I'd be interested in contributing, do you have any pointers on where to start? |
I'd like to add that there's a slightly different use case that I have, which is preventing me from switching to kotlinx.serialization. I have a situation where I would like to store the sub-object, as a JSON string, in a database, but I also want to deserialise it to examine its contents. Without RawJson, this means deserialising the whole JSON object, and then reserialising the sub-object for storage. Similarly, when serving the data again (potentially as part of a collection), I'd need to deserialise the sub-object before serialising the full object for output. I might be a bit naive, not having delved into the specifics of how this all works, but to me this seems to be a bit redundant. The string is already there as a substring of the original input, or will become a substring of the output. I've tried to achieve this through a custom serializer, a bit like this:
but I found that for large collections of data, this ended up slower than using Jackson with the JsonRawValue annotation. Is there a better way to achieve this? |
I'm following this guide to implement fallback for deserializing Enums. However, I would like to also log the raw value when it failed. Is there any way to get this from the |
Unfortunately, we do not support retrieving raw values yet. Also relevant: #1405 |
The server does return vulnerabilities which do not have a severity value in the dedicated property. The unspecified `databaseSpecific` property often times holds a primitive `severity` property with values such as `[HIGH, MEDIUM, LOW]`. Make use of these values as a fallback as these to provide more indication than a `null` value. Note: The data model of 'osv/client' currently uses subtypes of JsonElement to expose a couple of unspecified JSON objects as properties. Accessing these requires the client code to add 'kotlinx.serialization' as dependency which is not nice. A solution to that would be to use "raw" string values containing the JSON, which is unfortunately not yet possible but may become so in the future, see [1][2][3]. So, for now add 'kotlinx.serialization' as dependency to the advisor in order to access the property and leave a FIXME comment as reminder. [1] Kotlin/kotlinx.serialization#1298 [2] Kotlin/kotlinx.serialization#1405 [3] Kotlin/kotlinx.serialization#1058 Signed-off-by: Frank Viernau <[email protected]>
The server does return vulnerabilities which do not have a severity value in the dedicated property. The unspecified `databaseSpecific` property often times holds a primitive `severity` property with values such as `[HIGH, MEDIUM, LOW]`. Make use of these values as a fallback as these to provide more indication than a `null` value. Note: The data model of 'osv/client' currently uses subtypes of JsonElement to expose a couple of unspecified JSON objects as properties. Accessing these requires the client code to add 'kotlinx.serialization' as dependency which is not nice. A solution to that would be to use "raw" string values containing the JSON, which is unfortunately not yet possible but may become so in the future, see [1][2][3]. So, for now add 'kotlinx.serialization' as dependency to the advisor in order to access the property and leave a FIXME comment as reminder. [1] Kotlin/kotlinx.serialization#1298 [2] Kotlin/kotlinx.serialization#1405 [3] Kotlin/kotlinx.serialization#1058 Signed-off-by: Frank Viernau <[email protected]>
The server does return vulnerabilities which do not have a severity value in the dedicated property. The unspecified `databaseSpecific` property often times holds a primitive `severity` property with values such as `[HIGH, MEDIUM, LOW]`. Make use of these values as a fallback as these to provide more indication than a `null` value. Note: The data model of 'osv/client' currently uses subtypes of JsonElement to expose a couple of unspecified JSON objects as properties. Accessing these requires the client code to add 'kotlinx.serialization' as dependency which is not nice. A solution to that would be to use "raw" string values containing the JSON, which is unfortunately not yet possible but may become so in the future, see [1][2][3]. So, for now add 'kotlinx.serialization' as dependency to the advisor in order to access the property and leave a FIXME comment as reminder. [1] Kotlin/kotlinx.serialization#1298 [2] Kotlin/kotlinx.serialization#1405 [3] Kotlin/kotlinx.serialization#1058 Signed-off-by: Frank Viernau <[email protected]>
The server does return vulnerabilities which do not have a severity value in the dedicated property. The unspecified `databaseSpecific` property often times holds a primitive `severity` property with values such as `[HIGH, MEDIUM, LOW]`. Make use of these values as a fallback as these to provide more indication than a `null` value. Note: The data model of 'osv/client' currently uses subtypes of JsonElement to expose a couple of unspecified JSON objects as properties. Accessing these requires the client code to add 'kotlinx.serialization' as dependency which is not nice. A solution to that would be to use "raw" string values containing the JSON, which is unfortunately not yet possible but may become so in the future, see [1][2][3]. So, for now add 'kotlinx.serialization' as dependency to the advisor in order to access the property and leave a FIXME comment as reminder. [1] Kotlin/kotlinx.serialization#1298 [2] Kotlin/kotlinx.serialization#1405 [3] Kotlin/kotlinx.serialization#1058 Signed-off-by: Frank Viernau <[email protected]>
The server does return vulnerabilities which do not have a severity value in the dedicated property. The unspecified `databaseSpecific` property often times holds a primitive `severity` property with values such as `[HIGH, MEDIUM, LOW]`. Make use of these values as a fallback as these to provide more indication than a `null` value. Note: The data model of 'osv/client' currently uses subtypes of JsonElement to expose a couple of unspecified JSON objects as properties. Accessing these requires the client code to add 'kotlinx.serialization' as dependency which is not nice. A solution to that would be to use "raw" string values containing the JSON, which is unfortunately not yet possible but may become so in the future, see [1][2][3]. So, for now add 'kotlinx.serialization' as dependency to the advisor in order to access the property and leave a FIXME comment as reminder. [1] Kotlin/kotlinx.serialization#1298 [2] Kotlin/kotlinx.serialization#1405 [3] Kotlin/kotlinx.serialization#1058 Signed-off-by: Frank Viernau <[email protected]>
The server does return vulnerabilities which do not have a severity value in the dedicated property. The unspecified `databaseSpecific` property often times holds a primitive `severity` property with values such as `[HIGH, MEDIUM, LOW]`. Make use of these values as a fallback as these to provide more indication than a `null` value. Note: The data model of 'osv/client' currently uses subtypes of JsonElement to expose a couple of unspecified JSON objects as properties. Accessing these requires the client code to add 'kotlinx.serialization' as dependency which is not nice. A solution to that would be to use "raw" string values containing the JSON, which is unfortunately not yet possible but may become so in the future, see [1][2][3]. So, for now add 'kotlinx.serialization' as dependency to the advisor in order to access the property and leave a FIXME comment as reminder. [1] Kotlin/kotlinx.serialization#1298 [2] Kotlin/kotlinx.serialization#1405 [3] Kotlin/kotlinx.serialization#1058 Signed-off-by: Frank Viernau <[email protected]>
Currently we have any way to achieve it? The documentation said I must provide a correct descriptor. But in this case I don't know which descriptor is suitable. |
What is your use-case and why do you need this feature?
I am looking for a way to deserialize a specific field in my json into a raw byte array representing the value json sub-document.
Basically my json documents have large/complex json sub-trees that I would like to avoid parsing to save cpu/allocations. But I still need the value so I can re-create the original json if needed.
In golang, for example, this can be achieved with
json.RawMessage
: https://golang.org/pkg/encoding/json/#RawMessageIn gson, a type adapter can be used to regenerate json during parsing. This is not particularly cpu/gc efficient, but it works: google/gson#1368
In moshi, there is work being done to be able to skip over the value and consume it into a raw value field: square/moshi#675
Describe the solution you'd like
I'm not familiar enough with the kotlin.serialization APIs to know if there is already a way to do this, or if it can be implemented within a custom serializer. Any pointers would be appreciated!
The text was updated successfully, but these errors were encountered: