using Elwig.Helpers;
using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations.Schema;
using System.Linq;

namespace Elwig.Models {
    [Table("delivery"), PrimaryKey("Year", "DId"), Index("DateString", "ZwstId", "LNr", IsUnique = true), Index("LsNr", IsUnique = true)]
    public class Delivery {
        [Column("year")]
        public int Year { get; set; }

        [Column("did")]
        public int DId { get; set; }

        [Column("date")]
        public string DateString { get; set; }

        [NotMapped]
        public DateOnly Date {
            get {
                return DateOnly.ParseExact(DateString, "yyyy-MM-dd");
            }
            set {
                DateString = value.ToString("yyyy-MM-dd");
            }
        }

        [Column("time")]
        public string? TimeString { get; set; }

        [NotMapped]
        public TimeOnly? Time {
            get {
                return (TimeString == null) ? null : TimeOnly.ParseExact(TimeString, "HH:mm:ss");
            }
            set {
                TimeString = value?.ToString("HH:mm:ss");
            }
        }

        [NotMapped]
        public DateTime DateTime {
            get {
                return Date.ToDateTime(Time ?? TimeOnly.MinValue);
            }
            set {
                Date = DateOnly.FromDateTime(value);
                Time = TimeOnly.FromDateTime(value);
            }
        }

        [Column("zwstid")]
        public string ZwstId { get; set; }

        [ForeignKey("ZwstId")]
        public virtual Branch Branch { get; private set; }

        [Column("lnr")]
        public int LNr { get; set; }

        [Column("lsnr")]
        public string LsNr { get; set; }

        [Column("mgnr")]
        public int MgNr { get; set; }

        [ForeignKey("MgNr")]
        public virtual Member Member { get; private set; }

        [Column("comment")]
        public string? Comment { get; set; }

        [InverseProperty("Delivery")]
        public virtual ISet<DeliveryPart> Parts { get; private set; }

        public int Weight => Parts.Select(p => p.Weight).Sum();

        public IEnumerable<string> SortIds => Parts
            .GroupBy(p => p.SortId)
            .OrderByDescending(g => g.Select(p => p.Weight).Sum())
            .Select(g => g.Select(p => p.SortId).First());

        public string SortIdString => string.Join(", ", SortIds);

        public int SearchScore(IEnumerable<string> keywords) {
            var list = new string?[] {
                LsNr, Year.ToString(), Date.ToString("dd.MM.yyyy"), Time?.ToString("HH:ss"),
                MgNr.ToString(), Member.FamilyName, Member.MiddleName, Member.GivenName, Member.BillingAddress?.Name,
                Comment
            }.ToList();
            list.AddRange(Parts.Select(p => p.SortId).Distinct());
            list.AddRange(Parts.Select(p => p.Comment).Distinct());
            return Utils.GetSearchScore(list, keywords);
        }
    }
}