Files
notely/backend/tests/unit/auth_service_test.go
2026-03-26 16:27:14 +00:00

186 lines
4.7 KiB
Go

package unit
import (
"context"
"testing"
"gitea.hostxtra.co.uk/mrhid6/notely/backend/internal/application/dto"
"gitea.hostxtra.co.uk/mrhid6/notely/backend/internal/application/services"
"gitea.hostxtra.co.uk/mrhid6/notely/backend/internal/domain/entities"
"gitea.hostxtra.co.uk/mrhid6/notely/backend/internal/infrastructure/auth"
"gitea.hostxtra.co.uk/mrhid6/notely/backend/internal/infrastructure/security"
"go.mongodb.org/mongo-driver/v2/bson"
)
// MockUserRepository is a mock for testing
type MockUserRepository struct {
users map[string]*entities.User
}
func NewMockUserRepository() *MockUserRepository {
return &MockUserRepository{
users: make(map[string]*entities.User),
}
}
func (m *MockUserRepository) CreateUser(ctx context.Context, user *entities.User) error {
m.users[user.Email] = user
return nil
}
func (m *MockUserRepository) GetUserByID(ctx context.Context, id bson.ObjectID) (*entities.User, error) {
for _, u := range m.users {
if u.Email != "" {
return u, nil
}
}
return nil, nil
}
func (m *MockUserRepository) GetUserByEmail(ctx context.Context, email string) (*entities.User, error) {
if user, ok := m.users[email]; ok {
return user, nil
}
return nil, nil
}
func (m *MockUserRepository) GetUserByUsername(ctx context.Context, username string) (*entities.User, error) {
// Simplified mock
return nil, nil
}
func (m *MockUserRepository) UpdateUser(ctx context.Context, user *entities.User) error {
return nil
}
func (m *MockUserRepository) DeleteUser(ctx context.Context, id bson.ObjectID) error {
return nil
}
func (m *MockUserRepository) ListAllUsers(ctx context.Context) ([]*entities.User, error) {
users := make([]*entities.User, 0, len(m.users))
for _, user := range m.users {
users = append(users, user)
}
return users, nil
}
// TestRegisterUser tests user registration
func TestRegisterUser(t *testing.T) {
mockRepo := NewMockUserRepository()
jwtManager := auth.NewJWTManager("test-secret-key", "noteapp", 0)
passHasher := security.NewPasswordHasher()
encryptor, _ := security.NewEncryptor("00000000000000000000000000000000")
authService := services.NewAuthService(
mockRepo,
nil,
nil,
nil,
nil,
nil,
nil,
jwtManager,
passHasher,
encryptor,
)
req := &dto.RegisterRequest{
Email: "test@example.com",
Username: "testuser",
Password: "SecurePassword123",
PasswordConfirm: "SecurePassword123",
FirstName: "Test",
LastName: "User",
}
response, err := authService.Register(context.Background(), req)
if err != nil {
t.Fatalf("Expected no error, got %v", err)
}
if response == nil {
t.Fatal("Expected response, got nil")
}
if response.AccessToken == "" {
t.Fatal("Expected access token")
}
if response.User.Email != req.Email {
t.Fatalf("Expected email %s, got %s", req.Email, response.User.Email)
}
}
// TestPasswordHashing tests password hashing and verification
func TestPasswordHashing(t *testing.T) {
hasher := security.NewPasswordHasher()
password := "MySecurePassword123"
// Hash password
hash, err := hasher.HashPassword(password)
if err != nil {
t.Fatalf("Failed to hash password: %v", err)
}
// Verify correct password
valid, err := hasher.VerifyPassword(password, hash)
if err != nil || !valid {
t.Fatal("Expected password verification to succeed")
}
// Verify wrong password
valid, err = hasher.VerifyPassword("WrongPassword", hash)
if err == nil || valid {
t.Fatal("Expected password verification to fail")
}
}
// TestJWTGeneration tests JWT token generation and verification
func TestJWTGeneration(t *testing.T) {
jwtManager := auth.NewJWTManager("test-secret-key", "noteapp", 0)
token, err := jwtManager.GenerateAccessToken("user123", "user@example.com", "testuser")
if err != nil {
t.Fatalf("Failed to generate token: %v", err)
}
claims, err := jwtManager.VerifyAccessToken(token)
if err != nil {
t.Fatalf("Failed to verify token: %v", err)
}
if claims.UserID != "user123" {
t.Fatalf("Expected user_id user123, got %s", claims.UserID)
}
if claims.Email != "user@example.com" {
t.Fatalf("Expected email user@example.com, got %s", claims.Email)
}
}
// TestEncryption tests encryption and decryption
func TestEncryption(t *testing.T) {
encryptor, err := security.NewEncryptor("00000000000000000000000000000000")
if err != nil {
t.Fatalf("Failed to create encryptor: %v", err)
}
plaintext := "sensitive-data-to-encrypt"
encrypted, err := encryptor.Encrypt(plaintext)
if err != nil {
t.Fatalf("Failed to encrypt: %v", err)
}
decrypted, err := encryptor.Decrypt(encrypted)
if err != nil {
t.Fatalf("Failed to decrypt: %v", err)
}
if decrypted != plaintext {
t.Fatalf("Expected %s, got %s", plaintext, decrypted)
}
}