Files
restic-manager/internal/server/http/rbac_test.go
T

97 lines
2.6 KiB
Go

package http
import (
stdhttp "net/http"
"net/http/httptest"
"strings"
"testing"
"gitea.dcglab.co.uk/steve/restic-manager/internal/store"
)
func TestRoleAtLeast(t *testing.T) {
t.Parallel()
cases := []struct {
have store.Role
min store.Role
want bool
}{
{store.RoleViewer, store.RoleViewer, true},
{store.RoleOperator, store.RoleViewer, true},
{store.RoleAdmin, store.RoleViewer, true},
{store.RoleAdmin, store.RoleOperator, true},
{store.RoleAdmin, store.RoleAdmin, true},
{store.RoleViewer, store.RoleOperator, false},
{store.RoleViewer, store.RoleAdmin, false},
{store.RoleOperator, store.RoleAdmin, false},
{store.Role("nonsense"), store.RoleViewer, false},
{store.RoleAdmin, store.Role("nonsense"), false},
}
for _, c := range cases {
got := roleAtLeast(c.have, c.min)
if got != c.want {
t.Errorf("have=%q min=%q: got %v want %v", c.have, c.min, got, c.want)
}
}
}
func TestRequireRoleViewerAdmits(t *testing.T) {
t.Parallel()
srv, _ := newTestServer(t, false)
uid := makeUser(t, srv, "viewer1", store.RoleViewer)
cookie := loginAs(t, srv, uid)
mid := srv.requireRole(store.RoleViewer)
h := mid(stdhttp.HandlerFunc(func(w stdhttp.ResponseWriter, _ *stdhttp.Request) {
w.WriteHeader(stdhttp.StatusOK)
}))
rr := httptest.NewRecorder()
req, _ := stdhttp.NewRequest("GET", "/api/dummy", nil)
req.AddCookie(cookie)
h.ServeHTTP(rr, req)
if rr.Code != stdhttp.StatusOK {
t.Errorf("status: got %d want 200", rr.Code)
}
}
func TestRequireRoleViewerRejectedFromOperator(t *testing.T) {
t.Parallel()
srv, _ := newTestServer(t, false)
uid := makeUser(t, srv, "viewer2", store.RoleViewer)
cookie := loginAs(t, srv, uid)
mid := srv.requireRole(store.RoleOperator)
h := mid(stdhttp.HandlerFunc(func(w stdhttp.ResponseWriter, _ *stdhttp.Request) {
w.WriteHeader(stdhttp.StatusOK)
}))
rr := httptest.NewRecorder()
req, _ := stdhttp.NewRequest("GET", "/api/dummy", nil)
req.AddCookie(cookie)
h.ServeHTTP(rr, req)
if rr.Code != stdhttp.StatusForbidden {
t.Errorf("status: got %d want 403", rr.Code)
}
if !strings.Contains(rr.Body.String(), "insufficient_role") {
t.Errorf("body: got %q", rr.Body.String())
}
}
func TestRequireRoleUnauthenticated401OnAPI(t *testing.T) {
t.Parallel()
srv, _ := newTestServer(t, false)
mid := srv.requireRole(store.RoleViewer)
h := mid(stdhttp.HandlerFunc(func(w stdhttp.ResponseWriter, _ *stdhttp.Request) {
w.WriteHeader(stdhttp.StatusOK)
}))
rr := httptest.NewRecorder()
req, _ := stdhttp.NewRequest("GET", "/api/dummy", nil)
h.ServeHTTP(rr, req)
if rr.Code != stdhttp.StatusUnauthorized {
t.Errorf("status: got %d want 401", rr.Code)
}
}