Files
xinmi/internal/workbench/ownership_test.go
T

73 lines
2.9 KiB
Go
Raw Normal View History

package workbench
import (
"context"
"errors"
"testing"
"github.com/Tencent/WeKnora/internal/types"
"gorm.io/gorm"
)
func TestAdministratorCanManageTenantResourcesWithoutChangingOwner(t *testing.T) {
s := sqliteWorkbench(t)
r := seedResource(t, s, 1, "contributor", "training-maps")
ctx := workbenchContext(1, "admin", types.TenantRoleAdmin)
if _, err := s.get(ctx, r.Kind, r.ID); err != nil {
t.Fatal(err)
}
if _, err := lockResource(ctx, s.db, r.Kind, r.ID); err != nil {
t.Fatalf("administrator cannot lock tenant resource for writing: %v", err)
}
if _, err := s.submit(ctx, r.Kind, r.ID, "generate", ActionRequest{Version: 1}); !errors.Is(err, ErrForbidden) {
t.Fatalf("administrator queued another user's task: %v", err)
}
r.Name = "Administrator edit"
if err := s.save(ctx, r, 1); err != nil {
t.Fatalf("administrator cannot persist tenant resource: %v", err)
}
var stored Resource
if err := s.db.First(&stored, "id = ?", r.ID).Error; err != nil || stored.OwnerID != "contributor" || stored.Name != r.Name || stored.Version != 2 {
t.Fatalf("administrator edit changed ownership or was not saved: %+v %v", stored, err)
}
var revision Revision
if err := s.db.Where("resource_id = ? AND version = ?", r.ID, 2).First(&revision).Error; err != nil || revision.ActorID != "admin" {
t.Fatalf("administrator edit audit missing: %+v %v", revision, err)
}
var count int64
s.db.Model(&Job{}).Count(&count)
if count != 0 {
t.Fatal("unauthorized job was queued")
}
}
func TestOnlyAdministratorCanBindAnotherUsersPrivateMap(t *testing.T) {
s := sqliteWorkbench(t)
mapResource := seedResource(t, s, 1, "contributor", "training-maps")
s.db.Model(mapResource).Update("status", "confirmed")
flow := seedResource(t, s, 1, "admin", "flows")
ctx := workbenchContext(1, "admin", types.TenantRoleAdmin)
task := &Resource{TenantID: 1, OwnerID: "admin", Kind: "content-tasks", Data: asJSON(TaskData{MapID: mapResource.ID, FlowID: flow.ID})}
err := s.db.WithContext(context.Background()).Transaction(func(tx *gorm.DB) error { return lockReferences(ctx, tx, task) })
if err != nil {
t.Fatalf("administrator cannot use tenant map: %v", err)
}
ctx = workbenchContext(1, "admin", types.TenantRoleContributor)
err = s.db.Transaction(func(tx *gorm.DB) error { return lockReferences(ctx, tx, task) })
if !errors.Is(err, gorm.ErrRecordNotFound) {
t.Fatalf("non-administrator bound another user's private map: %v", err)
}
}
func TestWorkbenchAdministratorNeverEscapesActiveTenant(t *testing.T) {
s := sqliteWorkbench(t)
r := seedResource(t, s, 2, "contributor", "flows")
ctx := context.WithValue(workbenchContext(1, "admin", types.TenantRoleViewer), types.SystemAdminContextKey, true)
if _, err := lockResource(ctx, s.db, r.Kind, r.ID); !errors.Is(err, gorm.ErrRecordNotFound) {
t.Fatalf("cross-tenant write lock allowed: %v", err)
}
if err := persistResource(ctx, s.db, r, r.Version); !errors.Is(err, ErrForbidden) {
t.Fatalf("cross-tenant save allowed: %v", err)
}
}