You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

176 lines
7.3 KiB
C#

using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Haoliang.Models.Production;
using Haoliang.Data.Repositories;
namespace Haoliang.Data.Repositories
{
public interface IProgramProductionSummaryRepository : IRepository<ProgramProductionSummary>
{
Task<ProgramProductionSummary> GetByDeviceAndDateAsync(int deviceId, DateTime date);
Task<IEnumerable<ProgramProductionSummary>> GetByDateAsync(DateTime date);
Task<IEnumerable<ProgramProductionSummary>> GetByDeviceAsync(int deviceId);
Task<IEnumerable<ProgramProductionSummary>> GetByProgramAsync(string programName);
Task<ProgramProductionSummary> GetByDeviceAndProgramAsync(int deviceId, string programName);
Task<IEnumerable<ProgramProductionSummary>> GetByDateRangeAsync(DateTime startDate, DateTime endDate);
Task<ProductionSummary> GetTotalProductionAsync(DateTime date);
Task<bool> UpdateProductionSummaryAsync(int deviceId, string programName, int quantity);
Task ArchiveProductionSummariesAsync(int daysToKeep = 90);
}
public class ProgramProductionSummaryRepository : Repository<ProgramProductionSummary>, IProgramProductionSummaryRepository
{
private readonly CNCDbContext _context;
public ProgramProductionSummaryRepository(CNCDbContext context) : base(context)
{
_context = context;
}
public async Task<ProgramProductionSummary> GetByDeviceAndDateAsync(int deviceId, DateTime date)
{
var startOfDay = date.Date;
var endOfDay = startOfDay.AddDays(1);
return await _context.ProgramProductionSummaries
.FirstOrDefaultAsync(p => p.DeviceId == deviceId &&
p.ProductionDate >= startOfDay &&
p.ProductionDate < endOfDay);
}
public async Task<IEnumerable<ProgramProductionSummary>> GetByDateAsync(DateTime date)
{
var startOfDay = date.Date;
var endOfDay = startOfDay.AddDays(1);
return await _context.ProgramProductionSummaries
.Where(p => p.ProductionDate >= startOfDay &&
p.ProductionDate < endOfDay)
.OrderBy(p => p.DeviceName)
.ThenBy(p => p.ProgramName)
.ToListAsync();
}
public async Task<IEnumerable<ProgramProductionSummary>> GetByDeviceAsync(int deviceId)
{
return await _context.ProgramProductionSummaries
.Where(p => p.DeviceId == deviceId)
.OrderByDescending(p => p.ProductionDate)
.ThenBy(p => p.ProgramName)
.ToListAsync();
}
public async Task<IEnumerable<ProgramProductionSummary>> GetByProgramAsync(string programName)
{
return await _context.ProgramProductionSummaries
.Where(p => p.ProgramName == programName)
.OrderByDescending(p => p.ProductionDate)
.ThenBy(p => p.DeviceName)
.ToListAsync();
}
public async Task<ProgramProductionSummary> GetByDeviceAndProgramAsync(int deviceId, string programName)
{
var today = DateTime.Today;
return await _context.ProgramProductionSummaries
.FirstOrDefaultAsync(p => p.DeviceId == deviceId &&
p.ProgramName == programName &&
p.ProductionDate == today);
}
public async Task<IEnumerable<ProgramProductionSummary>> GetByDateRangeAsync(DateTime startDate, DateTime endDate)
{
return await _context.ProgramProductionSummaries
.Where(p => p.ProductionDate >= startDate &&
p.ProductionDate <= endDate)
.OrderBy(p => p.ProductionDate)
.ThenBy(p => p.DeviceName)
.ThenBy(p => p.ProgramName)
.ToListAsync();
}
public async Task<ProductionSummary> GetTotalProductionAsync(DateTime date)
{
var summaries = await GetByDateAsync(date);
var totalSummary = new ProductionSummary
{
ProductionDate = date,
TotalDevices = summaries.Select(s => s.DeviceId).Distinct().Count(),
TotalPrograms = summaries.Count(),
TotalQuantity = summaries.Sum(s => s.Quantity),
AverageQuantity = summaries.Any() ? summaries.Average(s => s.Quantity) : 0,
DeviceSummaries = summaries.GroupBy(s => s.DeviceId)
.Select(g => new DeviceProductionSummary
{
DeviceId = g.Key,
DeviceName = g.FirstOrDefault()?.DeviceName ?? "",
TotalQuantity = g.Sum(s => s.Quantity),
ProgramCount = g.Count(),
Programs = g.Select(s => new ProgramSummary
{
ProgramName = s.ProgramName,
Quantity = s.Quantity,
Percentage = g.Sum(s => s.Quantity) > 0 ?
(decimal)s.Quantity / g.Sum(s => s.Quantity) * 100 : 0
}).ToList()
}).ToList()
};
return totalSummary;
}
public async Task<bool> UpdateProductionSummaryAsync(int deviceId, string programName, int quantity)
{
var today = DateTime.Today;
var summary = await GetByDeviceAndProgramAsync(deviceId, programName);
if (summary != null)
{
// Update existing summary
summary.Quantity += quantity;
summary.UpdatedAt = DateTime.Now;
_context.ProgramProductionSummaries.Update(summary);
}
else
{
// Create new summary
var device = await _context.Devices.FindAsync(deviceId);
summary = new ProgramProductionSummary
{
DeviceId = deviceId,
DeviceName = device?.DeviceName ?? "",
ProgramName = programName,
Quantity = quantity,
ProductionDate = today,
CreatedAt = DateTime.Now,
UpdatedAt = DateTime.Now
};
_context.ProgramProductionSummaries.Add(summary);
}
await SaveAsync();
return true;
}
public async Task ArchiveProductionSummariesAsync(int daysToKeep = 90)
{
var cutoffDate = DateTime.Today.AddDays(-daysToKeep);
var summariesToArchive = await _context.ProgramProductionSummaries
.Where(p => p.ProductionDate < cutoffDate)
.ToListAsync();
if (summariesToArchive.Any())
{
// In a real implementation, you would move these to an archive table
_context.ProgramProductionSummaries.RemoveRange(summariesToArchive);
await SaveAsync();
}
}
}
}