From f73ac0d4d8ef17a5546dccdad34703c8c1d062c2 Mon Sep 17 00:00:00 2001 From: Gulum Date: Sat, 6 Jun 2026 09:21:19 +0200 Subject: [PATCH] =?UTF-8?q?WEB-0:=20CMS=20endpoint=20tests=20=E2=80=94=20s?= =?UTF-8?q?napshot=20shape/nav,=20Abgabetiere=20resolves=20ForSale=20(Beck?= =?UTF-8?q?en=20group),=20block=20CRUD+reorder=20(SQLite=20host)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- GerbilManager.Tests/CmsTests.cs | 83 +++++++++++++++++++++++++++++++++ 1 file changed, 83 insertions(+) create mode 100644 GerbilManager.Tests/CmsTests.cs diff --git a/GerbilManager.Tests/CmsTests.cs b/GerbilManager.Tests/CmsTests.cs new file mode 100644 index 0000000..037b65a --- /dev/null +++ b/GerbilManager.Tests/CmsTests.cs @@ -0,0 +1,83 @@ +using System.Net; +using System.Net.Http.Json; +using System.Text.Json; + +namespace GerbilManager.Tests; + +/// WEB-0: CMS snapshot shape, Abgabetiere auto-resolution from ForSale, block reorder. +public class CmsTests : IClassFixture +{ + private readonly HttpClient _client; + public CmsTests(ApiFactory factory) => _client = factory.CreateClient(); + + [Fact] + public async Task Snapshot_has_site_nav_and_six_seeded_pages() + { + var doc = JsonDocument.Parse(await _client.GetStringAsync("/api/site-snapshot")); + var root = doc.RootElement; + + Assert.Equal("de", root.GetProperty("site").GetProperty("defaultLocale").GetString()); + var nav = root.GetProperty("site").GetProperty("navOrder").EnumerateArray().Select(x => x.GetString()).ToList(); + Assert.Equal(new[] { "start", "ueber-die-zucht", "abgabetiere", "abgabebedingungen", "farben-genetik", "kontakt" }, nav); + + var pages = root.GetProperty("pages").EnumerateArray().ToList(); + Assert.Equal(6, pages.Count); + // abgabetiere page carries an AbgabetiereList block with a resolved (possibly empty) animals array + var abg = pages.Single(p => p.GetProperty("slug").GetString() == "abgabetiere"); + var listBlock = abg.GetProperty("blocks").EnumerateArray() + .Single(b => b.GetProperty("type").GetString() == "AbgabetiereList"); + Assert.Equal("auto", listBlock.GetProperty("data").GetProperty("mode").GetString()); + Assert.Equal(JsonValueKind.Array, listBlock.GetProperty("data").GetProperty("animals").ValueKind); + } + + [Fact] + public async Task Abgabetiere_resolves_ForSale_animals_with_becken_group() + { + // a Becken + a ForSale gerbil in it + var encResp = await _client.PostAsJsonAsync("/enclosures", new { name = "Verkaufsbecken" }); + var encId = JsonDocument.Parse(await encResp.Content.ReadAsStringAsync()).RootElement.GetProperty("id").GetString(); + await _client.PostAsJsonAsync("/gerbils", new { name = "Verkaufsmaus", gender = "female", status = "ForSale", enclosureId = encId }); + // a non-ForSale gerbil must NOT appear + await _client.PostAsJsonAsync("/gerbils", new { name = "Bleibtmaus", gender = "male", status = "Active" }); + + var doc = JsonDocument.Parse(await _client.GetStringAsync("/api/site-snapshot")); + var animals = doc.RootElement.GetProperty("pages").EnumerateArray() + .Single(p => p.GetProperty("slug").GetString() == "abgabetiere") + .GetProperty("blocks").EnumerateArray() + .Single(b => b.GetProperty("type").GetString() == "AbgabetiereList") + .GetProperty("data").GetProperty("animals").EnumerateArray().ToList(); + + var sale = animals.SingleOrDefault(a => a.GetProperty("name").GetString() == "Verkaufsmaus"); + Assert.Equal(JsonValueKind.Object, sale.ValueKind); + Assert.Equal("Verkaufsbecken", sale.GetProperty("group").GetString()); + Assert.Equal(JsonValueKind.Array, sale.GetProperty("photos").ValueKind); + Assert.DoesNotContain(animals, a => a.GetProperty("name").GetString() == "Bleibtmaus"); + } + + [Fact] + public async Task Block_crud_and_reorder() + { + // create a page + two blocks + var pageResp = await _client.PostAsJsonAsync("/api/pages", new { slug = "test-page", title = "Testseite" }); + Assert.Equal(HttpStatusCode.Created, pageResp.StatusCode); + var pageId = JsonDocument.Parse(await pageResp.Content.ReadAsStringAsync()).RootElement.GetProperty("id").GetString(); + + async Task AddBlock(string type, object data) => + JsonDocument.Parse(await (await _client.PostAsJsonAsync($"/api/pages/{pageId}/blocks", new { type, data })) + .Content.ReadAsStringAsync()).RootElement.GetProperty("id").GetGuid(); + + var b1 = await AddBlock("Heading", new { text = "Erstes", level = 2 }); + var b2 = await AddBlock("RichText", new { markdown = "**hallo**" }); + + // reorder: b2 before b1 + var reorder = await _client.PutAsJsonAsync($"/api/pages/{pageId}/blocks/order", new { blockIds = new[] { b2, b1 } }); + Assert.Equal(HttpStatusCode.NoContent, reorder.StatusCode); + + var blocks = JsonDocument.Parse(await _client.GetStringAsync("/api/pages/test-page")) + .RootElement.GetProperty("blocks").EnumerateArray().ToList(); + Assert.Equal(b2.ToString(), blocks[0].GetProperty("id").GetString()); + Assert.Equal(b1.ToString(), blocks[1].GetProperty("id").GetString()); + // RichText markdown round-trips inside data + Assert.Equal("**hallo**", blocks[0].GetProperty("data").GetProperty("markdown").GetString()); + } +}