Fast implementation of Git in pure Go
1package objectid_test
2
3import (
4 "bytes"
5 "strings"
6 "testing"
7
8 "codeberg.org/lindenii/furgit/objectid"
9)
10
11func TestParseAlgorithm(t *testing.T) {
12 t.Parallel()
13
14 algo, ok := objectid.ParseAlgorithm("sha1")
15 if !ok || algo != objectid.AlgorithmSHA1 {
16 t.Fatalf("ParseAlgorithm(sha1) = (%v,%v)", algo, ok)
17 }
18
19 algo, ok = objectid.ParseAlgorithm("sha256")
20 if !ok || algo != objectid.AlgorithmSHA256 {
21 t.Fatalf("ParseAlgorithm(sha256) = (%v,%v)", algo, ok)
22 }
23
24 if _, ok := objectid.ParseAlgorithm("md5"); ok {
25 t.Fatalf("ParseAlgorithm(md5) should fail")
26 }
27}
28
29func TestParseHexRoundtrip(t *testing.T) {
30 t.Parallel()
31
32 for _, algo := range objectid.SupportedAlgorithms() {
33 t.Run(algo.String(), func(t *testing.T) {
34 t.Parallel()
35
36 hex := strings.Repeat("01", algo.Size())
37
38 id, err := objectid.ParseHex(algo, hex)
39 if err != nil {
40 t.Fatalf("ParseHex failed: %v", err)
41 }
42
43 if got := id.String(); got != hex {
44 t.Fatalf("String() = %q, want %q", got, hex)
45 }
46
47 if got := id.Size(); got != algo.Size() {
48 t.Fatalf("Size() = %d, want %d", got, algo.Size())
49 }
50
51 raw := id.Bytes()
52 if len(raw) != algo.Size() {
53 t.Fatalf("Bytes len = %d, want %d", len(raw), algo.Size())
54 }
55
56 id2, err := objectid.FromBytes(algo, raw)
57 if err != nil {
58 t.Fatalf("FromBytes failed: %v", err)
59 }
60
61 if id2.String() != hex {
62 t.Fatalf("FromBytes roundtrip = %q, want %q", id2.String(), hex)
63 }
64 })
65 }
66}
67
68func TestParseHexErrors(t *testing.T) {
69 t.Parallel()
70
71 t.Run("unknown algo", func(t *testing.T) {
72 t.Parallel()
73
74 _, err := objectid.ParseHex(objectid.AlgorithmUnknown, "00")
75 if err == nil {
76 t.Fatalf("expected ParseHex error")
77 }
78 })
79
80 for _, algo := range objectid.SupportedAlgorithms() {
81 t.Run(algo.String(), func(t *testing.T) {
82 t.Parallel()
83
84 _, err := objectid.ParseHex(algo, strings.Repeat("0", algo.HexLen()-1))
85 if err == nil {
86 t.Fatalf("expected ParseHex odd-len error")
87 }
88
89 _, err = objectid.ParseHex(algo, strings.Repeat("0", algo.HexLen()-2))
90 if err == nil {
91 t.Fatalf("expected ParseHex wrong-len error")
92 }
93
94 _, err = objectid.ParseHex(algo, "z"+strings.Repeat("0", algo.HexLen()-1))
95 if err == nil {
96 t.Fatalf("expected ParseHex invalid-hex error")
97 }
98 })
99 }
100}
101
102func TestFromBytesErrors(t *testing.T) {
103 t.Parallel()
104
105 _, err := objectid.FromBytes(objectid.AlgorithmUnknown, []byte{1, 2})
106 if err == nil {
107 t.Fatalf("expected FromBytes unknown algo error")
108 }
109
110 for _, algo := range objectid.SupportedAlgorithms() {
111 _, err = objectid.FromBytes(algo, []byte{1, 2})
112 if err == nil {
113 t.Fatalf("expected FromBytes wrong size error")
114 }
115 }
116}
117
118func TestBytesReturnsCopy(t *testing.T) {
119 t.Parallel()
120
121 for _, algo := range objectid.SupportedAlgorithms() {
122 id, err := objectid.ParseHex(algo, strings.Repeat("01", algo.Size()))
123 if err != nil {
124 t.Fatalf("ParseHex failed: %v", err)
125 }
126
127 b1 := id.Bytes()
128
129 b2 := id.Bytes()
130 if !bytes.Equal(b1, b2) {
131 t.Fatalf("Bytes mismatch")
132 }
133
134 b1[0] ^= 0xff
135 if bytes.Equal(b1, b2) {
136 t.Fatalf("Bytes should return independent copies")
137 }
138 }
139}
140
141func TestRawBytesAliasesStorage(t *testing.T) {
142 t.Parallel()
143
144 for _, algo := range objectid.SupportedAlgorithms() {
145 id, err := objectid.ParseHex(algo, strings.Repeat("01", algo.Size()))
146 if err != nil {
147 t.Fatalf("ParseHex failed: %v", err)
148 }
149
150 b := id.RawBytes()
151 if len(b) != id.Size() {
152 t.Fatalf("RawBytes len = %d, want %d", len(b), id.Size())
153 }
154
155 if cap(b) != len(b) {
156 t.Fatalf("RawBytes cap = %d, want %d", cap(b), len(b))
157 }
158
159 orig := id.String()
160 b[0] ^= 0xff
161
162 if id.String() == orig {
163 t.Fatalf("RawBytes should alias object ID storage")
164 }
165 }
166}
167
168func TestAlgorithmSum(t *testing.T) {
169 t.Parallel()
170
171 id1 := objectid.AlgorithmSHA1.Sum([]byte("hello"))
172 if id1.Algorithm() != objectid.AlgorithmSHA1 || id1.Size() != objectid.AlgorithmSHA1.Size() {
173 t.Fatalf("sha1 sum produced invalid object id")
174 }
175
176 id2 := objectid.AlgorithmSHA256.Sum([]byte("hello"))
177 if id2.Algorithm() != objectid.AlgorithmSHA256 || id2.Size() != objectid.AlgorithmSHA256.Size() {
178 t.Fatalf("sha256 sum produced invalid object id")
179 }
180
181 if id1.String() == id2.String() {
182 t.Fatalf("sha1 and sha256 should differ")
183 }
184}