blob: 5382ac535208dd2ff4db1b10a6b16799c345e504 [file] [log] [blame]
Rob Pikeaaa3a622010-03-20 22:32:34 -07001// Go support for Protocol Buffers - Google's data interchange format
2//
3// Copyright 2010 Google Inc. All rights reserved.
4// http://code.google.com/p/goprotobuf/
5//
6// Redistribution and use in source and binary forms, with or without
7// modification, are permitted provided that the following conditions are
8// met:
9//
10// * Redistributions of source code must retain the above copyright
11// notice, this list of conditions and the following disclaimer.
12// * Redistributions in binary form must reproduce the above
13// copyright notice, this list of conditions and the following disclaimer
14// in the documentation and/or other materials provided with the
15// distribution.
16// * Neither the name of Google Inc. nor the names of its
17// contributors may be used to endorse or promote products derived from
18// this software without specific prior written permission.
19//
20// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
24// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
25// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
26// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
30// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31
32package proto_test
33
34import (
35 . "goprotobuf.googlecode.com/hg/proto"
36 . "./testdata/_obj/test_proto"
37 "reflect"
38 "testing"
39)
40
41type UnmarshalTextTest struct {
42 in string
43 error string // if "", no error expected
44 out *MyMessage
45}
46
47var unMarshalTextTests = []UnmarshalTextTest{
48 // Basic
49 UnmarshalTextTest{
50 in: " count:42\n name:\"Dave\" ",
51 out: &MyMessage{
52 Count: Int32(42),
Rob Pike9caa5b92010-05-11 16:04:57 -070053 Name: String("Dave"),
Rob Pikeaaa3a622010-03-20 22:32:34 -070054 },
55 },
56
57 // Empty quoted string
58 UnmarshalTextTest{
59 in: `count:42 name:""`,
60 out: &MyMessage{
61 Count: Int32(42),
Rob Pike9caa5b92010-05-11 16:04:57 -070062 Name: String(""),
Rob Pikeaaa3a622010-03-20 22:32:34 -070063 },
64 },
65
66 // Quoted string concatenation
67 UnmarshalTextTest{
68 in: `count:42 name: "My name is "` + "\n" + `"elsewhere"`,
69 out: &MyMessage{
70 Count: Int32(42),
Rob Pike9caa5b92010-05-11 16:04:57 -070071 Name: String("My name is elsewhere"),
Rob Pikeaaa3a622010-03-20 22:32:34 -070072 },
73 },
74
75 // Bad quoted string
76 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -070077 in: `inner: < host: "\0" >` + "\n",
Rob Pikeaaa3a622010-03-20 22:32:34 -070078 error: `line 1.15: invalid quoted string "\0"`,
79 },
80
81 // Number too large for int64
82 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -070083 in: "count: 123456789012345678901",
Rob Pikeaaa3a622010-03-20 22:32:34 -070084 error: "line 1.7: invalid int32: 123456789012345678901",
85 },
86
87 // Number too large for int32
88 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -070089 in: "count: 1234567890123",
Rob Pikeaaa3a622010-03-20 22:32:34 -070090 error: "line 1.7: invalid int32: 1234567890123",
91 },
92
93 // Number too large for float32
94 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -070095 in: "others:< weight: 12345678901234567890123456789012345678901234567890 >",
Rob Pikeaaa3a622010-03-20 22:32:34 -070096 error: "line 1.17: invalid float32: 12345678901234567890123456789012345678901234567890",
97 },
98
99 // Number posing as a quoted string
100 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -0700101 in: `inner: < host: 12 >` + "\n",
Rob Pikeaaa3a622010-03-20 22:32:34 -0700102 error: `line 1.15: invalid string: 12`,
103 },
104
105 // Quoted string posing as int32
106 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -0700107 in: `count: "12"`,
Rob Pikeaaa3a622010-03-20 22:32:34 -0700108 error: `line 1.7: invalid int32: "12"`,
109 },
110
111 // Quoted string posing a float32
112 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -0700113 in: `others:< weight: "17.4" >`,
Rob Pikeaaa3a622010-03-20 22:32:34 -0700114 error: `line 1.17: invalid float32: "17.4"`,
115 },
116
117 // Enum
118 UnmarshalTextTest{
119 in: `count:42 bikeshed: BLUE`,
120 out: &MyMessage{
Rob Pike9caa5b92010-05-11 16:04:57 -0700121 Count: Int32(42),
Rob Pikeaaa3a622010-03-20 22:32:34 -0700122 Bikeshed: NewMyMessage_Color(MyMessage_BLUE),
123 },
124 },
125
126 // Repeated field
127 UnmarshalTextTest{
128 in: `count:42 pet: "horsey" pet:"bunny"`,
129 out: &MyMessage{
130 Count: Int32(42),
Rob Pike9caa5b92010-05-11 16:04:57 -0700131 Pet: []string{"horsey", "bunny"},
Rob Pikeaaa3a622010-03-20 22:32:34 -0700132 },
133 },
134
Rob Pikeaaf695a2010-06-22 15:51:21 -0700135 // Repeated message with/without colon and <>/{}
136 UnmarshalTextTest{
137 in: `count:42 others:{} others{} others:<> others:{}`,
138 out: &MyMessage{
139 Count: Int32(42),
140 Others: []*OtherMessage{
141 &OtherMessage{},
142 &OtherMessage{},
143 &OtherMessage{},
144 &OtherMessage{},
145 },
146 },
147 },
148
Rob Pikeaaa3a622010-03-20 22:32:34 -0700149 // Missing colon for inner message
150 UnmarshalTextTest{
151 in: `count:42 inner < host: "cauchy.syd" >`,
152 out: &MyMessage{
153 Count: Int32(42),
154 Inner: &InnerMessage{
155 Host: String("cauchy.syd"),
156 },
157 },
158 },
159
160 // Missing colon for string field
161 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -0700162 in: `name "Dave"`,
Rob Pikeaaa3a622010-03-20 22:32:34 -0700163 error: `line 1.5: expected ':', found "\"Dave\""`,
164 },
165
166 // Missing colon for int32 field
167 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -0700168 in: `count 42`,
Rob Pikeaaa3a622010-03-20 22:32:34 -0700169 error: `line 1.6: expected ':', found "42"`,
170 },
171
172 // Missing required field
173 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -0700174 in: ``,
Rob Pikeaaa3a622010-03-20 22:32:34 -0700175 error: `line 1.0: message test_proto.MyMessage missing required field "count"`,
176 },
177
178 // Repeated non-repeated field
179 UnmarshalTextTest{
Rob Pike9caa5b92010-05-11 16:04:57 -0700180 in: `name: "Rob" name: "Russ"`,
Rob Pikeaaa3a622010-03-20 22:32:34 -0700181 error: `line 1.12: non-repeated field "name" was repeated`,
182 },
183
184 // Big all-in-one
185 UnmarshalTextTest{
186 in: "count:42 # Meaning\n" +
187 `name:"Dave" ` +
188 `quote:"\"I didn't want to go.\"" ` +
189 `pet:"bunny" ` +
190 `pet:"kitty" ` +
191 `pet:"horsey" ` +
192 `inner:<` +
193 ` host:"footrest.syd" ` +
194 ` port:7001 ` +
195 ` connected:true ` +
196 `> ` +
197 `others:<` +
198 ` key:3735928559 ` +
199 ` value:"\x01A\a\f" ` +
200 `> ` +
201 `others:<` +
202 " weight:58.9 # Atomic weight of Co\n" +
203 ` inner:<` +
204 ` host:"lesha.mtv" ` +
205 ` port:8002 ` +
206 ` >` +
207 `>`,
208 out: &MyMessage{
209 Count: Int32(42),
Rob Pike9caa5b92010-05-11 16:04:57 -0700210 Name: String("Dave"),
Rob Pikeaaa3a622010-03-20 22:32:34 -0700211 Quote: String(`"I didn't want to go."`),
Rob Pike9caa5b92010-05-11 16:04:57 -0700212 Pet: []string{"bunny", "kitty", "horsey"},
Rob Pikeaaa3a622010-03-20 22:32:34 -0700213 Inner: &InnerMessage{
Rob Pike9caa5b92010-05-11 16:04:57 -0700214 Host: String("footrest.syd"),
215 Port: Int32(7001),
Rob Pikeaaa3a622010-03-20 22:32:34 -0700216 Connected: Bool(true),
217 },
218 Others: []*OtherMessage{
219 &OtherMessage{
Rob Pike9caa5b92010-05-11 16:04:57 -0700220 Key: Int64(3735928559),
Rob Pikeaaa3a622010-03-20 22:32:34 -0700221 Value: []byte{0x1, 'A', '\a', '\f'},
222 },
223 &OtherMessage{
224 Weight: Float32(58.9),
225 Inner: &InnerMessage{
226 Host: String("lesha.mtv"),
227 Port: Int32(8002),
228 },
229 },
230 },
231 },
232 },
233}
234
235func TestUnmarshalText(t *testing.T) {
236 for i, test := range unMarshalTextTests {
237 pb := new(MyMessage)
238 err := UnmarshalText(test.in, pb)
239 if test.error == "" {
240 // We don't expect failure.
241 if err != nil {
242 t.Errorf("Test %d: Unexpected error: %v", i, err)
243 } else if !reflect.DeepEqual(pb, test.out) {
244 t.Errorf("Test %d: Incorrect populated \n"+
245 "Have: %v\nWant: %v",
246 i, CompactTextString(pb), CompactTextString(test.out))
247 }
248 } else {
249 // We do expect failure.
250 if err == nil {
251 t.Errorf("Test %d: Didn't get expected error: %v", i, test.error)
252 } else if err.String() != test.error {
253 t.Errorf("Test %d: Incorrect error.\nHave: %v\nWant: %v",
254 i, err.String(), test.error)
255 }
256 }
257 }
258}