1
16
17 package spew_test
18
19 import (
20 "fmt"
21 "reflect"
22 "testing"
23
24 "github.com/davecgh/go-spew/spew"
25 )
26
27
28 type stringer string
29
30
31
32 func (s stringer) String() string {
33 return "stringer " + string(s)
34 }
35
36
37 type pstringer string
38
39
40
41 func (s *pstringer) String() string {
42 return "stringer " + string(*s)
43 }
44
45
46
47 type xref1 struct {
48 ps2 *xref2
49 }
50 type xref2 struct {
51 ps1 *xref1
52 }
53
54
55
56 type indirCir1 struct {
57 ps2 *indirCir2
58 }
59 type indirCir2 struct {
60 ps3 *indirCir3
61 }
62 type indirCir3 struct {
63 ps1 *indirCir1
64 }
65
66
67 type embed struct {
68 a string
69 }
70
71
72 type embedwrap struct {
73 *embed
74 e *embed
75 }
76
77
78
79 type panicer int
80
81 func (p panicer) String() string {
82 panic("test panic")
83 }
84
85
86 type customError int
87
88 func (e customError) Error() string {
89 return fmt.Sprintf("error: %d", int(e))
90 }
91
92
93
94 func stringizeWants(wants []string) string {
95 s := ""
96 for i, want := range wants {
97 if i > 0 {
98 s += fmt.Sprintf("want%d: %s", i+1, want)
99 } else {
100 s += "want: " + want
101 }
102 }
103 return s
104 }
105
106
107
108 func testFailed(result string, wants []string) bool {
109 for _, want := range wants {
110 if result == want {
111 return false
112 }
113 }
114 return true
115 }
116
117 type sortableStruct struct {
118 x int
119 }
120
121 func (ss sortableStruct) String() string {
122 return fmt.Sprintf("ss.%d", ss.x)
123 }
124
125 type unsortableStruct struct {
126 x int
127 }
128
129 type sortTestCase struct {
130 input []reflect.Value
131 expected []reflect.Value
132 }
133
134 func helpTestSortValues(tests []sortTestCase, cs *spew.ConfigState, t *testing.T) {
135 getInterfaces := func(values []reflect.Value) []interface{} {
136 interfaces := []interface{}{}
137 for _, v := range values {
138 interfaces = append(interfaces, v.Interface())
139 }
140 return interfaces
141 }
142
143 for _, test := range tests {
144 spew.SortValues(test.input, cs)
145
146
147
148
149 input := getInterfaces(test.input)
150 expected := getInterfaces(test.expected)
151 if !reflect.DeepEqual(input, expected) {
152 t.Errorf("Sort mismatch:\n %v != %v", input, expected)
153 }
154 }
155 }
156
157
158
159 func TestSortValues(t *testing.T) {
160 v := reflect.ValueOf
161
162 a := v("a")
163 b := v("b")
164 c := v("c")
165 embedA := v(embed{"a"})
166 embedB := v(embed{"b"})
167 embedC := v(embed{"c"})
168 tests := []sortTestCase{
169
170 {
171 []reflect.Value{},
172 []reflect.Value{},
173 },
174
175 {
176 []reflect.Value{v(false), v(true), v(false)},
177 []reflect.Value{v(false), v(false), v(true)},
178 },
179
180 {
181 []reflect.Value{v(2), v(1), v(3)},
182 []reflect.Value{v(1), v(2), v(3)},
183 },
184
185 {
186 []reflect.Value{v(uint8(2)), v(uint8(1)), v(uint8(3))},
187 []reflect.Value{v(uint8(1)), v(uint8(2)), v(uint8(3))},
188 },
189
190 {
191 []reflect.Value{v(2.0), v(1.0), v(3.0)},
192 []reflect.Value{v(1.0), v(2.0), v(3.0)},
193 },
194
195 {
196 []reflect.Value{b, a, c},
197 []reflect.Value{a, b, c},
198 },
199
200 {
201 []reflect.Value{v([3]int{3, 2, 1}), v([3]int{1, 3, 2}), v([3]int{1, 2, 3})},
202 []reflect.Value{v([3]int{1, 2, 3}), v([3]int{1, 3, 2}), v([3]int{3, 2, 1})},
203 },
204
205 {
206 []reflect.Value{v(uintptr(2)), v(uintptr(1)), v(uintptr(3))},
207 []reflect.Value{v(uintptr(1)), v(uintptr(2)), v(uintptr(3))},
208 },
209
210 {
211
212 []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})},
213 []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})},
214 },
215
216 {
217
218 []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})},
219 []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})},
220 },
221
222 {
223 []reflect.Value{embedB, embedA, embedC},
224 []reflect.Value{embedB, embedA, embedC},
225 },
226 }
227 cs := spew.ConfigState{DisableMethods: true, SpewKeys: false}
228 helpTestSortValues(tests, &cs, t)
229 }
230
231
232
233 func TestSortValuesWithMethods(t *testing.T) {
234 v := reflect.ValueOf
235
236 a := v("a")
237 b := v("b")
238 c := v("c")
239 tests := []sortTestCase{
240
241 {
242 []reflect.Value{v(2), v(1), v(3)},
243 []reflect.Value{v(1), v(2), v(3)},
244 },
245
246 {
247 []reflect.Value{b, a, c},
248 []reflect.Value{a, b, c},
249 },
250
251 {
252 []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})},
253 []reflect.Value{v(sortableStruct{1}), v(sortableStruct{2}), v(sortableStruct{3})},
254 },
255
256 {
257
258 []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})},
259 []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})},
260 },
261 }
262 cs := spew.ConfigState{DisableMethods: false, SpewKeys: false}
263 helpTestSortValues(tests, &cs, t)
264 }
265
266
267
268 func TestSortValuesWithSpew(t *testing.T) {
269 v := reflect.ValueOf
270
271 a := v("a")
272 b := v("b")
273 c := v("c")
274 tests := []sortTestCase{
275
276 {
277 []reflect.Value{v(2), v(1), v(3)},
278 []reflect.Value{v(1), v(2), v(3)},
279 },
280
281 {
282 []reflect.Value{b, a, c},
283 []reflect.Value{a, b, c},
284 },
285
286 {
287 []reflect.Value{v(sortableStruct{2}), v(sortableStruct{1}), v(sortableStruct{3})},
288 []reflect.Value{v(sortableStruct{1}), v(sortableStruct{2}), v(sortableStruct{3})},
289 },
290
291 {
292 []reflect.Value{v(unsortableStruct{2}), v(unsortableStruct{1}), v(unsortableStruct{3})},
293 []reflect.Value{v(unsortableStruct{1}), v(unsortableStruct{2}), v(unsortableStruct{3})},
294 },
295 }
296 cs := spew.ConfigState{DisableMethods: true, SpewKeys: true}
297 helpTestSortValues(tests, &cs, t)
298 }
299
View as plain text