using Core.Entities;
using FuzzySharp;

namespace Core.Parsers;

public class StudentEventRankingParser : CsvParserBase
{
    public StudentEventRankingParser(FileSystemInfo csvFile, bool ignoreBlankLines = true) : base(csvFile, ignoreBlankLines)
    {
    }

    public StudentEventRanking[] Parse(ICollection<Student> students, ICollection<EventDefinition> events)
    { 
        var rankings = new List<StudentEventRanking>();

        CsvReader.Read();
        CsvReader.ReadHeader();

		while (CsvReader.Read())
		{
            var name = CsvReader.GetField("Student Name");
            if (string.IsNullOrEmpty(name))
                continue;

            var student = students.FirstOrDefault(s => Fuzz.Ratio(s.FirstNameLastName, name) > 90);
            if (student == null)
                continue;
            

            var competitiveEvents = new List<EventDefinition>(6);

            for (var i = 1; i <= 6; i++)
            {
	            var eventName = CsvReader.GetField(i.ToString());
	            if (string.IsNullOrEmpty(eventName) || eventName == "") continue;

	            eventName = eventName.Trim();

	            if (eventName == "I&I")
		            eventName = "Inventions & Innovations";
	            if (eventName == "Med Tech")
		            eventName = "Medical Technology";
	            if (eventName.StartsWith("Challenging Tech"))
		            eventName = "Challenging Technology Issues";

                var matches =
	                (from e in events
	                let rat = Fuzz.Ratio(e.Name, eventName)
	                where rat > 90
	                orderby rat descending 
	                select e).ToList();

                if (!matches.Any())
                {
	                matches =
		                (from e in events
			                where e.Name.StartsWith(eventName)
			                select e).ToList();
                }

                var competitiveEvent = matches.FirstOrDefault();
                if (competitiveEvent == null)
                {
					
	                //todo: throw new ArgumentException($"Event named '{eventName}' not found");
	                continue;
                }

                rankings.Add(new StudentEventRanking{
                    Student = student, EventDefinition = competitiveEvent,
                    Rank = i});
            }
		}

        return rankings.ToArray();
    }
}