120 lines
3.2 KiB
Go
120 lines
3.2 KiB
Go
package handlers
|
|
|
|
import (
|
|
"bytes"
|
|
"net/http"
|
|
"net/http/httptest"
|
|
"net/url"
|
|
"strings"
|
|
"testing"
|
|
|
|
"github.com/rs/zerolog"
|
|
"github.com/rs/zerolog/log"
|
|
"golang.org/x/crypto/bcrypt"
|
|
)
|
|
|
|
func TestSignupLogsAuthStoreMutations(t *testing.T) {
|
|
var buf bytes.Buffer
|
|
restore := log.Logger
|
|
log.Logger = zerolog.New(&buf)
|
|
defer func() {
|
|
log.Logger = restore
|
|
}()
|
|
|
|
handler := newTestAuthHandler(t)
|
|
|
|
form := url.Values{}
|
|
form.Set("email", "new@xtablo.com")
|
|
form.Set("password", "xtablo-secret")
|
|
|
|
req := httptest.NewRequest(http.MethodPost, "/signup", strings.NewReader(form.Encode()))
|
|
req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
|
|
rec := httptest.NewRecorder()
|
|
|
|
handler.PostSignup().ServeHTTP(rec, req)
|
|
|
|
output := buf.String()
|
|
for _, want := range []string{
|
|
`"action":"create_user"`,
|
|
`"email":"new@xtablo.com"`,
|
|
`"action":"create_session"`,
|
|
`"session_id":"`,
|
|
} {
|
|
if !strings.Contains(output, want) {
|
|
t.Fatalf("expected log output to contain %q, got %q", want, output)
|
|
}
|
|
}
|
|
}
|
|
|
|
func TestSignupHashesPasswordBeforeStoringUser(t *testing.T) {
|
|
repo := NewInMemoryAuthRepository()
|
|
handler := NewAuthHandler(repo)
|
|
|
|
form := url.Values{}
|
|
form.Set("email", "new@xtablo.com")
|
|
form.Set("password", "xtablo-secret")
|
|
|
|
req := httptest.NewRequest(http.MethodPost, "/signup", strings.NewReader(form.Encode()))
|
|
req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
|
|
rec := httptest.NewRecorder()
|
|
|
|
handler.PostSignup().ServeHTTP(rec, req)
|
|
|
|
if rec.Code != http.StatusOK {
|
|
t.Fatalf("expected status 200, got %d", rec.Code)
|
|
}
|
|
|
|
storedUser, err := repo.GetAuthUserByEmail(req.Context(), "new@xtablo.com")
|
|
if err != nil {
|
|
t.Fatalf("expected stored user, got error %v", err)
|
|
}
|
|
if storedUser.EncryptedPassword == "xtablo-secret" {
|
|
t.Fatalf("expected stored password hash, got plaintext")
|
|
}
|
|
if bcrypt.CompareHashAndPassword([]byte(storedUser.EncryptedPassword), []byte("xtablo-secret")) != nil {
|
|
t.Fatalf("expected stored password to match bcrypt hash")
|
|
}
|
|
}
|
|
|
|
func TestLogoutLogsSessionDeletion(t *testing.T) {
|
|
var buf bytes.Buffer
|
|
restore := log.Logger
|
|
log.Logger = zerolog.New(&buf)
|
|
defer func() {
|
|
log.Logger = restore
|
|
}()
|
|
|
|
handler := newTestAuthHandler(t)
|
|
|
|
loginForm := url.Values{}
|
|
loginForm.Set("email", "demo@xtablo.com")
|
|
loginForm.Set("password", "xtablo-demo")
|
|
|
|
loginReq := httptest.NewRequest(http.MethodPost, "/login", strings.NewReader(loginForm.Encode()))
|
|
loginReq.Header.Set("Content-Type", "application/x-www-form-urlencoded")
|
|
loginRec := httptest.NewRecorder()
|
|
handler.PostLogin().ServeHTTP(loginRec, loginReq)
|
|
|
|
sessionCookie := loginRec.Result().Cookies()[0]
|
|
|
|
logoutReq := httptest.NewRequest(http.MethodPost, "/logout", nil)
|
|
logoutReq.AddCookie(sessionCookie)
|
|
logoutRec := httptest.NewRecorder()
|
|
handler.PostLogout().ServeHTTP(logoutRec, logoutReq)
|
|
|
|
output := buf.String()
|
|
for _, want := range []string{
|
|
`"action":"delete_session"`,
|
|
`"email":"demo@xtablo.com"`,
|
|
`"session_id":"`,
|
|
} {
|
|
if !strings.Contains(output, want) {
|
|
t.Fatalf("expected log output to contain %q, got %q", want, output)
|
|
}
|
|
}
|
|
}
|
|
|
|
func newTestAuthHandler(t *testing.T) *AuthHandler {
|
|
t.Helper()
|
|
return NewAuthHandler(NewInMemoryAuthRepository())
|
|
}
|