Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions Readme.org
Original file line number Diff line number Diff line change
Expand Up @@ -41,12 +41,12 @@ For more see [[./doc/other_usage.org][other usage scenarios]], and [[./doc/json_
Assuming your ~$GOBIN~ directory is somewhere in your ~$PATH~ it's as simple as:

#+begin_src sh
go install github.com/draxil/json2nd@latest
go install codeberg.org/draxil/json2nd@latest
#+end_src

** Github releases

There are builds of release points on github. Grab the relevent build from [[https://github.com/draxil/json2nd/releases][the github releases]] page, right now these just contain a binary and docs.
There are builds of release points on github (but soon codeberg). Grab the relevent build from [[https://github.com/draxil/json2nd/releases][the github releases]] page, right now these just contain a binary and docs.

* Plans / what about XYZ?

Expand Down
3 changes: 1 addition & 2 deletions filemode.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,10 @@ import (
"io"
"os"

"github.com/draxil/json2nd/internal/options"
"codeberg.org/draxil/json2nd/internal/options"
)

func filemode(files []string, out io.Writer, opts options.Set) error {

for _, name := range files {
f, err := os.Open(name)
if err != nil {
Expand Down
3 changes: 1 addition & 2 deletions filemode_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,11 @@ import (
"errors"
"testing"

"github.com/draxil/json2nd/internal/options"
"codeberg.org/draxil/json2nd/internal/options"
"github.com/stretchr/testify/assert"
)

func TestFileMode(t *testing.T) {

cases := []struct {
name string
files []string
Expand Down
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
module github.com/draxil/json2nd
module codeberg.org/draxil/json2nd

go 1.16

Expand Down
11 changes: 7 additions & 4 deletions internal/json/json_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,6 @@ func sread(s string) io.Reader {
}

func TestNext(t *testing.T) {

cases := []struct {
name string
reader io.Reader
Expand Down Expand Up @@ -129,7 +128,6 @@ func TestWriteToByteChunkNoDelims(t *testing.T) {
}

func TestCurrentWriteTo(t *testing.T) {

cases := []struct {
name string
in io.Reader
Expand Down Expand Up @@ -324,6 +322,13 @@ func TestCurrentWriteTo(t *testing.T) {
assert.Equal(t, io.EOF, e)
},
},
{
name: "github issue #3",
in: sread(`[{"value":"abc\\"}]`),
delims: false,
exp: `{"value":"abc\\"}`,
expClue: '[',
},
}

for _, tc := range cases {
Expand All @@ -349,7 +354,6 @@ func TestCurrentWriteTo(t *testing.T) {
}

func TestScanForKey(t *testing.T) {

cases := []struct {
name string
reader io.Reader
Expand Down Expand Up @@ -424,7 +428,6 @@ func TestScanForKeyValueSimple(t *testing.T) {
}

func TestSaneValueStart(t *testing.T) {

cases := []struct {
in byte
exp bool
Expand Down
15 changes: 11 additions & 4 deletions internal/json/scanner.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ type state struct {
last byte
lastNotWs byte
inStr bool
escape bool
key bool
open bool
seek struct {
Expand All @@ -23,7 +24,6 @@ type state struct {
}

func NewScanState(in byte) *state {

var inStr bool
if in == '"' {
inStr = true
Expand All @@ -45,7 +45,6 @@ func (s *state) seekFor(key string) {
}

func (s *state) scan(chunk []byte, idx, max int) (int, error) {

if s.closer == 0 {
return 0, ErrBadJSONValue{s.in}
}
Expand All @@ -66,9 +65,15 @@ func (s *state) scan(chunk []byte, idx, max int) (int, error) {
}
}

if b == '\\' && s.inStr && !s.escape {
s.escape = true
continue
}

// start or end of a string:
if b == '"' {
if s.inStr && s.last != '\\' {
if s.inStr && !s.escape {

// end of string.
s.inStr = false
if s.in == '{' && s.key {
Expand All @@ -78,6 +83,7 @@ func (s *state) scan(chunk []byte, idx, max int) (int, error) {
if s.seek.matching && s.seek.cursor == len(s.seek.keyName) {
s.seeking = false
s.seekFound = true
s.escape = false
return idx, nil
}
}
Expand All @@ -87,6 +93,7 @@ func (s *state) scan(chunk []byte, idx, max int) (int, error) {
if s.closer == '"' {
s.last = b
s.open = false
s.escape = false
return idx, nil
}
} else if !s.inStr {
Expand Down Expand Up @@ -122,14 +129,14 @@ func (s *state) scan(chunk []byte, idx, max int) (int, error) {
} else {
s.closerBalance--
}

} else if b == s.in {
s.closerBalance++
}
}

s.last = b
s.lastNotWs = b
s.escape = false
}

return max, nil
Expand Down
10 changes: 8 additions & 2 deletions internal/json/scanner_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,6 @@ func TestScanCloseBeforeEnd(t *testing.T) {
pos, _ := s.scan(buf, 0, len(buf))
assert.False(t, s.open)
assert.Equal(t, buf[pos], byte('}'), "cursor ends where we expect")

}

func TestScanStringDoesNotCloseObject(t *testing.T) {
Expand Down Expand Up @@ -97,6 +96,14 @@ func TestEscapedSubStringDoesNotClose(t *testing.T) {
assert.False(t, s.open)
}

func TestGithubNumberThree(t *testing.T) {
s := NewScanState('"')
buf := []byte(`\\"`)
_, err := s.scan(buf, 0, len(buf))
assert.NoError(t, err)
assert.False(t, s.open)
}

func TestScanOnChar(t *testing.T) {
s := NewScanState('Z')
buf := []byte(`x\"`)
Expand All @@ -117,7 +124,6 @@ func TestScanForSimple(t *testing.T) {
_, err = s.scan(buf, 0, len(buf))
assert.NoError(t, err)
assert.True(t, s.seekFound, "found")

}

func TestScanForSimpleWithNestedTrap(t *testing.T) {
Expand Down
3 changes: 1 addition & 2 deletions json2nd.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,12 @@ import (
"os"
"runtime/debug"

"github.com/draxil/json2nd/internal/options"
"codeberg.org/draxil/json2nd/internal/options"
)

var version = ""

func main() {

oh, err := options.New(os.Args[1:])
if err != nil {
if err == flag.ErrHelp {
Expand Down
10 changes: 3 additions & 7 deletions processor.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@ import (
"io"
"strings"

"github.com/draxil/json2nd/internal/json"
"github.com/draxil/json2nd/internal/options"
"codeberg.org/draxil/json2nd/internal/json"
"codeberg.org/draxil/json2nd/internal/options"
)

type processor struct {
Expand All @@ -25,7 +25,6 @@ type processor struct {
// TODO: path to value?

func (p processor) run() error {

if p.in == nil {
return errNilInput()
}
Expand Down Expand Up @@ -56,7 +55,6 @@ func (p processor) handlePath(scan *json.JSON) error {
}

func (p processor) handlePathNodes(nodes []string, scan *json.JSON) error {

// shouldn't be possible? But never say never.
if len(nodes) == 0 {
return fmt.Errorf("novel error 1: please report")
Expand Down Expand Up @@ -101,7 +99,6 @@ func (p processor) prepOut() (w io.Writer, finishOut func() error) {
}

func (p processor) handleArray(js *json.JSON) error {

// shift the cursor from the start of the array:
js.MoveOff()

Expand All @@ -119,7 +116,6 @@ func (p processor) handleArray(js *json.JSON) error {
}

n, err := js.WriteCurrentTo(out, true)

if err != nil {
return arrayJSONErr(err)
}
Expand Down Expand Up @@ -202,7 +198,6 @@ func (p processor) handleNonArray(j *json.JSON, clue byte, topLevel bool) error
}

func guessJSONType(clue byte) string {

switch clue {
case '{':
return "object"
Expand Down Expand Up @@ -247,6 +242,7 @@ func errBadPath(chunk string) error {
func errBlankPath() error {
return fmt.Errorf("bad blank path node, did you have a double dot?")
}

func errPathLeadToBadValue(start byte, path string) error {
t := guessJSONType(start)

Expand Down
7 changes: 2 additions & 5 deletions processor_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,12 @@ import (
"strings"
"testing"

"github.com/draxil/json2nd/internal/json"
"github.com/draxil/json2nd/internal/options"
"codeberg.org/draxil/json2nd/internal/json"
"codeberg.org/draxil/json2nd/internal/options"
"github.com/stretchr/testify/assert"
)

func TestProcessor(t *testing.T) {

cases := []struct {
name string
in io.Reader
Expand Down Expand Up @@ -422,7 +421,6 @@ func TestProcessor(t *testing.T) {
}

func TestGuessJsonType(t *testing.T) {

cases := []struct {
in byte
exp string
Expand All @@ -449,7 +447,6 @@ func TestGuessJsonType(t *testing.T) {
}

func TestErrPathLeadToBadValueMessage(t *testing.T) {

cases := []struct {
name string
clue byte
Expand Down