using System; using System.Collections.Generic; using System.Linq; using System.Security.AccessControl; using System.Text; using System.Threading.Tasks; using GB5Shared.DTO.Framework.Login; using GB5Shared.GenerateAutoNumber; using GB5Shared.QueryExecutor; using MMDAL.DTO.Lot; using MMDAL.DTO.LotDetail; using GB5Shared.DTO.Framework.AutoNumber; using GB5Shared.DTO.Framework.Criteria; using MMDAL.CustomCode.Item; using MMDAL.CustomCode.Lot; namespace MMBLL.Lot { public class LotBLL : ILotBLL { private readonly AutoNumber _AutoNumber; private ILotDAL _LotDAL; public LotBLL( AutoNumber AutoNumber, ILotDAL LotDAL) { _AutoNumber = AutoNumber; _LotDAL = LotDAL; } public async Task LotDetailSave(List LotDetailDTOs, LoginDTO LoginDTO, int LotTag = 0) { //ILotDetailLibDAL LotDetailLibDAL = new LotDetailLibDAL(); List LotInfoDTOs = new List(); try { if (LotDetailDTOs.Count == 0) { return true; } //First Delete ALL then Insert Done by Vikash on 29 July 2023 For Redmine //[Artex - Bug #39599] (New) After creating the sale return. if they update that sale return, it removed the tlotdetail entries to the relevant document(sale return) for (int i = 0; i < LotDetailDTOs.Count; i++) { if (LotTag == 1) //For Check Save or Update 0-Save/1-Update { //string ssql = LotDetailLibDAL.DeleteLotDetails(LotDetailDTOs[i].BizTransactionTypeId, LotDetailDTOs[i].ObjectHeaderTypeId, LotDetailDTOs[i].LotDetailObjectHeaderId, LotDetailDTOs[i].ObjectTypeId, LotDetailDTOs[i].LotDetailObjectId); string ssql = " DELETE FROM TLOTDETAIL where 1=1 AND BIZTRANSACTIONTYPEID =" + LotDetailDTOs[i].BizTransactionTypeId + " AND OBJECTHEADERTYPEID=" + LotDetailDTOs[i].ObjectHeaderTypeId + " AND OBJECTHEADERID=" + LotDetailDTOs[i].LotDetailObjectHeaderId + " AND OBJECTTYPEID=" + LotDetailDTOs[i].ObjectTypeId + " AND LOTID=" + LotDetailDTOs[i].LotId; //GenericDal.ExceuteUpdateQuery(ssql, LoginDTO); string SShql = "SELECT count(LOTID) FROM TLOT WHERE LOTID=" + LotDetailDTOs[i].LotId; //int Total2 = GenericDal.TotalCountSql(SShql, LoginDTO, true); //if (Total2 == 0) //{ // string dellot = "DELETE FROM TLOT WHERE LOTID=" + LotDetailDTOs[i].LotId; // //GenericDal.ExceuteUpdateQuery(dellot, LoginDTO); //} } } AutoNumberDTO AutoNumberDTO = await _AutoNumber.GetNumberAsync(LotDetailDTOs.Count, "LOTDETAIL", LoginDTO); for (int i = 0; i < LotDetailDTOs.Count; i++) { LotDetailDTOs[i].LotDetailId = AutoNumberDTO.StartNumber + i; if (LotDetailDTOs[i].IsPlannedQuantityToBeZeroInLotDetail == 1) { LotDetailDTOs[i].LotDetailPlannedQuantity = LotDetailDTOs[i].LotDetailQuantity; } else { LotDetailDTOs[i].LotDetailPlannedQuantity = 0; } //GenericDal.Save(LotDetailDTOs[i], LoginDTO, null); //LotInfoDTO LotInfoDTO = new LotInfoDTO(); //LotInfoDTO.LotId = LotDetailDTOs[i].LotId; //LotInfoDTO.KRM = LotDetailDTOs[i].LotInfoKRM; //LotInfoDTO.ProductCode = LotDetailDTOs[i].LotInfoProductCode; //LotInfoDTO.DGSetSlNo = LotDetailDTOs[i].LotInfoDgSetSlNo; //LotInfoDTOs.Add(LotInfoDTO); } return true; } catch (Exception) { throw; } } public async Task GetSelectListLot(int FirstNumber, int MaxResult, CriteriaDTO criteriaDTO, LoginDTO loginDTO) { try { return await _LotDAL.GetSelectListLot(FirstNumber, MaxResult, criteriaDTO, loginDTO); } catch (Exception) { throw; } } /// /// Creates a new LOT entry in TLOT when LotId == 0 during Inspection save. /// Reserves AutoNumber for LotId, formats LotNumber as "LOT-0000001", /// then delegates the DB insert to ILotDAL. /// public async Task CreateLotAsync(LotDTO lotDTO, LoginDTO loginDTO, CancellationToken ct) { try { // ── STEP 1: AutoNumber ──────────────────────────────────── AutoNumberDTO autoNumberDTO = await _AutoNumber.GetNumberAsync(1, "LOT", loginDTO); lotDTO.LotId = autoNumberDTO.StartNumber; // Use caller-supplied number (e.g. VoucherNumberService from InspectionBLL). // Fall back to Id-based format when no number was pre-set. if (string.IsNullOrEmpty(lotDTO.LotLotNumber)) lotDTO.LotLotNumber = $"{Math.Abs(lotDTO.LotId):D7}"; // ── STEP 2: Audit ───────────────────────────────────────── lotDTO.LotCreatedById = loginDTO.UserId; lotDTO.LotCreatedOn = DateTime.UtcNow; lotDTO.LotModifiedById = loginDTO.UserId; lotDTO.LotModifiedOn = DateTime.UtcNow; lotDTO.LotStatus = 1; lotDTO.LotVersion = 1; // ── STEP 3: FK Defaults if not supplied ─────────────────── // PROCESSID → MPROCESS : must be a valid FK, use -1 only if // MPROCESS has a row with PROCESSID = -1 if (lotDTO.ProcessId == 0) lotDTO.ProcessId = -1; // LOTTYPEID → MLOTTYPE : must be a valid FK row // If not supplied from frontend, set your system default here if (lotDTO.LotTypeId == 0) lotDTO.LotTypeId = -1; lotDTO.LotMRPRate = 0; lotDTO.LotItemPostedCost = 0; // ── STEP 4: Persist ─────────────────────────────────────── await _LotDAL.CreateLotAsync(lotDTO, loginDTO, ct); return lotDTO.LotId; // → assigned to detail.LotId in Step 2.5 } catch (Exception ex) { throw new Exception($"CreateLotAsync failed: {ex.Message}", ex); } } public async Task GetSelectListLotReservation(CriteriaDTO criteriaDTO, LoginDTO loginDTO) { try { return await _LotDAL.GetSelectListLotReservation(criteriaDTO, loginDTO); } catch (Exception) { throw; } } public async Task GetLotSelectListForQuantity(int FirstNumber, int MaxResult, CriteriaDTO criteriaDTO, LoginDTO loginDTO) { try { return await _LotDAL.GetLotSelectListForQuantity(FirstNumber, MaxResult, criteriaDTO, loginDTO); } catch (Exception) { throw; } } } }