From 7b946aaf80f63fb5b7b27556078e17e57e9f4c71 Mon Sep 17 00:00:00 2001 From: Alvaro Tinoco Date: Tue, 19 Jul 2022 08:13:12 +0200 Subject: [PATCH 1/2] chore(deps): run go mod tidy --- v2/go.mod | 7 +++++-- v2/go.sum | 1 + 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/v2/go.mod b/v2/go.mod index 20dded0..3b33fe6 100644 --- a/v2/go.mod +++ b/v2/go.mod @@ -2,10 +2,13 @@ module github.com/elliotchance/orderedmap/v2 go 1.18 +require ( + github.com/stretchr/testify v1.7.1 + golang.org/x/exp v0.0.0-20220321173239-a90fa8a75705 +) + require ( github.com/davecgh/go-spew v1.1.0 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect - github.com/stretchr/testify v1.7.1 // indirect - golang.org/x/exp v0.0.0-20220321173239-a90fa8a75705 // indirect gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c // indirect ) diff --git a/v2/go.sum b/v2/go.sum index 23a78ea..26002b1 100644 --- a/v2/go.sum +++ b/v2/go.sum @@ -7,6 +7,7 @@ github.com/stretchr/testify v1.7.1 h1:5TQK59W5E3v0r2duFAb7P95B6hEeOyEnHRa8MjYSMT github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= golang.org/x/exp v0.0.0-20220321173239-a90fa8a75705 h1:ba9YlqfDGTTQ5aZ2fwOoQ1hf32QySyQkR6ODGDzHlnE= golang.org/x/exp v0.0.0-20220321173239-a90fa8a75705/go.mod h1:lgLbSvA5ygNOMpwM/9anMpWVlVJ7Z+cHWq/eFuinpGE= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= From a5fcd5c6e245eb910b5552c3663c72cc0c5dc845 Mon Sep 17 00:00:00 2001 From: Alvaro Tinoco Date: Tue, 19 Jul 2022 10:22:19 +0200 Subject: [PATCH 2/2] feature: json marshalling --- v2/orderedmap.go | 28 +++++++++++++++++++++++++++ v2/orderedmap_test.go | 45 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 73 insertions(+) diff --git a/v2/orderedmap.go b/v2/orderedmap.go index f5c2f64..9a94a64 100644 --- a/v2/orderedmap.go +++ b/v2/orderedmap.go @@ -1,7 +1,10 @@ package orderedmap import ( + "bytes" "container/list" + "encoding/json" + "golang.org/x/exp/constraints" ) @@ -152,3 +155,28 @@ func (m *OrderedMap[K, V]) Copy() *OrderedMap[K, V] { return m2 } + +// Implements JSON marshaling. +func (m *OrderedMap[string, V]) MarshalJSON() ([]byte, error) { + if m.Len() == 0 { + return []byte("{}"), nil + } + var buf bytes.Buffer + buf.WriteByte('{') + encoder := json.NewEncoder(&buf) + for el := m.Front(); el != nil; el = el.Next() { + // add key + if err := encoder.Encode(el.Key); err != nil { + return nil, err + } + buf.WriteByte(':') + // add value + if err := encoder.Encode(el.Value); err != nil { + return nil, err + } + buf.WriteByte(',') + } + buf.Truncate(buf.Len() - 1) + buf.WriteByte('}') + return buf.Bytes(), nil +} diff --git a/v2/orderedmap_test.go b/v2/orderedmap_test.go index 34f26b0..6bf893c 100644 --- a/v2/orderedmap_test.go +++ b/v2/orderedmap_test.go @@ -1,6 +1,7 @@ package orderedmap_test import ( + "encoding/json" "testing" "github.com/elliotchance/orderedmap/v2" @@ -249,3 +250,47 @@ func TestGetElement(t *testing.T) { assert.Nil(t, element) }) } + +func TestOrderedMapJSON(t *testing.T) { + t.Run("EmptyMap", func(t *testing.T) { + m := orderedmap.NewOrderedMap[int, string]() + json, err := json.Marshal(m) + + assert.NoError(t, err) + assert.Equal(t, `{}`, string(json)) + }) + + t.Run("InvalidJSON", func(t *testing.T) { + m := orderedmap.NewOrderedMap[int, any]() + m.Set(1, struct{ Foo string }{"bar"}) + + _, err := json.Marshal(m) + assert.Error(t, err) + }) + + t.Run("MarshalJSON", func(t *testing.T) { + m := orderedmap.NewOrderedMap[string, any]() + m.Set("string", "foo") + m.Set("number", 1337) + m.Set("slice", []string{"foo", "bar"}) + m.Set("map", map[string]string{"foo": "bar"}) + m.Set("bool", true) + m.Set("nil", nil) + m.Set("struct", struct { + Foo string `json:"foo_tag"` + }{"bar"}) + + m2 := orderedmap.NewOrderedMap[string, any]() + m2.Set("string", "foo") + m2.Set("number", 1337) + m2.Set("slice", []string{"foo", "bar"}) + + m.Set("orderedMap", m2) + + json, err := json.Marshal(m) + + assert.NoError(t, err) + assert.Equal(t, `{"string":"foo","number":1337,"slice":["foo","bar"],"map":{"foo":"bar"},"bool":true,"nil":null,"struct":{"foo_tag":"bar"},"orderedMap":{"string":"foo","number":1337,"slice":["foo","bar"]}}`, string(json)) + }) + +}