1package identity
2
3import (
4 "encoding/json"
5 "testing"
6
7 "github.com/MichaelMure/git-bug/entity"
8 "github.com/MichaelMure/git-bug/repository"
9 "github.com/stretchr/testify/assert"
10)
11
12// Test the commit and load of an Identity with multiple versions
13func TestIdentityCommitLoad(t *testing.T) {
14 mockRepo := repository.NewMockRepoForTest()
15
16 // single version
17
18 identity := &Identity{
19 id: entity.UnsetId,
20 versions: []*Version{
21 {
22 name: "René Descartes",
23 email: "rene.descartes@example.com",
24 },
25 },
26 }
27
28 err := identity.Commit(mockRepo)
29
30 assert.Nil(t, err)
31 assert.NotEmpty(t, identity.id)
32
33 loaded, err := ReadLocal(mockRepo, identity.id)
34 assert.Nil(t, err)
35 commitsAreSet(t, loaded)
36 assert.Equal(t, identity, loaded)
37
38 // multiple version
39
40 identity = &Identity{
41 id: entity.UnsetId,
42 versions: []*Version{
43 {
44 time: 100,
45 name: "René Descartes",
46 email: "rene.descartes@example.com",
47 keys: []*Key{
48 {PubKey: "pubkeyA"},
49 },
50 },
51 {
52 time: 200,
53 name: "René Descartes",
54 email: "rene.descartes@example.com",
55 keys: []*Key{
56 {PubKey: "pubkeyB"},
57 },
58 },
59 {
60 time: 201,
61 name: "René Descartes",
62 email: "rene.descartes@example.com",
63 keys: []*Key{
64 {PubKey: "pubkeyC"},
65 },
66 },
67 },
68 }
69
70 err = identity.Commit(mockRepo)
71
72 assert.Nil(t, err)
73 assert.NotEmpty(t, identity.id)
74
75 loaded, err = ReadLocal(mockRepo, identity.id)
76 assert.Nil(t, err)
77 commitsAreSet(t, loaded)
78 assert.Equal(t, identity, loaded)
79
80 // add more version
81
82 identity.addVersionForTest(&Version{
83 time: 201,
84 name: "René Descartes",
85 email: "rene.descartes@example.com",
86 keys: []*Key{
87 {PubKey: "pubkeyD"},
88 },
89 })
90
91 identity.addVersionForTest(&Version{
92 time: 300,
93 name: "René Descartes",
94 email: "rene.descartes@example.com",
95 keys: []*Key{
96 {PubKey: "pubkeyE"},
97 },
98 })
99
100 err = identity.Commit(mockRepo)
101
102 assert.Nil(t, err)
103 assert.NotEmpty(t, identity.id)
104
105 loaded, err = ReadLocal(mockRepo, identity.id)
106 assert.Nil(t, err)
107 commitsAreSet(t, loaded)
108 assert.Equal(t, identity, loaded)
109}
110
111func TestIdentityMutate(t *testing.T) {
112 identity := NewIdentity("René Descartes", "rene.descartes@example.com")
113
114 assert.Len(t, identity.versions, 1)
115
116 identity.Mutate(func(orig Mutator) Mutator {
117 orig.Email = "rene@descartes.fr"
118 orig.Name = "René"
119 orig.Login = "rene"
120 return orig
121 })
122
123 assert.Len(t, identity.versions, 2)
124 assert.Equal(t, identity.Email(), "rene@descartes.fr")
125 assert.Equal(t, identity.Name(), "René")
126 assert.Equal(t, identity.Login(), "rene")
127}
128
129func commitsAreSet(t *testing.T, identity *Identity) {
130 for _, version := range identity.versions {
131 assert.NotEmpty(t, version.commitHash)
132 }
133}
134
135// Test that the correct crypto keys are returned for a given lamport time
136func TestIdentity_ValidKeysAtTime(t *testing.T) {
137 identity := Identity{
138 id: entity.UnsetId,
139 versions: []*Version{
140 {
141 time: 100,
142 name: "René Descartes",
143 email: "rene.descartes@example.com",
144 keys: []*Key{
145 {PubKey: "pubkeyA"},
146 },
147 },
148 {
149 time: 200,
150 name: "René Descartes",
151 email: "rene.descartes@example.com",
152 keys: []*Key{
153 {PubKey: "pubkeyB"},
154 },
155 },
156 {
157 time: 201,
158 name: "René Descartes",
159 email: "rene.descartes@example.com",
160 keys: []*Key{
161 {PubKey: "pubkeyC"},
162 },
163 },
164 {
165 time: 201,
166 name: "René Descartes",
167 email: "rene.descartes@example.com",
168 keys: []*Key{
169 {PubKey: "pubkeyD"},
170 },
171 },
172 {
173 time: 300,
174 name: "René Descartes",
175 email: "rene.descartes@example.com",
176 keys: []*Key{
177 {PubKey: "pubkeyE"},
178 },
179 },
180 },
181 }
182
183 assert.Nil(t, identity.ValidKeysAtTime(10))
184 assert.Equal(t, identity.ValidKeysAtTime(100), []*Key{{PubKey: "pubkeyA"}})
185 assert.Equal(t, identity.ValidKeysAtTime(140), []*Key{{PubKey: "pubkeyA"}})
186 assert.Equal(t, identity.ValidKeysAtTime(200), []*Key{{PubKey: "pubkeyB"}})
187 assert.Equal(t, identity.ValidKeysAtTime(201), []*Key{{PubKey: "pubkeyD"}})
188 assert.Equal(t, identity.ValidKeysAtTime(202), []*Key{{PubKey: "pubkeyD"}})
189 assert.Equal(t, identity.ValidKeysAtTime(300), []*Key{{PubKey: "pubkeyE"}})
190 assert.Equal(t, identity.ValidKeysAtTime(3000), []*Key{{PubKey: "pubkeyE"}})
191}
192
193// Test the immutable or mutable metadata search
194func TestMetadata(t *testing.T) {
195 mockRepo := repository.NewMockRepoForTest()
196
197 identity := NewIdentity("René Descartes", "rene.descartes@example.com")
198
199 identity.SetMetadata("key1", "value1")
200 assertHasKeyValue(t, identity.ImmutableMetadata(), "key1", "value1")
201 assertHasKeyValue(t, identity.MutableMetadata(), "key1", "value1")
202
203 err := identity.Commit(mockRepo)
204 assert.NoError(t, err)
205
206 assertHasKeyValue(t, identity.ImmutableMetadata(), "key1", "value1")
207 assertHasKeyValue(t, identity.MutableMetadata(), "key1", "value1")
208
209 // try override
210 identity.addVersionForTest(&Version{
211 name: "René Descartes",
212 email: "rene.descartes@example.com",
213 })
214
215 identity.SetMetadata("key1", "value2")
216 assertHasKeyValue(t, identity.ImmutableMetadata(), "key1", "value1")
217 assertHasKeyValue(t, identity.MutableMetadata(), "key1", "value2")
218
219 err = identity.Commit(mockRepo)
220 assert.NoError(t, err)
221
222 // reload
223 loaded, err := ReadLocal(mockRepo, identity.id)
224 assert.Nil(t, err)
225
226 assertHasKeyValue(t, loaded.ImmutableMetadata(), "key1", "value1")
227 assertHasKeyValue(t, loaded.MutableMetadata(), "key1", "value2")
228}
229
230func assertHasKeyValue(t *testing.T, metadata map[string]string, key, value string) {
231 val, ok := metadata[key]
232 assert.True(t, ok)
233 assert.Equal(t, val, value)
234}
235
236func TestJSON(t *testing.T) {
237 mockRepo := repository.NewMockRepoForTest()
238
239 identity := &Identity{
240 id: entity.UnsetId,
241 versions: []*Version{
242 {
243 name: "René Descartes",
244 email: "rene.descartes@example.com",
245 },
246 },
247 }
248
249 // commit to make sure we have an Id
250 err := identity.Commit(mockRepo)
251 assert.Nil(t, err)
252 assert.NotEmpty(t, identity.id)
253
254 // serialize
255 data, err := json.Marshal(identity)
256 assert.NoError(t, err)
257
258 // deserialize, got a IdentityStub with the same id
259 var i Interface
260 i, err = UnmarshalJSON(data)
261 assert.NoError(t, err)
262 assert.Equal(t, identity.id, i.Id())
263
264 // make sure we can load the identity properly
265 i, err = ReadLocal(mockRepo, i.Id())
266 assert.NoError(t, err)
267}