]> git.ipfire.org Git - thirdparty/gcc.git/blob - libgo/go/encoding/json/stream_test.go
libgo: Update to current sources.
[thirdparty/gcc.git] / libgo / go / encoding / json / stream_test.go
1 // Copyright 2010 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
4
5 package json
6
7 import (
8 "bytes"
9 "net"
10 "reflect"
11 "testing"
12 )
13
14 // Test values for the stream test.
15 // One of each JSON kind.
16 var streamTest = []interface{}{
17 0.1,
18 "hello",
19 nil,
20 true,
21 false,
22 []interface{}{"a", "b", "c"},
23 map[string]interface{}{"K": "Kelvin", "ß": "long s"},
24 3.14, // another value to make sure something can follow map
25 }
26
27 var streamEncoded = `0.1
28 "hello"
29 null
30 true
31 false
32 ["a","b","c"]
33 {"ß":"long s","K":"Kelvin"}
34 3.14
35 `
36
37 func TestEncoder(t *testing.T) {
38 for i := 0; i <= len(streamTest); i++ {
39 var buf bytes.Buffer
40 enc := NewEncoder(&buf)
41 for j, v := range streamTest[0:i] {
42 if err := enc.Encode(v); err != nil {
43 t.Fatalf("encode #%d: %v", j, err)
44 }
45 }
46 if have, want := buf.String(), nlines(streamEncoded, i); have != want {
47 t.Errorf("encoding %d items: mismatch", i)
48 diff(t, []byte(have), []byte(want))
49 break
50 }
51 }
52 }
53
54 func TestDecoder(t *testing.T) {
55 for i := 0; i <= len(streamTest); i++ {
56 // Use stream without newlines as input,
57 // just to stress the decoder even more.
58 // Our test input does not include back-to-back numbers.
59 // Otherwise stripping the newlines would
60 // merge two adjacent JSON values.
61 var buf bytes.Buffer
62 for _, c := range nlines(streamEncoded, i) {
63 if c != '\n' {
64 buf.WriteRune(c)
65 }
66 }
67 out := make([]interface{}, i)
68 dec := NewDecoder(&buf)
69 for j := range out {
70 if err := dec.Decode(&out[j]); err != nil {
71 t.Fatalf("decode #%d/%d: %v", j, i, err)
72 }
73 }
74 if !reflect.DeepEqual(out, streamTest[0:i]) {
75 t.Errorf("decoding %d items: mismatch", i)
76 for j := range out {
77 if !reflect.DeepEqual(out[j], streamTest[j]) {
78 t.Errorf("#%d: have %v want %v", j, out[j], streamTest[j])
79 }
80 }
81 break
82 }
83 }
84 }
85
86 func nlines(s string, n int) string {
87 if n <= 0 {
88 return ""
89 }
90 for i, c := range s {
91 if c == '\n' {
92 if n--; n == 0 {
93 return s[0 : i+1]
94 }
95 }
96 }
97 return s
98 }
99
100 func TestRawMessage(t *testing.T) {
101 // TODO(rsc): Should not need the * in *RawMessage
102 var data struct {
103 X float64
104 Id *RawMessage
105 Y float32
106 }
107 const raw = `["\u0056",null]`
108 const msg = `{"X":0.1,"Id":["\u0056",null],"Y":0.2}`
109 err := Unmarshal([]byte(msg), &data)
110 if err != nil {
111 t.Fatalf("Unmarshal: %v", err)
112 }
113 if string([]byte(*data.Id)) != raw {
114 t.Fatalf("Raw mismatch: have %#q want %#q", []byte(*data.Id), raw)
115 }
116 b, err := Marshal(&data)
117 if err != nil {
118 t.Fatalf("Marshal: %v", err)
119 }
120 if string(b) != msg {
121 t.Fatalf("Marshal: have %#q want %#q", b, msg)
122 }
123 }
124
125 func TestNullRawMessage(t *testing.T) {
126 // TODO(rsc): Should not need the * in *RawMessage
127 var data struct {
128 X float64
129 Id *RawMessage
130 Y float32
131 }
132 data.Id = new(RawMessage)
133 const msg = `{"X":0.1,"Id":null,"Y":0.2}`
134 err := Unmarshal([]byte(msg), &data)
135 if err != nil {
136 t.Fatalf("Unmarshal: %v", err)
137 }
138 if data.Id != nil {
139 t.Fatalf("Raw mismatch: have non-nil, want nil")
140 }
141 b, err := Marshal(&data)
142 if err != nil {
143 t.Fatalf("Marshal: %v", err)
144 }
145 if string(b) != msg {
146 t.Fatalf("Marshal: have %#q want %#q", b, msg)
147 }
148 }
149
150 var blockingTests = []string{
151 `{"x": 1}`,
152 `[1, 2, 3]`,
153 }
154
155 func TestBlocking(t *testing.T) {
156 for _, enc := range blockingTests {
157 r, w := net.Pipe()
158 go w.Write([]byte(enc))
159 var val interface{}
160
161 // If Decode reads beyond what w.Write writes above,
162 // it will block, and the test will deadlock.
163 if err := NewDecoder(r).Decode(&val); err != nil {
164 t.Errorf("decoding %s: %v", enc, err)
165 }
166 r.Close()
167 w.Close()
168 }
169 }