156 lines
5.7 KiB
C#
156 lines
5.7 KiB
C#
using CPRNIMS.Domain.Contracts.Inventory;
|
|
using CPRNIMS.Infrastructure.Database;
|
|
using CPRNIMS.Infrastructure.Dto.Inventory;
|
|
using CPRNIMS.Infrastructure.Dto.Inventory.Request;
|
|
using CPRNIMS.Infrastructure.Dto.Inventory.Response;
|
|
using CPRNIMS.Infrastructure.Entities.Inventory;
|
|
using Microsoft.EntityFrameworkCore;
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Text;
|
|
using System.Threading.Tasks;
|
|
|
|
namespace CPRNIMS.Domain.Services.Inventory
|
|
{
|
|
public class MRS : IMRS
|
|
{
|
|
private readonly NonInventoryDbContext _db;
|
|
public MRS(NonInventoryDbContext db) => _db = db;
|
|
|
|
public async Task ApproveAsync(long mrsId, string approvedBy)
|
|
{
|
|
var rms = await _db.MRS.FindAsync(mrsId)
|
|
?? throw new InvalidOperationException("MRS not found.");
|
|
|
|
if (rms.Status != 0)
|
|
throw new InvalidOperationException("Only Draft MRS records can be approved.");
|
|
|
|
rms.Status = 1; // Approved
|
|
rms.ApprovedBy = approvedBy;
|
|
rms.ApprovedDate = DateTime.Now;
|
|
|
|
await _db.SaveChangesAsync();
|
|
}
|
|
|
|
public async Task<Infrastructure.Entities.Inventory.MRS> CreateAsync(CreateMRSRequest dto, string createdBy)
|
|
{
|
|
var ris = await _db.RIS
|
|
.Include(r => r.Inventory)
|
|
.FirstOrDefaultAsync(r => r.RISId == dto.RISId)
|
|
?? throw new InvalidOperationException("Referenced RIS not found.");
|
|
|
|
if (dto.QtyReturned > ris.QtyIssued)
|
|
throw new InvalidOperationException(
|
|
$"Cannot return more than issued. Issued: {ris.QtyIssued}.");
|
|
|
|
var mrsNo = await GenerateMRSNoAsync();
|
|
|
|
var mrs = new Infrastructure.Entities.Inventory.MRS
|
|
{
|
|
MRSNo = mrsNo,
|
|
RISId = dto.RISId,
|
|
InventoryId = ris.InventoryId,
|
|
ReturnedBy = dto.ReturnedBy,
|
|
QtyReturned = dto.QtyReturned,
|
|
Condition = dto.Condition,
|
|
Remarks = dto.Remarks,
|
|
Status = 0,
|
|
CreatedBy = createdBy,
|
|
CreatedDate = DateTime.Now
|
|
};
|
|
_db.MRS.Add(mrs);
|
|
|
|
var inventory = ris.Inventory;
|
|
inventory.QtyOut = Math.Max(0m, inventory.QtyOut - dto.QtyReturned);
|
|
|
|
inventory.QtyOnHand = inventory.QtyIn - inventory.QtyOut;
|
|
|
|
var trans = await _db.InventTrans
|
|
.FirstOrDefaultAsync(t => t.InventoryId == ris.InventoryId && t.IsActive == true)!;
|
|
|
|
_db.InventTransDetails.Add(new InventTransDetail
|
|
{
|
|
InventTransId = trans.InventTransId,
|
|
TransTypeId = 6,
|
|
QtyIn = dto.QtyReturned,
|
|
CreatedDate = DateTime.Now,
|
|
Remarks = $"MRS: {mrsNo} — return from MRS: {ris.RISNo}",
|
|
IsActive = true
|
|
});
|
|
|
|
await _db.SaveChangesAsync();
|
|
return mrs;
|
|
}
|
|
|
|
public async Task<Infrastructure.Entities.Inventory.MRS?> GetByIdAsync(long mrsId)
|
|
|
|
=> await _db.MRS
|
|
.Include(r => r.Inventory)
|
|
.Include(r => r.RIS)
|
|
.FirstOrDefaultAsync(r => r.RISId == mrsId);
|
|
|
|
public async Task<MRSPagedResult> GetPagedAsync(MRSFilterDto filter)
|
|
{
|
|
var q = _db.MRS
|
|
.Include(m => m.RIS)
|
|
.Include(m => m.Inventory)
|
|
.AsQueryable();
|
|
|
|
if (!string.IsNullOrWhiteSpace(filter.SearchMRSNo))
|
|
q = q.Where(m => m.MRSNo.Contains(filter.SearchMRSNo));
|
|
|
|
if (filter.RISId.HasValue)
|
|
q = q.Where(m => m.RISId == filter.RISId.Value);
|
|
|
|
if (filter.Status.HasValue)
|
|
q = q.Where(m => m.Status == filter.Status.Value);
|
|
|
|
if (filter.DateFrom.HasValue)
|
|
q = q.Where(m => m.CreatedDate >= filter.DateFrom.Value);
|
|
|
|
if (filter.DateTo.HasValue)
|
|
q = q.Where(m => m.CreatedDate <= filter.DateTo.Value.AddDays(1));
|
|
|
|
var total = await q.CountAsync();
|
|
|
|
var data = await q
|
|
.OrderByDescending(m => m.CreatedDate)
|
|
.Skip((filter.Page - 1) * filter.PageSize)
|
|
.Take(filter.PageSize)
|
|
.Select(m => new MRSResponse
|
|
{
|
|
MRSId = m.MRSId,
|
|
MRSNo = m.MRSNo,
|
|
RISId = m.RISId,
|
|
RISNo = m.RIS.RISNo,
|
|
InventoryId = m.InventoryId,
|
|
ItemName = m.Inventory.InventTrans
|
|
.SelectMany(t => t.InventTransDetails)
|
|
.Select(d => d.PRDetails != null ? d.PRDetails.ItemName : "—")
|
|
.FirstOrDefault() ?? "—",
|
|
ReturnedBy = m.ReturnedBy,
|
|
QtyReturned = m.QtyReturned,
|
|
Condition = m.Condition,
|
|
Remarks = m.Remarks,
|
|
Status = m.Status,
|
|
CreatedBy = m.CreatedBy,
|
|
CreatedDate = m.CreatedDate,
|
|
ApprovedBy = m.ApprovedBy,
|
|
ApprovedDate = m.ApprovedDate
|
|
})
|
|
.ToListAsync();
|
|
|
|
return new MRSPagedResult { Data = data, RecordsTotal = total };
|
|
}
|
|
|
|
private async Task<string> GenerateMRSNoAsync()
|
|
{
|
|
var year = DateTime.Now.Year;
|
|
var month = DateTime.Now.Month.ToString("D2");
|
|
var count = await _db.MRS.CountAsync(m => m.CreatedDate.Year == year) + 1;
|
|
return $"MRS-{year}{month}-{count:D4}";
|
|
}
|
|
}
|
|
}
|