Files
vigilcare-clinical/VigilCareClinicalAPI.Tests/Simulation/SimulationEndpointTests.cs
T
voltsrage 24f45851e9
CI / frontend (push) Canceled after 0s
CI / backend (push) Canceled after 8m32s
feature: In-App Simulation Runner (Backend)
2026-08-06 01:52:53 +08:00

153 lines
4.9 KiB
C#

using System.Net;
using System.Net.Http.Json;
using System.Text.Json;
using FluentAssertions;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using StackExchange.Redis;
[Collection("Integration")]
public class SimulationEndpointTests : IAsyncLifetime
{
private readonly ApiFixture _fixture;
private readonly HttpClient _client;
public SimulationEndpointTests(ApiFixture fixture)
{
_fixture = fixture;
_client = fixture.CreateClient();
}
public async Task InitializeAsync()
{
using var scope = _fixture.Services.CreateScope();
var db = scope.ServiceProvider.GetRequiredService<AppDbContext>();
var redis = scope.ServiceProvider.GetRequiredService<IConnectionMultiplexer>();
await DbResetHelper.ResetAsync(db);
await DataSeeder.SeedThresholdsOnlyAsync(db, redis);
_fixture.SimulationClientFactory.HangOnCreate = false;
_fixture.SimulationClientFactory.FailOnCreate = false;
_client.DefaultRequestHeaders.Remove("X-Test-Role");
_client.DefaultRequestHeaders.Remove("X-Test-User-Id");
_client.AsAdmin();
}
public Task DisposeAsync() => Task.CompletedTask;
[Fact]
public async Task Config_ReturnsEnabledFalse_WhenDisabled()
{
using var factory = _fixture.WithWebHostBuilder(builder =>
{
builder.ConfigureAppConfiguration((_, config) =>
{
config.AddInMemoryCollection(new Dictionary<string, string?>
{
["Simulation:Enabled"] = "false",
});
});
});
var client = factory.CreateClient();
client.AsAdmin();
var resp = await client.GetAsync("/api/v1/simulation/config");
resp.StatusCode.Should().Be(HttpStatusCode.OK);
var body = await resp.Content.ReadFromJsonAsync<JsonElement>();
body.GetProperty("data").GetProperty("enabled").GetBoolean().Should().BeFalse();
}
[Fact]
public async Task Scenarios_WhenDisabled_Returns404()
{
using var factory = _fixture.WithWebHostBuilder(builder =>
{
builder.ConfigureAppConfiguration((_, config) =>
{
config.AddInMemoryCollection(new Dictionary<string, string?>
{
["Simulation:Enabled"] = "false",
});
});
});
var client = factory.CreateClient();
client.AsAdmin();
var resp = await client.GetAsync("/api/v1/simulation/scenarios");
resp.StatusCode.Should().Be(HttpStatusCode.NotFound);
}
[Fact]
public async Task Scenarios_AsNurse_Returns200()
{
_client.AsNurse();
var resp = await _client.GetAsync("/api/v1/simulation/scenarios");
resp.StatusCode.Should().Be(HttpStatusCode.OK);
var body = await resp.Content.ReadFromJsonAsync<JsonElement>();
var items = body.GetProperty("data");
items.GetArrayLength().Should().BeGreaterThan(0);
items[0].GetProperty("id").GetString().Should().Be("minimal-sim-01");
}
[Fact]
public async Task StartRun_AsIntegrationRole_Returns403()
{
_client.AsIntegration();
var resp = await _client.PostAsJsonAsync("/api/v1/simulation/runs", new
{
scenarioId = "minimal-sim-01",
speed = 600
});
resp.StatusCode.Should().Be(HttpStatusCode.Forbidden);
}
[Fact]
public async Task StartRun_WritesAuditLog()
{
_client.AsPhysician();
var resp = await _client.PostAsJsonAsync("/api/v1/simulation/runs", new
{
scenarioId = "minimal-sim-01",
speed = 600
});
resp.StatusCode.Should().Be(HttpStatusCode.Created);
var body = await resp.Content.ReadFromJsonAsync<JsonElement>();
var runId = body.GetProperty("data").GetProperty("runId").GetGuid();
using var scope = _fixture.Services.CreateScope();
var db = scope.ServiceProvider.GetRequiredService<AppDbContext>();
var audit = await db.ClinicalAuditLogs
.Where(a => a.Action == AuditAction.SimulationRunStarted && a.EntityId == runId)
.SingleOrDefaultAsync();
audit.Should().NotBeNull();
audit!.EntityType.Should().Be("SimulationRun");
}
[Fact]
public async Task Config_WhenEnabled_ReturnsLimits()
{
_client.AsNurse();
var resp = await _client.GetAsync("/api/v1/simulation/config");
resp.StatusCode.Should().Be(HttpStatusCode.OK);
var body = await resp.Content.ReadFromJsonAsync<JsonElement>();
var data = body.GetProperty("data");
data.GetProperty("enabled").GetBoolean().Should().BeTrue();
data.GetProperty("maxSpeed").GetDouble().Should().Be(600);
data.GetProperty("maxConcurrentRuns").GetInt32().Should().Be(2);
}
}