blob: d536c4ea9466b4b7a96be3a55f984cfc8d993948 [file] [log] [blame]
// Package alogin defines the Login interface for handling login in web
// applications.
//
// The implementations of Login should be used with the
// //infra-sk/modules/alogin-sk control.
package alogin_test
import (
"encoding/json"
"net/http"
"net/http/httptest"
"testing"
"github.com/stretchr/testify/require"
"go.skia.org/infra/go/alogin"
"go.skia.org/infra/go/alogin/mocks"
"go.skia.org/infra/go/roles"
)
const (
email alogin.EMail = "user@example.com"
)
func TestSessionMiddleware_UserIsLoggedIn_SessionIsReturedWithEmailAndRoles(t *testing.T) {
r := httptest.NewRequest("GET", "/", nil)
w := httptest.NewRecorder()
login := mocks.NewLogin(t)
login.On("Roles", r).Return(roles.Roles{roles.Editor})
login.On("LoggedInAs", r).Return(email)
called := false
m := alogin.StatusMiddleware(login)(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
s := alogin.GetStatus(r.Context())
require.Equal(t, &alogin.Status{
EMail: email,
Roles: roles.Roles{roles.Editor},
}, s)
called = true
}))
m.ServeHTTP(w, r)
require.True(t, called)
}
func TestSessionMiddleware_UserIsNotLoggedIn_EmptySessionIsRetured(t *testing.T) {
r := httptest.NewRequest("GET", "/", nil)
s := alogin.GetStatus(r.Context())
require.Equal(t, &alogin.Status{}, s)
}
func TestLoginStatusHandler(t *testing.T) {
r := httptest.NewRequest("GET", "/", nil)
w := httptest.NewRecorder()
login := mocks.NewLogin(t)
login.On("Status", r).Return(alogin.Status{
EMail: email,
Roles: roles.Roles{roles.Editor},
})
alogin.LoginStatusHandler(login)(w, r)
var status alogin.Status
err := json.Unmarshal(w.Body.Bytes(), &status)
require.NoError(t, err)
require.Equal(t, "application/json", w.Header().Get("Content-Type"))
}
func TestForceRole_UserIsLoggedIn_HandlerIsCalled(t *testing.T) {
r := httptest.NewRequest("GET", "/", nil)
w := httptest.NewRecorder()
login := mocks.NewLogin(t)
login.On("HasRole", r, roles.Editor).Return(true)
login.On("LoggedInAs", r).Return(email)
called := false
m := alogin.ForceRole(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
called = true
}), login, roles.Editor)
m.ServeHTTP(w, r)
require.True(t, called)
require.Equal(t, w.Code, http.StatusOK)
}
func TestForceRole_UserIsNotLoggedIn_HandlerIsNotCalled(t *testing.T) {
r := httptest.NewRequest("GET", "/", nil)
w := httptest.NewRecorder()
login := mocks.NewLogin(t)
login.On("LoggedInAs", r).Return(alogin.NotLoggedIn)
called := false
m := alogin.ForceRole(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
called = true
}), login, roles.Viewer)
m.ServeHTTP(w, r)
require.False(t, called)
require.Equal(t, w.Code, http.StatusUnauthorized)
}
func TestForceRoleMiddleware_UserIsLoggedIn_HandlerCalled(t *testing.T) {
r := httptest.NewRequest("GET", "/", nil)
w := httptest.NewRecorder()
login := mocks.NewLogin(t)
login.On("HasRole", r, roles.Viewer).Return(true)
called := false
m := alogin.ForceRoleMiddleware(login, roles.Viewer)
h := m(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
called = true
}))
h.ServeHTTP(w, r)
require.True(t, called)
require.Equal(t, w.Code, http.StatusOK)
}
func TestForceRoleMiddleware_UserIsNotLoggedIn_HandleIsNotCalled(t *testing.T) {
r := httptest.NewRequest("GET", "/", nil)
w := httptest.NewRecorder()
login := mocks.NewLogin(t)
login.On("HasRole", r, roles.Viewer).Return(false)
login.On("LoginURL", r).Return("https://skia.org/login")
called := false
m := alogin.ForceRoleMiddleware(login, roles.Viewer)
h := m(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
called = true
}))
h.ServeHTTP(w, r)
require.False(t, called)
require.Equal(t, w.Code, http.StatusSeeOther)
}