using TeleWave.Application.Metadata;
using TeleWave.Domain.Library;
using Xunit;

namespace TeleWave.Application.Tests.Metadata;

public class ContentRatingTests
{
    [Theory]
    [InlineData("G", ShowAudience.G)]
    [InlineData("PG", ShowAudience.Pg)]
    [InlineData("PG-13", ShowAudience.Pg13)]
    [InlineData("R", ShowAudience.R)]
    [InlineData("NC-17", ShowAudience.Nc17)]
    public void Parse_Mpaa(string value, ShowAudience expected) =>
        Assert.Equal(expected, ContentRating.Parse(value));

    [Theory]
    [InlineData("TV-Y", ShowAudience.G)]
    [InlineData("TV-Y7", ShowAudience.G)]
    [InlineData("TV-G", ShowAudience.G)]
    [InlineData("TV-PG", ShowAudience.Pg)]
    [InlineData("TV-14", ShowAudience.Pg13)]
    [InlineData("TV-MA", ShowAudience.R)]
    public void Parse_TvGuidelines_MapsToNearest(string value, ShowAudience expected) =>
        Assert.Equal(expected, ContentRating.Parse(value));

    [Theory]
    [InlineData("0+", ShowAudience.G)]
    [InlineData("6+", ShowAudience.G)]
    [InlineData("12+", ShowAudience.Pg)]
    [InlineData("16+", ShowAudience.Pg13)]
    [InlineData("18+", ShowAudience.R)]
    public void Parse_RussianMarking_MapsApproximately(string value, ShowAudience expected) =>
        Assert.Equal(expected, ContentRating.Parse(value));

    [Theory]
    [InlineData("M", ShowAudience.Pg)]
    [InlineData("GP", ShowAudience.Pg)]
    [InlineData("X", ShowAudience.Nc17)]
    public void Parse_HistoricalCodes(string value, ShowAudience expected) =>
        Assert.Equal(expected, ContentRating.Parse(value));

    [Theory]
    [InlineData("pg-13", ShowAudience.Pg13)]
    [InlineData("  R  ", ShowAudience.R)]
    public void Parse_IgnoresCaseAndPadding(string value, ShowAudience expected) =>
        Assert.Equal(expected, ContentRating.Parse(value));

    [Theory]
    [InlineData(null)]
    [InlineData("")]
    [InlineData("   ")]
    [InlineData("N/A")]
    [InlineData("Not Rated")]
    [InlineData("Unrated")]
    [InlineData("Approved")]
    [InlineData("Passed")]
    // Голые числа — это немецкая FSK и французская шкала, которых мы не поддерживаем: «16» там
    // означает не то же, что российское «16+», и принимать их за него нельзя.
    [InlineData("16")]
    [InlineData("12")]
    [InlineData("какая-то ерунда")]
    public void Parse_UnknownOrAbsent_IsNull(string? value)
    {
        // Незнакомое значение не должно превращаться в догадку: по нему шоу попало бы в детский эфир
        // непроверенным. Отдельно проверяем «Approved»/«Passed» — исторические пометки IMDb,
        // означающие «цензуру прошёл», а не «подходит детям».
        Assert.Null(ContentRating.Parse(value));
    }
}
