295 lines
7.1 KiB
Go
295 lines
7.1 KiB
Go
package service
|
|
|
|
import (
|
|
"acc-server-manager/local/model"
|
|
"acc-server-manager/local/utl/jwt"
|
|
"acc-server-manager/local/utl/password"
|
|
"acc-server-manager/tests"
|
|
"testing"
|
|
|
|
"github.com/google/uuid"
|
|
)
|
|
|
|
func TestJWT_GenerateAndValidateToken(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Create test user
|
|
user := &model.User{
|
|
ID: uuid.New(),
|
|
Username: "testuser",
|
|
RoleID: uuid.New(),
|
|
}
|
|
|
|
// Test JWT generation
|
|
token, err := jwt.GenerateToken(user)
|
|
tests.AssertNoError(t, err)
|
|
tests.AssertNotNil(t, token)
|
|
|
|
// Verify token is not empty
|
|
if token == "" {
|
|
t.Fatal("Expected non-empty token, got empty string")
|
|
}
|
|
|
|
// Test JWT validation
|
|
claims, err := jwt.ValidateToken(token)
|
|
tests.AssertNoError(t, err)
|
|
tests.AssertNotNil(t, claims)
|
|
tests.AssertEqual(t, user.ID.String(), claims.UserID)
|
|
}
|
|
|
|
func TestJWT_ValidateToken_InvalidToken(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Test with invalid token
|
|
claims, err := jwt.ValidateToken("invalid-token")
|
|
if err == nil {
|
|
t.Fatal("Expected error for invalid token, got nil")
|
|
}
|
|
// Direct nil check to avoid the interface wrapping issue
|
|
if claims != nil {
|
|
t.Fatalf("Expected nil claims, got %v", claims)
|
|
}
|
|
}
|
|
|
|
func TestJWT_ValidateToken_EmptyToken(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Test with empty token
|
|
claims, err := jwt.ValidateToken("")
|
|
if err == nil {
|
|
t.Fatal("Expected error for empty token, got nil")
|
|
}
|
|
// Direct nil check to avoid the interface wrapping issue
|
|
if claims != nil {
|
|
t.Fatalf("Expected nil claims, got %v", claims)
|
|
}
|
|
}
|
|
|
|
func TestUser_VerifyPassword_Success(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Create test user
|
|
user := &model.User{
|
|
ID: uuid.New(),
|
|
Username: "testuser",
|
|
RoleID: uuid.New(),
|
|
}
|
|
|
|
// Hash password manually (simulating what BeforeCreate would do)
|
|
plainPassword := "password123"
|
|
hashedPassword, err := password.HashPassword(plainPassword)
|
|
tests.AssertNoError(t, err)
|
|
user.Password = hashedPassword
|
|
|
|
// Test password verification - should succeed
|
|
err = user.VerifyPassword(plainPassword)
|
|
tests.AssertNoError(t, err)
|
|
}
|
|
|
|
func TestUser_VerifyPassword_Failure(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Create test user
|
|
user := &model.User{
|
|
ID: uuid.New(),
|
|
Username: "testuser",
|
|
RoleID: uuid.New(),
|
|
}
|
|
|
|
// Hash password manually
|
|
hashedPassword, err := password.HashPassword("correct_password")
|
|
tests.AssertNoError(t, err)
|
|
user.Password = hashedPassword
|
|
|
|
// Test password verification with wrong password - should fail
|
|
err = user.VerifyPassword("wrong_password")
|
|
if err == nil {
|
|
t.Fatal("Expected error for wrong password, got nil")
|
|
}
|
|
}
|
|
|
|
func TestUser_Validate_Success(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Create valid user
|
|
user := &model.User{
|
|
ID: uuid.New(),
|
|
Username: "testuser",
|
|
Password: "password123",
|
|
RoleID: uuid.New(),
|
|
}
|
|
|
|
// Test validation - should succeed
|
|
err := user.Validate()
|
|
tests.AssertNoError(t, err)
|
|
}
|
|
|
|
func TestUser_Validate_MissingUsername(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Create user without username
|
|
user := &model.User{
|
|
ID: uuid.New(),
|
|
Username: "", // Missing username
|
|
Password: "password123",
|
|
RoleID: uuid.New(),
|
|
}
|
|
|
|
// Test validation - should fail
|
|
err := user.Validate()
|
|
if err == nil {
|
|
t.Fatal("Expected error for missing username, got nil")
|
|
}
|
|
}
|
|
|
|
func TestUser_Validate_MissingPassword(t *testing.T) {
|
|
// Setup
|
|
helper := tests.NewTestHelper(t)
|
|
defer helper.Cleanup()
|
|
|
|
// Create user without password
|
|
user := &model.User{
|
|
ID: uuid.New(),
|
|
Username: "testuser",
|
|
Password: "", // Missing password
|
|
RoleID: uuid.New(),
|
|
}
|
|
|
|
// Test validation - should fail
|
|
err := user.Validate()
|
|
if err == nil {
|
|
t.Fatal("Expected error for missing password, got nil")
|
|
}
|
|
}
|
|
|
|
func TestPassword_HashAndVerify(t *testing.T) {
|
|
// Test password hashing and verification directly
|
|
plainPassword := "test_password_123"
|
|
|
|
// Hash password
|
|
hashedPassword, err := password.HashPassword(plainPassword)
|
|
tests.AssertNoError(t, err)
|
|
tests.AssertNotNil(t, hashedPassword)
|
|
|
|
// Verify hashed password is not the same as plain password
|
|
if hashedPassword == plainPassword {
|
|
t.Fatal("Hashed password should not equal plain password")
|
|
}
|
|
|
|
// Verify correct password
|
|
err = password.VerifyPassword(hashedPassword, plainPassword)
|
|
tests.AssertNoError(t, err)
|
|
|
|
// Verify wrong password fails
|
|
err = password.VerifyPassword(hashedPassword, "wrong_password")
|
|
if err == nil {
|
|
t.Fatal("Expected error for wrong password, got nil")
|
|
}
|
|
}
|
|
|
|
func TestPassword_ValidatePasswordStrength(t *testing.T) {
|
|
testCases := []struct {
|
|
name string
|
|
password string
|
|
shouldError bool
|
|
}{
|
|
{"Valid password", "StrongPassword123!", false},
|
|
{"Too short", "123", true},
|
|
{"Empty password", "", true},
|
|
{"Medium password", "password123", false}, // Depends on validation rules
|
|
}
|
|
|
|
for _, tc := range testCases {
|
|
t.Run(tc.name, func(t *testing.T) {
|
|
err := password.ValidatePasswordStrength(tc.password)
|
|
if tc.shouldError {
|
|
if err == nil {
|
|
t.Fatalf("Expected error for password '%s', got nil", tc.password)
|
|
}
|
|
} else {
|
|
if err != nil {
|
|
t.Fatalf("Expected no error for password '%s', got: %v", tc.password, err)
|
|
}
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestRole_Model(t *testing.T) {
|
|
// Test Role model structure
|
|
permissions := []model.Permission{
|
|
{ID: uuid.New(), Name: "read"},
|
|
{ID: uuid.New(), Name: "write"},
|
|
{ID: uuid.New(), Name: "admin"},
|
|
}
|
|
|
|
role := &model.Role{
|
|
ID: uuid.New(),
|
|
Name: "Test Role",
|
|
Permissions: permissions,
|
|
}
|
|
|
|
// Verify role structure
|
|
tests.AssertEqual(t, "Test Role", role.Name)
|
|
tests.AssertEqual(t, 3, len(role.Permissions))
|
|
tests.AssertEqual(t, "read", role.Permissions[0].Name)
|
|
tests.AssertEqual(t, "write", role.Permissions[1].Name)
|
|
tests.AssertEqual(t, "admin", role.Permissions[2].Name)
|
|
}
|
|
|
|
func TestPermission_Model(t *testing.T) {
|
|
// Test Permission model structure
|
|
permission := &model.Permission{
|
|
ID: uuid.New(),
|
|
Name: "test_permission",
|
|
}
|
|
|
|
// Verify permission structure
|
|
tests.AssertEqual(t, "test_permission", permission.Name)
|
|
tests.AssertNotNil(t, permission.ID)
|
|
}
|
|
|
|
func TestUser_WithRole_Model(t *testing.T) {
|
|
// Test User model with Role relationship
|
|
permissions := []model.Permission{
|
|
{ID: uuid.New(), Name: "read"},
|
|
{ID: uuid.New(), Name: "write"},
|
|
}
|
|
|
|
role := model.Role{
|
|
ID: uuid.New(),
|
|
Name: "User",
|
|
Permissions: permissions,
|
|
}
|
|
|
|
user := &model.User{
|
|
ID: uuid.New(),
|
|
Username: "testuser",
|
|
Password: "hashedpassword",
|
|
RoleID: role.ID,
|
|
Role: role,
|
|
}
|
|
|
|
// Verify user-role relationship
|
|
tests.AssertEqual(t, "testuser", user.Username)
|
|
tests.AssertEqual(t, role.ID, user.RoleID)
|
|
tests.AssertEqual(t, "User", user.Role.Name)
|
|
tests.AssertEqual(t, 2, len(user.Role.Permissions))
|
|
tests.AssertEqual(t, "read", user.Role.Permissions[0].Name)
|
|
tests.AssertEqual(t, "write", user.Role.Permissions[1].Name)
|
|
}
|