Files
admin/e2e/Azaion.E2E/Tests/UserManagementTests.cs
Oleksandr Bezdieniezhnykh 74f5594b0c [AZ-200] Drop email length rule
Made-with: Cursor
2026-04-16 06:59:12 +03:00

222 lines
7.5 KiB
C#

using System.Net;
using System.Net.Http.Json;
using System.Text.Json;
using Azaion.E2E.Helpers;
using FluentAssertions;
using Xunit;
namespace Azaion.E2E.Tests;
[Collection("E2E")]
public sealed class UserManagementTests
{
private static readonly JsonSerializerOptions JsonOptions = new()
{
PropertyNameCaseInsensitive = true
};
private sealed record ErrorResponse(int ErrorCode, string Message);
private sealed record UserDto(Guid Id, string Email, int Role, bool IsEnabled);
private readonly TestFixture _fixture;
public UserManagementTests(TestFixture fixture) => _fixture = fixture;
private static string UserBasePath(string email) => $"/users/{Uri.EscapeDataString(email)}";
[Fact]
public async Task Registration_with_valid_data_succeeds()
{
var email = $"testuser-{Guid.NewGuid():N}@azaion.com";
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
try
{
// Arrange
var body = new { email, password = "SecurePass1!", role = 10 };
// Act
using var response = await client.PostAsync("/users", body);
// Assert
response.StatusCode.Should().BeOneOf(HttpStatusCode.OK, HttpStatusCode.NoContent);
}
finally
{
using var deleteResponse = await client.DeleteAsync(UserBasePath(email));
}
}
[Fact]
public async Task List_users_returns_non_empty_array()
{
// Arrange
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
// Act
using var response = await client.GetAsync("/users");
// Assert
response.StatusCode.Should().Be(HttpStatusCode.OK);
var users = await response.Content.ReadFromJsonAsync<UserDto[]>(JsonOptions);
users.Should().NotBeNull();
users!.Length.Should().BeGreaterThanOrEqualTo(1);
}
[Fact]
public async Task List_users_filtered_by_email_contains_only_matches()
{
// Arrange
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
// Act
using var response = await client.GetAsync("/users?searchEmail=" + Uri.EscapeDataString("admin"));
// Assert
response.StatusCode.Should().Be(HttpStatusCode.OK);
var users = await response.Content.ReadFromJsonAsync<UserDto[]>(JsonOptions);
users.Should().NotBeNull();
users!.Should().NotBeEmpty();
users.Should().OnlyContain(u => u.Email.Contains("admin", StringComparison.OrdinalIgnoreCase));
}
[Fact]
public async Task Set_user_role_succeeds()
{
var email = $"testuser-{Guid.NewGuid():N}@azaion.com";
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
try
{
// Arrange
using (var createResp = await client.PostAsync("/users", new { email, password = "SecurePass1!", role = 10 }))
{
createResp.StatusCode.Should().BeOneOf(HttpStatusCode.OK, HttpStatusCode.NoContent);
}
// Act
using var response = await client.PutAsync($"{UserBasePath(email)}/set-role/50");
// Assert
response.StatusCode.Should().BeOneOf(HttpStatusCode.OK, HttpStatusCode.NoContent);
}
finally
{
using var deleteResponse = await client.DeleteAsync(UserBasePath(email));
}
}
[Fact]
public async Task Disable_user_succeeds()
{
var email = $"testuser-{Guid.NewGuid():N}@azaion.com";
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
try
{
// Arrange
using (var createResp = await client.PostAsync("/users", new { email, password = "SecurePass1!", role = 10 }))
{
createResp.StatusCode.Should().BeOneOf(HttpStatusCode.OK, HttpStatusCode.NoContent);
}
// Act
using var response = await client.PutAsync($"{UserBasePath(email)}/disable");
// Assert
response.StatusCode.Should().BeOneOf(HttpStatusCode.OK, HttpStatusCode.NoContent);
}
finally
{
using var deleteResponse = await client.DeleteAsync(UserBasePath(email));
}
}
[Fact]
public async Task Delete_user_succeeds_and_user_not_in_search_results()
{
var email = $"testuser-{Guid.NewGuid():N}@azaion.com";
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
try
{
// Arrange
using (var createResp = await client.PostAsync("/users", new { email, password = "SecurePass1!", role = 10 }))
{
createResp.StatusCode.Should().BeOneOf(HttpStatusCode.OK, HttpStatusCode.NoContent);
}
// Act
using var deleteResponse = await client.DeleteAsync(UserBasePath(email));
// Assert
deleteResponse.StatusCode.Should().BeOneOf(HttpStatusCode.OK, HttpStatusCode.NoContent);
using var verifyResponse = await client.GetAsync("/users?searchEmail=" + Uri.EscapeDataString(email));
verifyResponse.StatusCode.Should().Be(HttpStatusCode.OK);
var users = await verifyResponse.Content.ReadFromJsonAsync<UserDto[]>(JsonOptions);
users.Should().NotBeNull();
users!.Should().NotContain(u => u.Email.Equals(email, StringComparison.OrdinalIgnoreCase));
}
finally
{
using var deleteResponse = await client.DeleteAsync(UserBasePath(email));
}
}
[Fact]
public async Task Registration_rejects_empty_email_with_400()
{
// Arrange
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
// Act
using var response = await client.PostAsync("/users",
new { email = "", password = "ValidPass123", role = 10 });
// Assert
response.StatusCode.Should().Be(HttpStatusCode.BadRequest);
}
[Fact]
public async Task Registration_rejects_invalid_email_format_with_400()
{
// Arrange
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
// Act
using var response = await client.PostAsync("/users",
new { email = "notavalidemail", password = "ValidPass123", role = 10 });
// Assert
response.StatusCode.Should().Be(HttpStatusCode.BadRequest);
}
[Fact]
public async Task Registration_rejects_short_password_with_400()
{
// Arrange
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
// Act
using var response = await client.PostAsync("/users",
new { email = "validmail@test.com", password = "short", role = 10 });
// Assert
response.StatusCode.Should().Be(HttpStatusCode.BadRequest);
}
[Fact]
public async Task Registration_rejects_duplicate_admin_email_with_409()
{
// Arrange
using var client = _fixture.CreateAuthenticatedClient(_fixture.AdminToken);
// Act
using var response = await client.PostAsync("/users",
new { email = _fixture.AdminEmail, password = "DuplicateP1!", role = 10 });
// Assert
response.StatusCode.Should().Be(HttpStatusCode.Conflict);
var err = await response.Content.ReadFromJsonAsync<ErrorResponse>(JsonOptions);
err.Should().NotBeNull();
err!.ErrorCode.Should().Be(20);
}
}