using Jiaowu.Api.Domain.Academic;
using Jiaowu.Api.Infrastructure.Scheduling;

namespace Jiaowu.Api.Tests;

public sealed class ScheduleConflictTests
{
    [Fact]
    public void Same_classroom_and_overlapping_weeks_conflict()
    {
        var classroomId = Guid.NewGuid();
        var first = Entry(classroomId, WeekPattern.All, new TeachingTask
        {
            TaskNumber = "TASK-1",
            Name = "教学班一"
        });
        var second = Entry(classroomId, WeekPattern.All, new TeachingTask
        {
            TaskNumber = "TASK-2",
            Name = "教学班二"
        });

        Assert.True(ScheduleConflictDetector.TimeOverlaps(first, second));
        Assert.Equal("教室", ScheduleConflictDetector.ConflictReason(first, second));
    }

    [Fact]
    public void Odd_and_even_week_arrangements_do_not_overlap()
    {
        var first = Entry(Guid.NewGuid(), WeekPattern.Odd, new TeachingTask
        {
            TaskNumber = "TASK-1",
            Name = "教学班一"
        });
        var second = Entry(Guid.NewGuid(), WeekPattern.Even, new TeachingTask
        {
            TaskNumber = "TASK-2",
            Name = "教学班二"
        });

        Assert.False(ScheduleConflictDetector.TimeOverlaps(first, second));
    }

    [Fact]
    public void Shared_teacher_conflicts_across_different_classrooms()
    {
        var teacherId = Guid.NewGuid();
        var firstTask = new TeachingTask
        {
            TaskNumber = "TASK-1",
            Name = "教学班一",
            Teachers = [new TeachingTaskTeacher { TeacherId = teacherId }]
        };
        var secondTask = new TeachingTask
        {
            TaskNumber = "TASK-2",
            Name = "教学班二",
            Teachers = [new TeachingTaskTeacher { TeacherId = teacherId }]
        };
        var first = Entry(Guid.NewGuid(), WeekPattern.All, firstTask);
        var second = Entry(Guid.NewGuid(), WeekPattern.All, secondTask);

        Assert.Equal("教师", ScheduleConflictDetector.ConflictReason(first, second));
    }

    [Fact]
    public void Two_roomless_courses_do_not_create_a_classroom_conflict()
    {
        var first = Entry(null, WeekPattern.All, new TeachingTask
        {
            TaskNumber = "ONLINE-1",
            Name = "线上课程一"
        });
        var second = Entry(null, WeekPattern.All, new TeachingTask
        {
            TaskNumber = "ONLINE-2",
            Name = "线上课程二"
        });

        Assert.True(ScheduleConflictDetector.TimeOverlaps(first, second));
        Assert.Null(ScheduleConflictDetector.ConflictReason(first, second));
    }

    private static ScheduleEntry Entry(
        Guid? classroomId,
        WeekPattern weekPattern,
        TeachingTask task) =>
        new()
        {
            ClassroomId = classroomId,
            DayOfWeek = 1,
            StartPeriod = 1,
            PeriodCount = 2,
            StartWeek = 1,
            EndWeek = 16,
            WeekPattern = weekPattern,
            TeachingTask = task
        };
}
