permissions_basic_test.gno

13.21 Kb · 523 lines
  1package boards2
  2
  3import (
  4	"std"
  5	"testing"
  6
  7	"gno.land/p/nt/commondao"
  8	"gno.land/p/nt/uassert"
  9	"gno.land/p/nt/urequire"
 10)
 11
 12var _ Permissions = (*BasicPermissions)(nil)
 13
 14func TestBasicPermissionsWithPermission(t *testing.T) {
 15	cases := []struct {
 16		name       string
 17		user       std.Address
 18		permission Permission
 19		args       Args
 20		setup      func() *BasicPermissions
 21		err        string
 22		called     bool
 23	}{
 24		{
 25			name:       "ok",
 26			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
 27			permission: "bar",
 28			setup: func() *BasicPermissions {
 29				perms := NewBasicPermissions(commondao.New())
 30				perms.AddRole("foo", "bar")
 31				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "foo")
 32				return perms
 33			},
 34			called: true,
 35		},
 36		{
 37			name:       "ok with arguments",
 38			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
 39			permission: "bar",
 40			args:       Args{"a", "b"},
 41			setup: func() *BasicPermissions {
 42				perms := NewBasicPermissions(commondao.New())
 43				perms.AddRole("foo", "bar")
 44				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "foo")
 45				return perms
 46			},
 47			called: true,
 48		},
 49		{
 50			name:       "no permission",
 51			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
 52			permission: "bar",
 53			setup: func() *BasicPermissions {
 54				perms := NewBasicPermissions(commondao.New())
 55				perms.AddRole("foo", "bar")
 56				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5")
 57				return perms
 58			},
 59			err: "unauthorized",
 60		},
 61		{
 62			name:       "is not a DAO member",
 63			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
 64			permission: "bar",
 65			setup: func() *BasicPermissions {
 66				return NewBasicPermissions(commondao.New())
 67			},
 68			err: "unauthorized",
 69		},
 70	}
 71
 72	for _, tc := range cases {
 73		t.Run(tc.name, func(t *testing.T) {
 74			var (
 75				called bool
 76				args   Args
 77			)
 78
 79			perms := tc.setup()
 80			callback := func(_ realm, a Args) {
 81				args = a
 82				called = true
 83			}
 84
 85			testCaseFn := func() {
 86				perms.WithPermission(cross, tc.user, tc.permission, tc.args, callback)
 87			}
 88
 89			if tc.err != "" {
 90				urequire.AbortsWithMessage(t, tc.err, testCaseFn, "panic")
 91				return
 92			} else {
 93				urequire.NotPanics(t, testCaseFn, "no panic")
 94			}
 95
 96			urequire.Equal(t, tc.called, called, "callback called")
 97			urequire.Equal(t, len(tc.args), len(args), "args count")
 98			for i, a := range args {
 99				uassert.Equal(t, tc.args[i].(string), a.(string))
100			}
101		})
102	}
103}
104
105func TestBasicPermissionsGetUserRoles(t *testing.T) {
106	cases := []struct {
107		name  string
108		user  std.Address
109		roles []string
110		setup func() *BasicPermissions
111	}{
112		{
113			name:  "single role",
114			user:  "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
115			roles: []string{"admin"},
116			setup: func() *BasicPermissions {
117				perms := NewBasicPermissions(commondao.New())
118				perms.AddRole("admin", "x")
119				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "admin")
120				return perms
121			},
122		},
123		{
124			name:  "multiple roles",
125			user:  "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
126			roles: []string{"admin", "foo", "bar"},
127			setup: func() *BasicPermissions {
128				perms := NewBasicPermissions(commondao.New())
129				perms.AddRole("admin", "x")
130				perms.AddRole("foo", "x")
131				perms.AddRole("bar", "x")
132				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "admin", "foo", "bar")
133				return perms
134			},
135		},
136		{
137			name: "without roles",
138			user: "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
139			setup: func() *BasicPermissions {
140				perms := NewBasicPermissions(commondao.New())
141				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5")
142				return perms
143			},
144		},
145		{
146			name: "not a user",
147			user: "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
148			setup: func() *BasicPermissions {
149				return NewBasicPermissions(commondao.New())
150			},
151		},
152		{
153			name:  "multiple users",
154			user:  "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
155			roles: []string{"admin"},
156			setup: func() *BasicPermissions {
157				perms := NewBasicPermissions(commondao.New())
158				perms.AddRole("admin", "x")
159				perms.AddRole("bar", "x")
160				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "admin")
161				perms.SetUserRoles(cross, "g1w4ek2u33ta047h6lta047h6lta047h6ldvdwpn", "admin")
162				perms.SetUserRoles(cross, "g1w4ek2u3jta047h6lta047h6lta047h6l9huexc", "admin", "bar")
163				return perms
164			},
165		},
166	}
167
168	for _, tc := range cases {
169		t.Run(tc.name, func(t *testing.T) {
170			perms := tc.setup()
171			roles := perms.GetUserRoles(tc.user)
172
173			urequire.Equal(t, len(tc.roles), len(roles), "user role count")
174			for i, r := range roles {
175				uassert.Equal(t, tc.roles[i], string(r))
176			}
177		})
178	}
179}
180
181func TestBasicPermissionsHasRole(t *testing.T) {
182	cases := []struct {
183		name  string
184		user  std.Address
185		role  Role
186		setup func() *BasicPermissions
187		want  bool
188	}{
189		{
190			name: "ok",
191			user: "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
192			role: "admin",
193			setup: func() *BasicPermissions {
194				perms := NewBasicPermissions(commondao.New())
195				perms.AddRole("admin", "x")
196				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "admin")
197				return perms
198			},
199			want: true,
200		},
201		{
202			name: "ok with multiple roles",
203			user: "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
204			role: "foo",
205			setup: func() *BasicPermissions {
206				perms := NewBasicPermissions(commondao.New())
207				perms.AddRole("admin", "x")
208				perms.AddRole("foo", "x")
209				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "admin", "foo")
210				return perms
211			},
212			want: true,
213		},
214		{
215			name: "user without roles",
216			user: "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
217			setup: func() *BasicPermissions {
218				perms := NewBasicPermissions(commondao.New())
219				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5")
220				return perms
221			},
222		},
223		{
224			name: "has no role",
225			user: "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
226			role: "bar",
227			setup: func() *BasicPermissions {
228				perms := NewBasicPermissions(commondao.New())
229				perms.AddRole("foo", "x")
230				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "foo")
231				return perms
232			},
233		},
234	}
235
236	for _, tc := range cases {
237		t.Run(tc.name, func(t *testing.T) {
238			perms := tc.setup()
239			got := perms.HasRole(tc.user, tc.role)
240			uassert.Equal(t, got, tc.want)
241		})
242	}
243}
244
245func TestBasicPermissionsHasPermission(t *testing.T) {
246	cases := []struct {
247		name       string
248		user       std.Address
249		permission Permission
250		setup      func() *BasicPermissions
251		want       bool
252	}{
253		{
254			name:       "ok",
255			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
256			permission: "bar",
257			setup: func() *BasicPermissions {
258				perms := NewBasicPermissions(commondao.New())
259				perms.AddRole("foo", "bar")
260				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "foo")
261				return perms
262			},
263			want: true,
264		},
265		{
266			name:       "ok with multiple users",
267			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
268			permission: "bar",
269			setup: func() *BasicPermissions {
270				perms := NewBasicPermissions(commondao.New())
271				perms.AddRole("foo", "bar")
272				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "foo")
273				perms.SetUserRoles(cross, "g1w4ek2u33ta047h6lta047h6lta047h6ldvdwpn", "foo")
274				return perms
275			},
276			want: true,
277		},
278		{
279			name:       "ok with multiple roles",
280			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
281			permission: "other",
282			setup: func() *BasicPermissions {
283				perms := NewBasicPermissions(commondao.New())
284				perms.AddRole("foo", "bar")
285				perms.AddRole("baz", "other")
286				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "foo", "baz")
287				return perms
288			},
289			want: true,
290		},
291		{
292			name:       "no permission",
293			user:       "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
294			permission: "other",
295			setup: func() *BasicPermissions {
296				perms := NewBasicPermissions(commondao.New())
297				perms.AddRole("foo", "bar")
298				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "foo")
299				return perms
300			},
301		},
302	}
303
304	for _, tc := range cases {
305		t.Run(tc.name, func(t *testing.T) {
306			perms := tc.setup()
307			got := perms.HasPermission(tc.user, tc.permission)
308			uassert.Equal(t, got, tc.want)
309		})
310	}
311}
312
313func TestBasicPermissionsSetUserRoles(t *testing.T) {
314	cases := []struct {
315		name  string
316		user  std.Address
317		roles []Role
318		setup func() *BasicPermissions
319		err   string
320	}{
321		{
322			name:  "add user",
323			user:  std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
324			roles: []Role{"a"},
325			setup: func() *BasicPermissions {
326				perms := NewBasicPermissions(commondao.New())
327				perms.AddRole("a", "permission1")
328				return perms
329			},
330		},
331		{
332			name:  "add user with multiple roles",
333			user:  std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
334			roles: []Role{"a", "b"},
335			setup: func() *BasicPermissions {
336				perms := NewBasicPermissions(commondao.New())
337				perms.AddRole("a", "permission1")
338				perms.AddRole("b", "permission2")
339				return perms
340			},
341		},
342		{
343			name:  "add when other users exists",
344			user:  std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
345			roles: []Role{"a"},
346			setup: func() *BasicPermissions {
347				perms := NewBasicPermissions(commondao.New())
348				perms.AddRole("a", "permission1")
349				perms.SetUserRoles(cross, "g1w4ek2u33ta047h6lta047h6lta047h6ldvdwpn", "a")
350				perms.SetUserRoles(cross, "g1w4ek2u3jta047h6lta047h6lta047h6l9huexc")
351				return perms
352			},
353		},
354		{
355			name:  "update user roles",
356			user:  std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
357			roles: []Role{"a", "b"},
358			setup: func() *BasicPermissions {
359				perms := NewBasicPermissions(commondao.New())
360				perms.AddRole("a", "permission1")
361				perms.AddRole("b", "permission2")
362				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "a")
363				return perms
364			},
365		},
366		{
367			name:  "clear user roles",
368			user:  std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
369			roles: []Role{},
370			setup: func() *BasicPermissions {
371				perms := NewBasicPermissions(commondao.New())
372				perms.AddRole("a", "permission1")
373				perms.AddRole("b", "permission2")
374				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5", "a", "b")
375				return perms
376			},
377		},
378		{
379			name:  "set invalid role",
380			user:  std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
381			roles: []Role{"a", "foo"},
382			setup: func() *BasicPermissions {
383				perms := NewBasicPermissions(commondao.New())
384				perms.AddRole("a", "permission1")
385				return perms
386			},
387			err: "invalid role: foo",
388		},
389	}
390
391	for _, tc := range cases {
392		t.Run(tc.name, func(t *testing.T) {
393			perms := tc.setup()
394
395			err := perms.SetUserRoles(cross, tc.user, tc.roles...)
396
397			if tc.err != "" {
398				urequire.Error(t, err, "expected an error")
399				uassert.Equal(t, tc.err, err.Error())
400				return
401			} else {
402				urequire.NoError(t, err)
403			}
404
405			roles := perms.GetUserRoles(tc.user)
406			uassert.Equal(t, len(tc.roles), len(roles))
407			for i, r := range roles {
408				urequire.Equal(t, string(tc.roles[i]), string(r))
409			}
410		})
411	}
412}
413
414func TestBasicPermissionsRemoveUser(t *testing.T) {
415	cases := []struct {
416		name  string
417		user  std.Address
418		setup func() *BasicPermissions
419		want  bool
420	}{
421		{
422			name: "ok",
423			user: std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
424			setup: func() *BasicPermissions {
425				perms := NewBasicPermissions(commondao.New())
426				perms.SetUserRoles(cross, "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5")
427				return perms
428			},
429			want: true,
430		},
431		{
432			name: "user not found",
433			user: std.Address("g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5"),
434			setup: func() *BasicPermissions {
435				return NewBasicPermissions(commondao.New())
436			},
437		},
438	}
439
440	for _, tc := range cases {
441		t.Run(tc.name, func(t *testing.T) {
442			perms := tc.setup()
443			got := perms.RemoveUser(cross, tc.user)
444			uassert.Equal(t, tc.want, got)
445		})
446	}
447}
448
449func TestBasicPermissionsIterateUsers(t *testing.T) {
450	users := []User{
451		{
452			Address: "g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5",
453			Roles:   []Role{"foo"},
454		},
455		{
456			Address: "g1us8428u2a5satrlxzagqqa5m6vmuze025anjlj",
457			Roles:   []Role{"foo", "bar"},
458		},
459		{
460			Address: "g1vh7krmmzfua5xjmkatvmx09z37w34lsvd2mxa5",
461			Roles:   []Role{"bar"},
462		},
463	}
464
465	perms := NewBasicPermissions(commondao.New())
466	perms.AddRole("foo", "perm1")
467	perms.AddRole("bar", "perm2")
468	for _, u := range users {
469		perms.SetUserRoles(cross, u.Address, u.Roles...)
470	}
471
472	cases := []struct {
473		name               string
474		start, count, want int
475	}{
476		{
477			name:  "exceed users count",
478			count: 50,
479			want:  3,
480		},
481		{
482			name:  "exact users count",
483			count: 3,
484			want:  3,
485		},
486		{
487			name:  "two users",
488			start: 1,
489			count: 2,
490			want:  2,
491		},
492		{
493			name:  "one user",
494			start: 1,
495			count: 1,
496			want:  1,
497		},
498		{
499			name:  "no iteration",
500			start: 50,
501		},
502	}
503
504	for _, tc := range cases {
505		t.Run(tc.name, func(t *testing.T) {
506			var i int
507			perms.IterateUsers(0, len(users), func(u User) bool {
508				urequire.True(t, i < len(users), "expect iterator to respect number of users")
509				uassert.Equal(t, users[i].Address, u.Address)
510
511				urequire.Equal(t, len(users[i].Roles), len(u.Roles), "expect number of roles to match")
512				for j := range u.Roles {
513					uassert.Equal(t, string(users[i].Roles[j]), string(u.Roles[j]))
514				}
515
516				i++
517				return false
518			})
519
520			uassert.Equal(t, i, len(users), "expect iterator to iterate all users")
521		})
522	}
523}