Something went wrong. Try again.
This repository has no description
Something went wrong. Try again.
8.9 kB · 246 lines
Go
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247package moderation
import ( "context" "fmt" "testing" "time"
glex "github.com/streamplace/glex/runtime" "github.com/stretchr/testify/require" "stream.place/streamplace/pkg/appbsky" "stream.place/streamplace/pkg/placestream")
func TestPermissionChecker_CheckPermission_StreamerSelfModeration(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
streamerDID := "did:plc:streamer123"
err := pc.CheckPermission(context.Background(), streamerDID, streamerDID, "createBlock") require.NoError(t, err, "streamer should have permission for self-moderation")
err = pc.CheckPermission(context.Background(), streamerDID, streamerDID, "createGate") require.NoError(t, err, "streamer should have permission for self-moderation")
err = pc.CheckPermission(context.Background(), streamerDID, streamerDID, "updateLivestream") require.NoError(t, err, "streamer should have permission for self-moderation")}
func TestPermissionChecker_CheckPermission_WithCorrectPermission(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
mod.addPermissionView(streamerDID, moderatorDID, []string{"ban", "hide"}, nil)
err := pc.CheckPermission(ctx, moderatorDID, streamerDID, "createBlock") require.NoError(t, err, "moderator with 'ban' permission should be able to createBlock")
err = pc.CheckPermission(ctx, moderatorDID, streamerDID, "createGate") require.NoError(t, err, "moderator with 'hide' permission should be able to createGate")}
func TestPermissionChecker_CheckPermission_WithWrongPermission(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
mod.addPermissionView(streamerDID, moderatorDID, []string{"hide"}, nil)
err := pc.CheckPermission(ctx, moderatorDID, streamerDID, "createBlock") require.Error(t, err, "moderator with only 'hide' permission should not be able to createBlock") require.Contains(t, err.Error(), "does not have permission 'ban'")}
func TestPermissionChecker_CheckPermission_WithoutAnyPermission(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
err := pc.CheckPermission(ctx, moderatorDID, streamerDID, "createBlock") require.Error(t, err, "moderator without any delegation should be denied") require.Contains(t, err.Error(), "does not have permission")}
func TestPermissionChecker_CheckPermission_UnknownAction(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
streamerDID := "did:plc:streamer123"
err := pc.CheckPermission(context.Background(), streamerDID, streamerDID, "unknownAction") require.Error(t, err) require.Contains(t, err.Error(), "unknown action")}
func TestPermissionChecker_HasPermission(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
mod.addPermissionView(streamerDID, moderatorDID, []string{"ban", "hide"}, nil)
has, err := pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionBan) require.NoError(t, err) require.True(t, has, "should have 'ban' permission")
has, err = pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionHide) require.NoError(t, err) require.True(t, has, "should have 'hide' permission")
has, err = pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionLivestreamManage) require.NoError(t, err) require.False(t, has, "should not have 'livestream.manage' permission")}
func TestActionPermissions_Mapping(t *testing.T) { require.Equal(t, PermissionBan, ActionPermissions["createBlock"]) require.Equal(t, PermissionBan, ActionPermissions["deleteBlock"]) require.Equal(t, PermissionHide, ActionPermissions["createGate"]) require.Equal(t, PermissionHide, ActionPermissions["deleteGate"]) for _, action := range []string{"finalizeLivestream", "listVideos", "publishVideo", "updateVideo", "deleteVideo"} { require.Equal(t, PermissionLivestreamManage, ActionPermissions[action], action) } require.Equal(t, PermissionLivestreamManage, ActionPermissions["updateLivestream"])}
func TestPermissionChecker_HasPermission_MultipleSeparateRecords(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
mod.addPermissionView(streamerDID, moderatorDID, []string{"ban"}, nil) mod.addPermissionView(streamerDID, moderatorDID, []string{"hide"}, nil)
hasBan, err := pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionBan) require.NoError(t, err) require.True(t, hasBan, "should have 'ban' permission from first record")
hasHide, err := pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionHide) require.NoError(t, err) require.True(t, hasHide, "should have 'hide' permission from second record")
err = pc.CheckPermission(ctx, moderatorDID, streamerDID, "createBlock") require.NoError(t, err, "should allow createBlock with 'ban' permission from separate record")
err = pc.CheckPermission(ctx, moderatorDID, streamerDID, "createGate") require.NoError(t, err, "should allow createGate with 'hide' permission from separate record")}
func TestPermissionChecker_HasPermission_ExpiredDelegation(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
expiredTime := time.Now().Add(-1 * time.Hour) mod.addPermissionView(streamerDID, moderatorDID, []string{"ban"}, &expiredTime)
hasPermission, err := pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionBan) require.NoError(t, err) require.False(t, hasPermission, "should deny permission for expired delegation")
err = pc.CheckPermission(ctx, moderatorDID, streamerDID, "createBlock") require.Error(t, err, "should deny action for expired delegation") require.Contains(t, err.Error(), "does not have permission")}
func TestPermissionChecker_HasPermission_NotYetExpired(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
futureTime := time.Now().Add(1 * time.Hour) mod.addPermissionView(streamerDID, moderatorDID, []string{"ban", "hide"}, &futureTime)
hasPermission, err := pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionBan) require.NoError(t, err) require.True(t, hasPermission, "should allow permission for not-yet-expired delegation")
err = pc.CheckPermission(ctx, moderatorDID, streamerDID, "createBlock") require.NoError(t, err, "should allow action for not-yet-expired delegation")}
func TestPermissionChecker_HasPermission_NoExpiration(t *testing.T) { mod := newMockModel() pc := NewPermissionChecker(mod)
ctx := context.Background() streamerDID := "did:plc:streamer123" moderatorDID := "did:plc:moderator456"
mod.addPermissionView(streamerDID, moderatorDID, []string{"ban", "hide"}, nil)
hasPermission, err := pc.HasPermission(ctx, moderatorDID, streamerDID, PermissionBan) require.NoError(t, err) require.True(t, hasPermission, "should allow permission for delegation with no expiration")
err = pc.CheckPermission(ctx, moderatorDID, streamerDID, "createBlock") require.NoError(t, err, "should allow action for delegation with no expiration")}
type mockModel struct { delegations map[string][]placestream.ModerationDefs_PermissionView}
func newMockModel() *mockModel { return &mockModel{ delegations: make(map[string][]placestream.ModerationDefs_PermissionView), }}
func (m *mockModel) addPermissionView(streamerDID, moderatorDID string, permissions []string, expirationTime *time.Time) { key := streamerDID + "_" + moderatorDID
var expTimeStr *string if expirationTime != nil { str := expirationTime.Format(time.RFC3339) expTimeStr = &str }
permRecord := &placestream.ModerationPermission{ Moderator: moderatorDID, Permissions: permissions, ExpirationTime: expTimeStr, }
view := placestream.ModerationDefs_PermissionView{ Uri: fmt.Sprintf("at://%s/place.stream.moderation.permission/test", streamerDID), Cid: "bafytest", Author: appbsky.ActorDefs_ProfileViewBasic{Did: streamerDID}, Record: &glex.LexiconTypeDecoder{Val: permRecord}, }
m.delegations[key] = append(m.delegations[key], view)}
func (m *mockModel) GetModerationDelegations(ctx context.Context, streamerDID, moderatorDID string) ([]placestream.ModerationDefs_PermissionView, error) { key := streamerDID + "_" + moderatorDID delegations, exists := m.delegations[key] if !exists { return nil, nil } return delegations, nil}