1package fsnoder
2
3import (
4	"github.com/go-git/go-git/v5/utils/merkletrie/noder"
5
6	. "gopkg.in/check.v1"
7)
8
9type FSNoderSuite struct{}
10
11var _ = Suite(&FSNoderSuite{})
12
13func check(c *C, input string, expected *dir) {
14	obtained, err := New(input)
15	c.Assert(err, IsNil, Commentf("input = %s", input))
16
17	comment := Commentf("\n   input = %s\n"+
18		"expected = %s\nobtained = %s",
19		input, expected, obtained)
20	c.Assert(obtained.Hash(), DeepEquals, expected.Hash(), comment)
21}
22
23func (s *FSNoderSuite) TestNoDataFails(c *C) {
24	_, err := New("")
25	c.Assert(err, Not(IsNil))
26
27	_, err = New(" 	") // SPC + TAB
28	c.Assert(err, Not(IsNil))
29}
30
31func (s *FSNoderSuite) TestUnnamedRootFailsIfNotRoot(c *C) {
32	_, err := decodeDir([]byte("()"), false)
33	c.Assert(err, Not(IsNil))
34}
35
36func (s *FSNoderSuite) TestUnnamedInnerFails(c *C) {
37	_, err := New("(())")
38	c.Assert(err, Not(IsNil))
39	_, err = New("((a<>))")
40	c.Assert(err, Not(IsNil))
41}
42
43func (s *FSNoderSuite) TestMalformedFile(c *C) {
44	_, err := New("(4<>)")
45	c.Assert(err, Not(IsNil))
46	_, err = New("(4<1>)")
47	c.Assert(err, Not(IsNil))
48	_, err = New("(4?1>)")
49	c.Assert(err, Not(IsNil))
50	_, err = New("(4<a>)")
51	c.Assert(err, Not(IsNil))
52	_, err = New("(4<a?)")
53	c.Assert(err, Not(IsNil))
54
55	_, err = decodeFile([]byte("a?1>"))
56	c.Assert(err, Not(IsNil))
57	_, err = decodeFile([]byte("a<a>"))
58	c.Assert(err, Not(IsNil))
59	_, err = decodeFile([]byte("a<1?"))
60	c.Assert(err, Not(IsNil))
61
62	_, err = decodeFile([]byte("a?>"))
63	c.Assert(err, Not(IsNil))
64	_, err = decodeFile([]byte("1<>"))
65	c.Assert(err, Not(IsNil))
66	_, err = decodeFile([]byte("a<?"))
67	c.Assert(err, Not(IsNil))
68}
69
70func (s *FSNoderSuite) TestMalformedRootFails(c *C) {
71	_, err := New(")")
72	c.Assert(err, Not(IsNil))
73	_, err = New("(")
74	c.Assert(err, Not(IsNil))
75	_, err = New("(a<>")
76	c.Assert(err, Not(IsNil))
77	_, err = New("a<>")
78	c.Assert(err, Not(IsNil))
79}
80
81func (s *FSNoderSuite) TestUnnamedEmptyRoot(c *C) {
82	input := "()"
83
84	expected, err := newDir("", nil)
85	c.Assert(err, IsNil)
86
87	check(c, input, expected)
88}
89
90func (s *FSNoderSuite) TestNamedEmptyRoot(c *C) {
91	input := "a()"
92
93	expected, err := newDir("a", nil)
94	c.Assert(err, IsNil)
95
96	check(c, input, expected)
97}
98
99func (s *FSNoderSuite) TestEmptyFile(c *C) {
100	input := "(a<>)"
101
102	a1, err := newFile("a", "")
103	c.Assert(err, IsNil)
104	expected, err := newDir("", []noder.Noder{a1})
105	c.Assert(err, IsNil)
106
107	check(c, input, expected)
108}
109
110func (s *FSNoderSuite) TestNonEmptyFile(c *C) {
111	input := "(a<1>)"
112
113	a1, err := newFile("a", "1")
114	c.Assert(err, IsNil)
115	expected, err := newDir("", []noder.Noder{a1})
116	c.Assert(err, IsNil)
117
118	check(c, input, expected)
119}
120
121func (s *FSNoderSuite) TestTwoFilesSameContents(c *C) {
122	input := "(b<1> a<1>)"
123
124	a1, err := newFile("a", "1")
125	c.Assert(err, IsNil)
126	b1, err := newFile("b", "1")
127	c.Assert(err, IsNil)
128	expected, err := newDir("", []noder.Noder{a1, b1})
129	c.Assert(err, IsNil)
130
131	check(c, input, expected)
132}
133
134func (s *FSNoderSuite) TestTwoFilesDifferentContents(c *C) {
135	input := "(b<2> a<1>)"
136
137	a1, err := newFile("a", "1")
138	c.Assert(err, IsNil)
139	b2, err := newFile("b", "2")
140	c.Assert(err, IsNil)
141	expected, err := newDir("", []noder.Noder{a1, b2})
142	c.Assert(err, IsNil)
143
144	check(c, input, expected)
145}
146
147func (s *FSNoderSuite) TestManyFiles(c *C) {
148	input := "(e<1> b<2> a<1> c<1> d<3> f<4>)"
149
150	a1, err := newFile("a", "1")
151	c.Assert(err, IsNil)
152	b2, err := newFile("b", "2")
153	c.Assert(err, IsNil)
154	c1, err := newFile("c", "1")
155	c.Assert(err, IsNil)
156	d3, err := newFile("d", "3")
157	c.Assert(err, IsNil)
158	e1, err := newFile("e", "1")
159	c.Assert(err, IsNil)
160	f4, err := newFile("f", "4")
161	c.Assert(err, IsNil)
162	expected, err := newDir("", []noder.Noder{e1, b2, a1, c1, d3, f4})
163	c.Assert(err, IsNil)
164
165	check(c, input, expected)
166}
167
168func (s *FSNoderSuite) TestEmptyDir(c *C) {
169	input := "(A())"
170
171	A, err := newDir("A", nil)
172	c.Assert(err, IsNil)
173	expected, err := newDir("", []noder.Noder{A})
174	c.Assert(err, IsNil)
175
176	check(c, input, expected)
177}
178
179func (s *FSNoderSuite) TestDirWithEmptyFile(c *C) {
180	input := "(A(a<>))"
181
182	a, err := newFile("a", "")
183	c.Assert(err, IsNil)
184	A, err := newDir("A", []noder.Noder{a})
185	c.Assert(err, IsNil)
186	expected, err := newDir("", []noder.Noder{A})
187	c.Assert(err, IsNil)
188
189	check(c, input, expected)
190}
191
192func (s *FSNoderSuite) TestDirWithEmptyFileSameName(c *C) {
193	input := "(A(A<>))"
194
195	f, err := newFile("A", "")
196	c.Assert(err, IsNil)
197	A, err := newDir("A", []noder.Noder{f})
198	c.Assert(err, IsNil)
199	expected, err := newDir("", []noder.Noder{A})
200	c.Assert(err, IsNil)
201
202	check(c, input, expected)
203}
204
205func (s *FSNoderSuite) TestDirWithFileLongContents(c *C) {
206	input := "(A(a<12>))"
207
208	a1, err := newFile("a", "12")
209	c.Assert(err, IsNil)
210	A, err := newDir("A", []noder.Noder{a1})
211	c.Assert(err, IsNil)
212	expected, err := newDir("", []noder.Noder{A})
213	c.Assert(err, IsNil)
214
215	check(c, input, expected)
216}
217
218func (s *FSNoderSuite) TestDirWithFileLongName(c *C) {
219	input := "(A(abc<12>))"
220
221	a1, err := newFile("abc", "12")
222	c.Assert(err, IsNil)
223	A, err := newDir("A", []noder.Noder{a1})
224	c.Assert(err, IsNil)
225	expected, err := newDir("", []noder.Noder{A})
226	c.Assert(err, IsNil)
227
228	check(c, input, expected)
229}
230
231func (s *FSNoderSuite) TestDirWithFile(c *C) {
232	input := "(A(a<1>))"
233
234	a1, err := newFile("a", "1")
235	c.Assert(err, IsNil)
236	A, err := newDir("A", []noder.Noder{a1})
237	c.Assert(err, IsNil)
238	expected, err := newDir("", []noder.Noder{A})
239	c.Assert(err, IsNil)
240
241	check(c, input, expected)
242}
243
244func (s *FSNoderSuite) TestDirWithEmptyDirSameName(c *C) {
245	input := "(A(A()))"
246
247	A2, err := newDir("A", nil)
248	c.Assert(err, IsNil)
249	A1, err := newDir("A", []noder.Noder{A2})
250	c.Assert(err, IsNil)
251	expected, err := newDir("", []noder.Noder{A1})
252	c.Assert(err, IsNil)
253
254	check(c, input, expected)
255}
256
257func (s *FSNoderSuite) TestDirWithEmptyDir(c *C) {
258	input := "(A(B()))"
259
260	B, err := newDir("B", nil)
261	c.Assert(err, IsNil)
262	A, err := newDir("A", []noder.Noder{B})
263	c.Assert(err, IsNil)
264	expected, err := newDir("", []noder.Noder{A})
265	c.Assert(err, IsNil)
266
267	check(c, input, expected)
268}
269
270func (s *FSNoderSuite) TestDirWithTwoFiles(c *C) {
271	input := "(A(a<1> b<2>))"
272
273	a1, err := newFile("a", "1")
274	c.Assert(err, IsNil)
275	b2, err := newFile("b", "2")
276	c.Assert(err, IsNil)
277	A, err := newDir("A", []noder.Noder{b2, a1})
278	c.Assert(err, IsNil)
279	expected, err := newDir("", []noder.Noder{A})
280	c.Assert(err, IsNil)
281
282	check(c, input, expected)
283}
284
285func (s *FSNoderSuite) TestCrazy(c *C) {
286	//           ""
287	//            |
288	//   -------------------------
289	//   |    |      |      |    |
290	//  a1    B     c1     d2    E
291	//        |                  |
292	//   -------------           E
293	//   |   |   |   |           |
294	//   A   B   X   c1          E
295	//           |               |
296	//          a1               e1
297	input := "(d<2> b(c<1> b() a() x(a<1>)) a<1> c<1> e(e(e(e<1>))))"
298
299	e1, err := newFile("e", "1")
300	c.Assert(err, IsNil)
301	E, err := newDir("e", []noder.Noder{e1})
302	c.Assert(err, IsNil)
303	E, err = newDir("e", []noder.Noder{E})
304	c.Assert(err, IsNil)
305	E, err = newDir("e", []noder.Noder{E})
306	c.Assert(err, IsNil)
307
308	A, err := newDir("a", nil)
309	c.Assert(err, IsNil)
310	B, err := newDir("b", nil)
311	c.Assert(err, IsNil)
312	a1, err := newFile("a", "1")
313	c.Assert(err, IsNil)
314	X, err := newDir("x", []noder.Noder{a1})
315	c.Assert(err, IsNil)
316	c1, err := newFile("c", "1")
317	c.Assert(err, IsNil)
318	B, err = newDir("b", []noder.Noder{c1, B, X, A})
319	c.Assert(err, IsNil)
320
321	a1, err = newFile("a", "1")
322	c.Assert(err, IsNil)
323	c1, err = newFile("c", "1")
324	c.Assert(err, IsNil)
325	d2, err := newFile("d", "2")
326	c.Assert(err, IsNil)
327
328	expected, err := newDir("", []noder.Noder{a1, d2, E, B, c1})
329	c.Assert(err, IsNil)
330
331	check(c, input, expected)
332}
333
334func (s *FSNoderSuite) TestHashEqual(c *C) {
335	input1 := "(A(a<1> b<2>))"
336	input2 := "(A(a<1> b<2>))"
337	input3 := "(A(a<> b<2>))"
338
339	t1, err := New(input1)
340	c.Assert(err, IsNil)
341	t2, err := New(input2)
342	c.Assert(err, IsNil)
343	t3, err := New(input3)
344	c.Assert(err, IsNil)
345
346	c.Assert(HashEqual(t1, t2), Equals, true)
347	c.Assert(HashEqual(t2, t1), Equals, true)
348
349	c.Assert(HashEqual(t2, t3), Equals, false)
350	c.Assert(HashEqual(t3, t2), Equals, false)
351
352	c.Assert(HashEqual(t3, t1), Equals, false)
353	c.Assert(HashEqual(t1, t3), Equals, false)
354}
355