using System.Net.Http.Headers; using System.Net.Http.Json; using Halo.Api.Endpoints; using Microsoft.AspNetCore.Mvc.Testing; namespace Halo.Api.Tests; /// Ein frisch gestarteter Server mit leerer Datenbank. /// /// /// Eine echte SQLite-Datei, kein Ersatz im Arbeitsspeicher. Damit läuft /// auch das durch, worauf es beim ersten Start ankommt: Verzeichnisse anlegen, /// Migration wandern lassen, Einrichtung anbieten. Genau diese Kette sieht ein /// Fremder als Erstes — und genau sie würde ein Ersatzspeicher überspringen. /// public sealed class HaloServer : IDisposable { private readonly WebApplicationFactory _fabrik; private readonly string _verzeichnis; public HttpClient Client { get; } public HaloServer() { _verzeichnis = Path.Combine(Path.GetTempPath(), "halo-test-" + Guid.CreateVersion7().ToString("N")); Environment.SetEnvironmentVariable("HALO_DATA", Path.Combine(_verzeichnis, "config")); Environment.SetEnvironmentVariable("HALO_CACHE", Path.Combine(_verzeichnis, "cache")); Environment.SetEnvironmentVariable("HALO_TRANSCODE", Path.Combine(_verzeichnis, "transcode")); // Die Zugriffsgrenze zählt je Adresse, und im Test kommt alles von // derselben. Ohne das Hochsetzen prüfte man hier die Grenze statt der // Anmeldung. Environment.SetEnvironmentVariable("HALO_RATELIMIT_SIGNIN", "10000"); _fabrik = new WebApplicationFactory(); Client = _fabrik.CreateClient(); } /// Richtet ein und meldet den Administrator an. public async Task SetUpAndSignIn(string name = "guido", string passwort = "ein-langes-passwort") { var einrichten = await Client.PostAsJsonAsync("/api/v1/system/setup", new SetupRequest(name, passwort)); einrichten.EnsureSuccessStatusCode(); return await SignIn(name, passwort); } public async Task SignIn(string name, string passwort, string gerät = "iPhone", string kennung = "geraet-1") { var antwort = await Client.PostAsJsonAsync("/api/v1/auth/login", new LoginRequest(name, passwort, gerät, kennung)); antwort.EnsureSuccessStatusCode(); return (await antwort.Content.ReadFromJsonAsync())!; } /// Ein eigener Client, der ein Token vorzeigt. public HttpClient AlsAngemeldeter(string token) { var client = _fabrik.CreateClient(); client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", token); return client; } public void Dispose() { _fabrik.Dispose(); try { Directory.Delete(_verzeichnis, recursive: true); } catch (IOException) { /* Aufräumen ist Kür */ } } }