using System.Net;
using System.Net.Http.Json;
using System.Text.RegularExpressions;
using GerbilManagerWebAPI.SaleAd;

namespace GerbilManager.Tests;

/// <summary>FEAT-14a: Charakterbogen (traits + note) persists/round-trips, and the
/// sale-ad prompt includes the character info.</summary>
public class GerbilCharacterTests : IClassFixture<ApiFactory>
{
    private readonly HttpClient _client;

    public GerbilCharacterTests(ApiFactory factory) => _client = factory.CreateClient();

    [Fact]
    public async Task CharacterTraits_and_note_round_trip()
    {
        var create = await _client.PostAsync("/gerbils", JsonContent.Create(new
        {
            name = "Charakter Test",
            gender = "female",
            characterTraits = new[] { "zutraulich", "handzahm" },
            characterNote = "sehr aktiv und neugierig",
        }));
        Assert.Equal(HttpStatusCode.Created, create.StatusCode);

        var created = await create.Content.ReadAsStringAsync();
        // POST response is the created GerbilDto — traits serialise straight back
        Assert.Contains("zutraulich", created);
        Assert.Contains("handzahm", created);
        Assert.Contains("sehr aktiv und neugierig", created);

        var id = Regex.Match(created, "\"id\":\"([^\"]+)\"").Groups[1].Value;
        Assert.NotEqual("", id);

        // re-read from the DB to prove persistence (not just echo)
        var fetched = await _client.GetStringAsync($"/gerbils/{id}");
        Assert.Contains("zutraulich", fetched);
        Assert.Contains("handzahm", fetched);
        Assert.Contains("sehr aktiv und neugierig", fetched);
    }

    [Fact]
    public async Task Omitting_traits_defaults_to_empty_list()
    {
        var create = await _client.PostAsync("/gerbils", JsonContent.Create(new
        {
            name = "Ohne Charakter",
            gender = "male",
        }));
        Assert.Equal(HttpStatusCode.Created, create.StatusCode);
        var body = await create.Content.ReadAsStringAsync();
        Assert.Contains("\"characterTraits\":[]", body.Replace(" ", ""));
    }

    [Fact]
    public void SaleAd_prompt_includes_traits_and_note()
    {
        var request = new SaleAdRequest(
            Animals: new List<SaleAdAnimal>
            {
                new("Bella", "Agouti", "2025-01-15", "verspielt",
                    Traits: new List<string> { "zutraulich", "handzahm" },
                    CharacterNote: "liebt Sonnenblumenkerne"),
            },
            StatusLine: "FREI",
            Hints: "");

        var prompt = SaleAdPromptBuilder.BuildUserPrompt(request);

        Assert.Contains("Charakter: zutraulich, handzahm", prompt);
        Assert.Contains("liebt Sonnenblumenkerne", prompt);
    }
}
