Marcono1234 / struson

Streaming JSON reader and writer written in Rust
https://crates.io/crates/struson
Apache License 2.0
64 stars 6 forks source link

[simple-api] Support `seek_to` at nested levels #49

Closed Marcono1234 closed 8 months ago

Marcono1234 commented 8 months ago

Problem solved by the enhancement

Currently the Simple API only supports seek_to at the top level. However, for example when trying to process all elements of an intermediate JSON array or object, this means you can only seek to that intermediate array or object and have to traverse the JSON data manually afterwards.

For example, consider this JSON path (where * represents all items):

first.second[*].third.fourth

Currently you can only use seek_to for the path first.second and then afterwards have to manually traverse third and fourth.

Enhancement description

seek_to should be available at all nesting levels. For non-top level values it should remember (based on the given JSON path) how many arrays and objects were opened, to then manually close them again after the value was consumed.

For the example above, this would then allow first seeking to first.second, and then for each array item seeking to third.fourth.

Alternatives / workarounds

The feature #48 might render this obsolete to some extend, but maybe there are still use cases where that feature cannot be used, e.g. when intermediate object member names are consumed in some way before traversing further down. Therefore supporting seek_to for nested levels still seems to be useful.

Marcono1234 commented 8 months ago

Instead of having seek_to at nested levels, would probably need a read_seeked(path: JsonPath, f: FnOnce(ValueReader)) to be able to detect if the caller consumed the value, or to implicitly skip it otherwise.

Could then consider removing the existing top-level seek_to method (because read_seeked will be available there as well), or keep it for now. If seek_to is kept, its documentation should mention that it is equivalent to read_seeked, except that it allows reading the seeked value without having to use a closure, but that on the other hand seek_to is only available for the top-level value.

Marcono1234 commented 8 months ago

The documentation for read_seeked should mention that: If the path matches a value, then f is called exactly once for reading that value. Otherwise if the path does not match, an error is returned and f is not called.

And similar to the other methods taking a Fn, if the value is not consumed explicitly it will be skipped implicitly.