Skip to content

Commit

Permalink
add option to not parse beyond end of structure (ipld#435)
Browse files Browse the repository at this point in the history
  • Loading branch information
petar committed Jun 9, 2022
1 parent c88f0b4 commit 120991f
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 0 deletions.
42 changes: 42 additions & 0 deletions codec/dagjson/nongreedy_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
package dagjson

import (
"bytes"
"testing"

"github.com/ipld/go-ipld-prime/datamodel"
"github.com/ipld/go-ipld-prime/node/basicnode"
)

func TestNonGreedy(t *testing.T) {
buf := bytes.NewBufferString(`{"a": 1}{"b": 2}`)
opts := DecodeOptions{
ParseLinks: false,
ParseBytes: false,
DontParseBeyondEnd: true,
}
nb1 := basicnode.Prototype.Map.NewBuilder()
err := opts.Decode(nb1, buf)
if err != nil {
t.Fatalf("first decode (%v)", err)
}
n1 := nb1.Build()
if n1.Kind() != datamodel.Kind_Map {
t.Errorf("expecting a map")
}
if _, err := n1.LookupByString("a"); err != nil {
t.Fatalf("missing fist key")
}
nb2 := basicnode.Prototype.Map.NewBuilder()
err = opts.Decode(nb2, buf)
if err != nil {
t.Fatalf("second decode (%v)", err)
}
n2 := nb2.Build()
if n2.Kind() != datamodel.Kind_Map {
t.Errorf("expecting a map")
}
if _, err := n2.LookupByString("b"); err != nil {
t.Fatalf("missing second key")
}
}
10 changes: 10 additions & 0 deletions codec/dagjson/unmarshal.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,13 @@ type DecodeOptions struct {
// If true, parse DAG-JSON `{"/":{"bytes":"base64 bytes..."}}` as a Bytes kind
// node rather than nested plain maps
ParseBytes bool

// If true, the decoder stops reading from the stream at the end of the JSON structure.
// i.e. it does not slurp remaining whitespaces and EOF.
// As per standard IPLD behavior, the parser considers the entire block to be
// part of the JSON structure and will error if there is extraneous
// non-whitespace data.
DontParseBeyondEnd bool
}

// Decode deserializes data from the given io.Reader and feeds it into the given datamodel.NodeAssembler.
Expand All @@ -43,6 +50,9 @@ func (cfg DecodeOptions) Decode(na datamodel.NodeAssembler, r io.Reader) error {
if err != nil {
return err
}
if cfg.DontParseBeyondEnd {
return nil
}
// Slurp any remaining whitespace.
// This behavior may be due for review.
// (This is relevant if our reader is tee'ing bytes to a hasher, and
Expand Down

0 comments on commit 120991f

Please sign in to comment.