using CPRNIMS.Domain.Contracts.Items; using CPRNIMS.Infrastructure.Database; using CPRNIMS.Infrastructure.Dto.Items; using CPRNIMS.Infrastructure.Entities.Account; using CPRNIMS.Infrastructure.Entities.Items; using CPRNIMS.Infrastructure.Entities.Purchasing; using CPRNIMS.Infrastructure.Models.Common; using Microsoft.Data.SqlClient; using Microsoft.EntityFrameworkCore; using System.Data; using System.Linq; using System.Text; using System.Threading.Tasks; namespace CPRNIMS.Domain.Services.Items { public class Item : IItem { private readonly NonInventoryDbContext _dbContext; public Item(NonInventoryDbContext dbContext) { _dbContext = dbContext; } public async Task PostPutItem(ItemCodeDto itemDto) { var messCodeParam = new SqlParameter("@MessCode", SqlDbType.TinyInt) { Direction = ParameterDirection.Output }; var messageParam = new SqlParameter("@Message", SqlDbType.VarChar, 500) { Direction = ParameterDirection.Output }; var itemCodeParam = new SqlParameter("@ItemCode", SqlDbType.BigInt) { Direction = ParameterDirection.Output }; await _dbContext.Database.ExecuteSqlRawAsync( "EXEC PostPutItem @ItemCodeId, @ItemName, @ItemDescription, @ItemCategoryId, @Status, @UserId, " + "@ItemCode OUTPUT, @MessCode OUTPUT, @Message OUTPUT", new SqlParameter("@ItemCodeId", itemDto.ItemCodeId != null ? itemDto.ItemCodeId : 0L), new SqlParameter("@ItemName", itemDto.ItemName ?? (object)DBNull.Value), new SqlParameter("@ItemDescription", itemDto.ItemDescription ?? (object)DBNull.Value), new SqlParameter("@ItemCategoryId", itemDto.ItemCategoryId), new SqlParameter("@Status", itemDto.Status != null ? itemDto.Status : 4), new SqlParameter("@UserId", itemDto.UserId ?? (object)DBNull.Value), itemCodeParam, messCodeParam, messageParam ); var messCode = (byte)messCodeParam.Value; var message = messageParam.Value?.ToString(); var itemCode = itemCodeParam.Value != DBNull.Value ? (long?)itemCodeParam.Value : null; return new ItemCodeDto { ItemCodeId = Convert.ToInt64(itemCode), ItemName = itemDto.ItemName, ItemDescription = itemDto.ItemDescription, ItemCategoryId = itemDto.ItemCategoryId, Status = itemDto.Status, UserId = itemDto.UserId }; } public async Task PutItemDetail(ItemDto itemDto) { await _dbContext.Database .ExecuteSqlRawAsync($"EXEC PutItemDetail @ItemCodeId,@ItemLocalId,@ItemTypeId,@UOMId,@ItemColorId,@IsActive," + $"@UserId,@ItemNo,@PRTypeId,@PackagingTypeId,@Qty,@ItemAttachId,@ItemAttachPath,@IsCommon,@ItemCategoryId," + $"@RequestTypeId,@ItemName,@ItemDescription,@IsMDLD", new SqlParameter("@ItemCodeId", itemDto.ItemCodeId != null ? itemDto.ItemCodeId : 0L), new SqlParameter("@ItemLocalId", itemDto.ItemLocalId), new SqlParameter("@ItemTypeId", itemDto.ItemTypeId), new SqlParameter("@UOMId", itemDto.UOMId), new SqlParameter("@ItemColorId", itemDto.ItemColorId), new SqlParameter("@IsActive", itemDto.IsActive), new SqlParameter("@UserId", itemDto.UserId), new SqlParameter("@ItemNo", itemDto.ItemNo), new SqlParameter("@PRTypeId", itemDto.PRTypeId), new SqlParameter("@PackagingTypeId", itemDto.PackagingTypeId), new SqlParameter("@Qty", itemDto.Qty), new SqlParameter("@ItemAttachId", itemDto.ItemAttachId != null ? itemDto.ItemAttachId : 0L), new SqlParameter("@ItemAttachPath", itemDto.ItemAttachPath ?? "N/A"), new SqlParameter("@IsCommon", itemDto.IsCommon), new SqlParameter("@ItemCategoryId", itemDto.ItemCategoryId), new SqlParameter("@RequestTypeId", itemDto.RequestTypeId), new SqlParameter("@ItemName", itemDto.ItemName), new SqlParameter("@ItemDescription", itemDto.ItemDescription), new SqlParameter("@IsMDLD", itemDto.IsMDLD)); return new Infrastructure.Entities.Items.Item(); } public async Task> GetItemLocalization(ItemDto itemDto) { var localizations = await _dbContext.ItemLocalizations .Where(ic => ic.IsActive == true && EF.Functions.Like(ic.ItemLocalName, $"%{itemDto.ItemLocalName}%")) .Take(15) .ToListAsync(); return localizations ?? new List(); } public async Task> GetItemCateg(ItemDto itemDto) { if (itemDto.ItemCategoryId == 0 || itemDto.ItemCategoryId == null) { var categories = await _dbContext.ItemCategories .Where(ic => ic.IsActive == true) .ToListAsync(); return categories ?? new List(); } else { var categories = await _dbContext.ItemCategories .Where(ic => ic.IsActive == true && ic.ItemCategoryId == itemDto.ItemCategoryId) .ToListAsync(); return categories ?? new List(); } } public async Task> GetItemDetail(ItemDto itemDto) { var allItems = await _dbContext.Items .FromSqlRaw($"EXEC GetItemDetail @ItemCodeId,@UserId", new SqlParameter("@ItemCodeId", itemDto.ItemCodeId), new SqlParameter("@UserId", itemDto.UserId)) .ToListAsync(); return allItems ?? new List(); } public async Task> GetItemList(ItemCodeDto dto) { var parameters = new[] { new SqlParameter("@UserId", dto.UserId), new SqlParameter("@SearchItemNo", dto.SearchItemNo ?? ""), new SqlParameter("@SearchItemName", dto.SearchItemName ?? ""), new SqlParameter("@SearchCategory", dto.SearchCategory ?? ""), new SqlParameter("@PageNumber", dto.PageNumber), new SqlParameter("@PageSize", dto.PageSize) }; int totalCount = 0; var items = new List(); var categoryList = new List(); // Use ADO.NET to read two result sets var conn = _dbContext.Database.GetDbConnection(); await conn.OpenAsync(); using var cmd = conn.CreateCommand(); cmd.CommandText = "EXEC GetItemList @UserId, @SearchItemNo,@SearchItemName,@SearchCategory, @PageNumber, @PageSize"; foreach (var p in parameters) cmd.Parameters.Add(p); cmd.CommandTimeout = 60; using var reader = await cmd.ExecuteReaderAsync(); while (await reader.ReadAsync()) categoryList.Add(reader.GetString(0)); await reader.NextResultAsync(); if (await reader.ReadAsync()) totalCount = reader.GetInt32(0); await reader.NextResultAsync(); while (await reader.ReadAsync()) { items.Add(new ItemList { ItemCodeId = Convert.ToInt64(reader["ItemCodeId"]), ItemNo = Convert.ToInt64(reader["ItemNo"]), ItemName = reader["ItemName"]?.ToString(), ItemDescription = reader["ItemDescription"]?.ToString(), ItemCategoryName = reader["ItemCategoryName"]?.ToString(), CartItemCount = Convert.ToInt32(reader["CartItemCount"]) }); } await conn.CloseAsync(); return new PagedResult { Data = items, TotalCount = totalCount, CategoryList= categoryList, PageNumber = dto.PageNumber, PageSize = dto.PageSize }; } public async Task> GetItemColor(ItemDto itemDto) { var colors = await _dbContext.ItemColors .Where(ic => EF.Functions.Like(ic.ItemColorName, $"%{itemDto.ItemColorName}%")) .Take(5) .ToListAsync(); return colors ?? new List(); } public async Task> GetItemUOM(ItemDto itemDto) { var uoms = await _dbContext.UnitOfMessures .Where(ic => ic.IsActive == true && EF.Functions.Like(ic.UOMName, $"%{itemDto.UOMName}%")) .Take(150) .ToListAsync(); return uoms ?? new List(); } public async Task PostPutItemPath(ItemDto itemDto) { var isExist = await _dbContext.ItemAttachements .FirstOrDefaultAsync(ia => ia.IsActive == true && ia.ItemNo == itemDto.ItemNo); if (isExist != null) { isExist.ItemAttachPath = itemDto.ItemAttachPath; await _dbContext.SaveChangesAsync(); return new ItemAttachement(); } else { return new ItemAttachement(); } } public async Task PostPutItemCart(ItemDto itemDto) { await _dbContext.Database .ExecuteSqlRawAsync("EXEC PostPutItemCart @ItemCartId,@ItemNo,@UserId,@UOMId,@ItemColorId,@ItemCategoryId,@PackagingTypeId,@ItemAttachId,@ItemLocalId", new SqlParameter("@ItemCartId", itemDto.ItemCartId != null ? itemDto.ItemCartId : 0L), new SqlParameter("@ItemNo", itemDto.ItemNo != null ? itemDto.ItemNo : 0L), new SqlParameter("@UOMId", itemDto.UOMId), new SqlParameter("@ItemColorId", itemDto.ItemColorId), new SqlParameter("@ItemCategoryId", itemDto.ItemCategoryId), new SqlParameter("@PackagingTypeId", itemDto.PackagingTypeId), new SqlParameter("@ItemAttachId", itemDto.ItemAttachId), new SqlParameter("@UserId", itemDto.UserId), new SqlParameter("@ItemLocalId", itemDto.ItemLocalId)); return new ItemCart(); } public async Task> GetItemCart(ItemDto itemDto) { var allItems = await _dbContext.ItemCarts .FromSqlRaw($"EXEC GetItemCart @UserId,@RequestTypeId,@IsCount", new SqlParameter("@UserId", itemDto.UserId), new SqlParameter("@RequestTypeId", itemDto.RequestTypeId), new SqlParameter("@IsCount", itemDto.IsCount)) .ToListAsync(); return allItems ?? new List(); } public async Task PostPurchRequest(ItemDto itemDto) { var (messCode, message) = OutputParamMessage.CreateOutputParams(); if (itemDto.RequestTypeId == 1)//Internal { itemDto.Status = 2; itemDto.IsApproved = 2; await _dbContext.Database .ExecuteSqlRawAsync("EXEC PostPutReqItems @UserId, @RequestItemId, @ItemNo, @QtyRequest,@Status,@IsApproved,@QtyReceived,@LotId," + "@MessCode OUTPUT, @Message OUTPUT", new SqlParameter("@UserId", itemDto.UserId), new SqlParameter("@ItemNo", itemDto.ItemNo), new SqlParameter("@RequestItemId", itemDto.RequestItemId != null ? itemDto.RequestItemId : 0L), new SqlParameter("@QtyRequest", itemDto.Qty), new SqlParameter("@Status", itemDto.Status), new SqlParameter("@IsApproved", itemDto.IsApproved), new SqlParameter("@QtyReceived", itemDto.QtyReceived), new SqlParameter("@LotId", itemDto.LotId), messCode,message); } else { await _dbContext.Database .ExecuteSqlRawAsync("EXEC PostPurchRequest @ItemCartId, @IsActive, @UserId,@ItemCount," + "@PRNo,@DateNeeded,@Qty,@ChargeTo,@Remarks,@ProjectCodeId,@MessCode OUTPUT, @Message OUTPUT", new SqlParameter("@ItemCartId", itemDto.ItemCartId != null ? itemDto.ItemCartId : 0L), new SqlParameter("@IsActive", 1), new SqlParameter("@UserId", itemDto.UserId), new SqlParameter("@ItemCount", itemDto.ItemCount), new SqlParameter("@PRNo", itemDto.PRNo), new SqlParameter("@DateNeeded", itemDto.DateNeeded), new SqlParameter("@Qty", itemDto.Qty), new SqlParameter("@ChargeTo", itemDto.ChargeTo), new SqlParameter("@Remarks", itemDto.Remarks ?? "N/A"), new SqlParameter("@ProjectCodeId", itemDto.ProjectCodeId), messCode, message); } return new ResponseObject() { messCode= (byte)messCode.Value, message= message.Value.ToString() }; } public async Task PostPutAttachment(AttachmentRequest attach) { var existing = await _dbContext.PRAttachments .FirstOrDefaultAsync(a => a.PRId == attach.PRId); if (existing == null) { var attchmnt = new PRAttachments() { FileName = attach.FileName, OrigFileName = attach.OrigFileName, PRId = attach.PRId }; await _dbContext.PRAttachments.AddAsync(attchmnt); } else { existing.OrigFileName = attach.OrigFileName; existing.FileName = attach.FileName; } await _dbContext.SaveChangesAsync(); } public async Task<(long,long)> GetPRNo() { try { var latestPR = await _dbContext.PRs .Where(ic => ic.PRNo != null) .OrderByDescending(ic => ic.PRNo) .FirstOrDefaultAsync(); if (latestPR != null) return (latestPR.PRNo + 1,latestPR.PRId + 1); else return (0,0); } catch (Exception ex) { throw; } } Task IItem.PostPutItemPath(ItemDto itemDto) { throw new NotImplementedException(); } public async Task > GetDepartment(ItemCodeDto itemCode) { return await _dbContext.Departments .Where(d => d.IsActive == true) .ToListAsync(); } public async Task> GetNotifUserKey(ItemDto itemDto) { var allItems = await _dbContext.NotifUserKeys .FromSqlRaw($"EXEC GetNotifUserKey @UserId,@Status,@PRDetailsId,@PRNo", new SqlParameter("@UserId", itemDto.UserId), new SqlParameter("@Status", itemDto.Status), new SqlParameter("@PRDetailsId", itemDto.PRDetailsId), new SqlParameter("@PRNo", itemDto.PRNo)) .ToListAsync(); return allItems ?? new List(); } public async Task> GetProjectCode() { return await _dbContext.ProjectCodes .AsNoTracking() .ToListAsync(); } public async Task> GetProjectCodeByTerm(string? term) { return await _dbContext.ProjectCodes .AsNoTracking() .Where(p => EF.Functions.Like(p.ProjectCode, $"%{term}%")) .ToListAsync(); } } }