using Elwig.Documents; using Elwig.Helpers; using Elwig.Models.Entities; using Microsoft.EntityFrameworkCore; using System.Collections.Generic; using System.ComponentModel.DataAnnotations.Schema; using System.Data.Entity.Core.Common.CommandTrees.ExpressionBuilder; using System.Linq; using System.Threading.Tasks; namespace Elwig.Models.Dtos { public class PaymentVariantSummaryData : DataTable { private static readonly (string, string, string?, int?)[] FieldNames = [ ("Type", "Typ", null, 10), ("Variety", "Sorte", null, 40), ("Attribute", "Attribut", null, 20), ("Cultivation", "Bewirt.", null, 20), ("QualityLevel", "Qualitätsstufe", null, 30), ("Oe", "Gradation", "°Oe", 20), ("Ungeb", "ungebunden", "kg|€/kg|€/kg", 60), ("LowGeb", "attributlos gebunden", "kg|€/kg|€/kg", 60), ("Geb", "gebunden", "kg|€/kg|€/kg", 60), ("Amount", "Gesamt", "€", 25), ]; public record struct PaymentRow( string Type, string Variety, string? Attribute, string? Cultivation, string QualityLevel, double Oe, (int Weight, decimal? MinPrice, decimal? MaxPrice) Ungeb, (int Weight, decimal? MinPrice, decimal? MaxPrice) LowGeb, (int Weight, decimal? MinPrice, decimal? MaxPrice) Geb, decimal Amount ); public PaymentVariantSummaryData(PaymentVar v, IEnumerable rows) : base($"{PaymentVariantSummary.Name} {v.Year}", $"{PaymentVariantSummary.Name} Lese {v.Year}", v.Name, rows, FieldNames) { } public static async Task ForPaymentVariant(PaymentVar v, DbSet table) { return new(v, (await FromDbSet(table, v.Year, v.AvNr)) .Select(r => new PaymentRow(r.Type, r.Variety, r.Attribute, r.Cultivation, r.QualityLevel, r.Oe, (r.WeightUngeb, r.MinPriceUngeb != null ? Utils.DecFromDb(r.MinPriceUngeb.Value, v.Season.Precision) : null, r.MaxPriceUngeb != null ? Utils.DecFromDb(r.MaxPriceUngeb.Value, v.Season.Precision) : null), (r.WeightLowGeb, r.MinPriceLowGeb != null ? Utils.DecFromDb(r.MinPriceLowGeb.Value, v.Season.Precision) : null, r.MaxPriceLowGeb != null ? Utils.DecFromDb(r.MaxPriceLowGeb.Value, v.Season.Precision) : null), (r.WeightGeb, r.MinPriceGeb != null ? Utils.DecFromDb(r.MinPriceGeb.Value, v.Season.Precision) : null, r.MaxPriceGeb != null ? Utils.DecFromDb(r.MaxPriceGeb.Value, v.Season.Precision) : null), Utils.DecFromDb(r.Amount, v.Season.Precision))) .ToArray()); } private static async Task> FromDbSet(DbSet table, int year, int avnr) { return await table.FromSql($""" SELECT v.type AS type, v.name AS variety, a.name AS attribute, c.name AS cultivation, q.name AS quality_level, ROUND(kmw * (4.54 + 0.022 * kmw)) AS oe, SUM(IIF(w.discr = '_', w.value, 0)) AS weight_ungeb, MIN(IIF(w.discr = '_', b.price, NULL)) AS min_price_ungeb, MAX(IIF(w.discr = '_', b.price, NULL)) AS max_price_ungeb, SUM(IIF(w.discr NOT IN (COALESCE(p.attrid, ''), '_'), w.value, 0)) AS weight_lowgeb, MIN(IIF(w.discr NOT IN (COALESCE(p.attrid, ''), '_'), b.price, NULL)) AS min_price_lowgeb, MAX(IIF(w.discr NOT IN (COALESCE(p.attrid, ''), '_'), b.price, NULL)) AS max_price_lowgeb, SUM(IIF(w.discr = COALESCE(p.attrid, ''), w.value, 0)) AS weight_geb, MIN(IIF(w.discr = COALESCE(p.attrid, ''), b.price, NULL)) AS min_price_geb, MAX(IIF(w.discr = COALESCE(p.attrid, ''), b.price, NULL)) AS max_price_geb, SUM(b.amount) AS amount FROM payment_delivery_part_bucket b LEFT JOIN delivery_part_bucket w ON (w.year, w.did, w.dpnr, w.bktnr) = (b.year, b.did, b.dpnr, b.bktnr) LEFT JOIN delivery_part p ON (p.year, p.did, p.dpnr) = (b.year, b.did, b.dpnr) LEFT JOIN wine_variety v ON v.sortid = p.sortid LEFT JOIN wine_attribute a ON a.attrid = p.attrid LEFT JOIN wine_cultivation c ON c.cultid = p.cultid LEFT JOIN wine_quality_level q ON q.qualid = p.qualid WHERE p.year = {year} AND b.avnr = {avnr} GROUP BY variety, attribute, cultivation, q.min_kmw, oe ORDER BY variety, attribute, cultivation, q.min_kmw, oe """).ToListAsync(); } } [Keyless] public class PaymentVariantSummaryRow { [Column("type")] public required string Type { get; set; } [Column("variety")] public required string Variety { get; set; } [Column("attribute")] public string? Attribute { get; set; } [Column("cultivation")] public string? Cultivation { get; set; } [Column("quality_level")] public required string QualityLevel { get; set; } [Column("oe")] public double Oe { get; set; } [Column("weight_ungeb")] public int WeightUngeb { get; set; } [Column("min_price_ungeb")] public long? MinPriceUngeb { get; set; } [Column("max_price_ungeb")] public long? MaxPriceUngeb { get; set; } [Column("weight_lowgeb")] public int WeightLowGeb { get; set; } [Column("min_price_lowgeb")] public long? MinPriceLowGeb { get; set; } [Column("max_price_lowgeb")] public long? MaxPriceLowGeb { get; set; } [Column("weight_geb")] public int WeightGeb { get; set; } [Column("min_price_geb")] public long? MinPriceGeb { get; set; } [Column("max_price_geb")] public long? MaxPriceGeb { get; set; } [Column("amount")] public long Amount { get; set; } } }