#nullable enable using AyCode.Core.Extensions; using AyCode.Core.Loggers; using AyCode.Utils.Extensions; using FruitBank.Common.Dtos; using FruitBank.Common.Entities; using FruitBank.Common.Interfaces; using FruitBank.Common.Models; using Mango.Nop.Core.Entities; using Mango.Nop.Core.Extensions; using Mango.Nop.Core.Loggers; using Mango.Nop.Data.Repositories; using Microsoft.EntityFrameworkCore; using Nop.Core; using Nop.Core.Caching; using Nop.Core.Domain.Catalog; using Nop.Core.Domain.Common; using Nop.Core.Domain.Customers; using Nop.Core.Domain.Orders; using Nop.Core.Domain.Shipping; using Nop.Core.Events; using Nop.Data; using Nop.Plugin.Misc.FruitBankPlugin.Domains.DataLayer.Interfaces; using Nop.Plugin.Misc.FruitBankPlugin.Services; using Nop.Services.Catalog; using Nop.Services.Security; using WebMarkupMin.Core.Loggers; namespace Nop.Plugin.Misc.FruitBankPlugin.Domains.DataLayer; public class FruitBankDbContext : MgDbContextBase, IOrderDtoDbSet, IOrderItemDtoDbSet, IPartnerDbSet, IShippingDbSet, IShippingDocumentDbSet, IShippingItemDbSet, IShippingItemPalletDbSet, IOrderItemPalletDbSet, IShippingDocumentToFilesDbSet, IFilesDbSet { private readonly FruitBankAttributeService _fruitBankAttributeService; private readonly IStoreContext _storeContext; private readonly IProductService _productService; private readonly IStaticCacheManager _staticCacheManager; protected readonly IEventPublisher _eventPublisher; public ProductDtoDbTable ProductDtos { get; set; } public OrderDtoDbTable OrderDtos { get; set; } public OrderItemDtoDbTable OrderItemDtos { get; set; } public PartnerDbTable Partners { get; set; } public ShippingDbTable Shippings { get; set; } public ShippingDocumentDbTable ShippingDocuments { get; set; } public ShippingItemDbTable ShippingItems { get; set; } public ShippingItemPalletDbTable ShippingItemPallets { get; set; } public OrderItemPalletDbTable OrderItemPallets { get; set; } public FilesDbTable Files { get; set; } public ShippingDocumentToFilesDbTable ShippingDocumentToFiles { get; set; } public StockQuantityHistoryDtoDbTable StockQuantityHistoryDtos { get; set; } public IRepository Customers { get; set; } public IRepository CustomerRoles { get; set; } public IRepository CustomerRoleMappings { get; set; } public IRepository CustomerAddressMappings { get; set; } public IRepository GenericAttributes { get; set; } public IRepository StockQuantityHistories { get; set; } public IRepository StockQuantityHistoriesExt { get; set; } public FruitBankDbContext(INopDataProvider dataProvider, ILockService lockService, FruitBankAttributeService fruitBankAttributeService, IStoreContext storeContext, PartnerDbTable partnerDbTable, ShippingDbTable shippingDbTable, ShippingDocumentDbTable shippingDocumentDbTable, ShippingItemDbTable shippingItemDbTable, ShippingItemPalletDbTable shippingItemPalletDbTable, FilesDbTable filesDbTable, ShippingDocumentToFilesDbTable shippingDocumentToFilesDbTable, ProductDtoDbTable productDtoDbTable, OrderDtoDbTable orderDtoDbTable, OrderItemDtoDbTable orderItemDtoDbTable, OrderItemPalletDbTable orderItemPalletDbTable, StockQuantityHistoryDtoDbTable stockQuantityHistoryDtos, IProductService productService, IStaticCacheManager staticCacheManager, IRepository orderRepository, IRepository orderItemRepository, IRepository productRepository, IRepository customerRepository, IRepository customerCustomerRoleMappingRepository, IRepository customerAddressMappingRepository, IRepository customerRoleRepository, IRepository genericAttributes, IRepository stockQuantityHistories, IRepository stockQuantityHistoriesExt, IEventPublisher eventPublisher, IEnumerable logWriters) : base(productRepository, orderRepository, orderItemRepository, dataProvider, lockService, new Logger(logWriters.ToArray())) { _eventPublisher = eventPublisher; _storeContext = storeContext; _productService = productService; _staticCacheManager = staticCacheManager; _fruitBankAttributeService = fruitBankAttributeService; Files = filesDbTable; Partners = partnerDbTable; Products = productRepository; ProductDtos = productDtoDbTable; OrderDtos = orderDtoDbTable; OrderItemDtos = orderItemDtoDbTable; OrderItemPallets = orderItemPalletDbTable; Shippings = shippingDbTable; ShippingDocuments = shippingDocumentDbTable; ShippingItems = shippingItemDbTable; ShippingItemPallets = shippingItemPalletDbTable; ShippingDocumentToFiles = shippingDocumentToFilesDbTable; Customers = customerRepository; CustomerRoles = customerRoleRepository; CustomerRoleMappings = customerCustomerRoleMappingRepository; CustomerAddressMappings = customerAddressMappingRepository; GenericAttributes = genericAttributes; StockQuantityHistories = stockQuantityHistories; StockQuantityHistoriesExt = stockQuantityHistoriesExt; StockQuantityHistoryDtos = stockQuantityHistoryDtos; } public IQueryable GetCustomersBySystemRoleName(string systemRoleName) { if (systemRoleName.IsNullOrWhiteSpace()) throw new ArgumentException("systemRoleName.IsNullOrWhiteSpace()", nameof(systemRoleName)); var query = from c in Customers.Table join crm in CustomerRoleMappings.Table on c.Id equals crm.CustomerId join cr in CustomerRoles.Table on crm.CustomerRoleId equals cr.Id where c.Active && !c.Deleted && cr.SystemName == systemRoleName select c; return query.Distinct().OrderBy(o => o.Username); } public IQueryable GetCustomerRolesByCustomerId(int customerId) { var query = from cr in CustomerRoles.Table join crm in CustomerRoleMappings.Table on cr.Id equals crm.CustomerRoleId where crm.CustomerId == customerId select cr; return query.Distinct(); } //public IQueryable GetAllProducts(bool includeDeleted) // => Products.Table.Where(p => includeDeleted || !p.Deleted).OrderBy(o => o.Name); //public IQueryable GetAllProductDtos(bool includeDeleted) // => GetAllProducts(includeDeleted).Select(product => new ProductDto(product)); //public IAsyncEnumerable GetAllMeasuringProductDtos(bool includeDeleted) // => GetAllProducts(includeDeleted).AsEnumerable().SelectAwait(async product => new MeasuringProductDto(product, await GetMeasuringAttributeValuesByProductIdAsync(product.Id))); //public async Task GetMeasuringProductDtoByIdAsync(int productId) // => await Products.Table.Where(product => product.Id == productId).AsEnumerable().SelectAwait(async product => new MeasuringProductDto(product, await GetMeasuringAttributeValuesByProductIdAsync(product.Id))).FirstOrDefaultAsync(); //public async Task GetMeasuringAttributeValuesByProductIdAsync(int productId) // => await _fruitBankAttributeService.GetMeasuringAttributeValuesAsync(productId); //public async Task> ProcessAndSaveFullShippingDocumentJson(string fullShippingDocumentJson) //{ // var partners = fullShippingDocumentJson.JsonTo>(); // if (partners != null) // { // foreach (var partner in partners) // { // //await Partners.InsertAsync(partner); // if (partner.ShippingDocuments == null) continue; // foreach (var shippingDocument in partner.ShippingDocuments) // { // await ShippingDocuments.InsertAsync(shippingDocument); // } // } // } //} public async Task DeleteShippingSafeAsync(Shipping shipping) { await TransactionSafeAsync(async _ => { await Shippings.DeleteAsync(shipping, true); return true; }); } public async Task DeleteShippingDocumentSafeAsync(ShippingDocument shippingDocument) { await TransactionSafeAsync(async _ => { await ShippingDocuments.DeleteAsync(shippingDocument, true); return true; }); } public async Task DeleteShippingItemSafeAsync(ShippingItem shippingItem) { await TransactionSafeAsync(async _ => { await ShippingItems.DeleteAsync(shippingItem, true); return true; }); } public Task UpdateMeasuredShippingItemSafeAsync(ShippingItem shippingItem) { if (shippingItem.IsValidMeasuringValues()) return UpdateShippingItemSafeAsync(shippingItem); Logger.Error("shippingItem.IsMeasurable && !shippingItem.IsValidMeasuringValues()"); return Task.FromResult(false); } public Task AddShippingItemSafeAsync(ShippingItem shippingItem) => TransactionSafeAsync(async _ => await AddShippingItemAsync(shippingItem)); public async Task AddShippingItemAsync(ShippingItem shippingItem) { var productId = shippingItem.ProductId.GetValueOrDefault(0); if (productId > 0) { var productDto = await ProductDtos.GetByIdAsync(productId, true); if (productDto != null) { shippingItem.IsMeasurable = productDto.IsMeasurable; shippingItem.Name = productDto.Name; } } //IDEIGLENES, AMÍG NEM VEZETJÜK KI A shippingItem.Name-et! if (shippingItem.Name.IsNullOrEmpty() && !shippingItem.NameOnDocument.IsNullOrEmpty()) shippingItem.Name = shippingItem.NameOnDocument; else if (shippingItem.Name.IsNullOrEmpty()) shippingItem.Name = string.Empty; await ShippingItems.InsertAsync(shippingItem); return true; } public Task UpdateShippingItemSafeAsync(ShippingItem shippingItem) => TransactionSafeAsync(async _ => await UpdateShippingItemAsync(shippingItem)); public async Task UpdateShippingItemAsync(ShippingItem shippingItem) { try { //Logger.Warning($"UpdateShippingItemAsync"); //throw new Exception($"Teszt"); ProductDto? productDto = null; var productIsMeasurable = false; if (shippingItem.ProductId.GetValueOrDefault(0) > 0) { productDto = await ProductDtos.GetByIdAsync(shippingItem.ProductId!.Value, true); if (productDto == null) throw new Exception($"shippingItem.ProductId > 0 && product == null; shippingItem.ProductId: {shippingItem.ProductId}"); productIsMeasurable = productDto.IsMeasurable; shippingItem.Name = productDto.Name; } shippingItem.IsMeasurable = productIsMeasurable; //if (shippingItem.ShippingItemPallets is { Count: > 0 }) await AddOrUpdateShippingItemPalletAsync(shippingItem); //await AddOrUpdateShippingItemPalletAsync(shippingItem.ShippingItemPallets.Where(x => x.IsValidMeasuringValues(shippingItem.IsMeasurable)), shippingItem); //Nem tudhatjuk, h minden Pallet-et tartalmaz-e a shippingItem paraméter! A Biztonság kedvéért lekérjük db-ből! - J. shippingItem.ShippingItemPallets = await ShippingItemPallets.GetAllByShippingItemIdAsync(shippingItem.Id, false).ToListAsync(); //Update előtt kivesszük a korábbi ShippingItem-et a db-ből! - J. var dbShippingItem = await ShippingItems.GetByIdAsync(shippingItem.Id, false); if (dbShippingItem == null) throw new Exception($"dbShippingItem == null; shippingItem.Id: {shippingItem.Id}"); var isMeasuredPrerequisite = productDto != null && shippingItem.MeasuringCount == shippingItem.ShippingItemPallets.Count && shippingItem.ShippingItemPallets.All(x => x.IsMeasuredAndValid(shippingItem.IsMeasurable)); SetupShippingItemMeasuringValues(shippingItem, isMeasuredPrerequisite); shippingItem.IsMeasured = isMeasuredPrerequisite && shippingItem.IsValidMeasuringValues(); await ShippingItems.UpdateAsync(shippingItem, shippingItem.IsMeasured != dbShippingItem.IsMeasured); if (shippingItem.ProductId == dbShippingItem.ProductId && shippingItem.IsMeasured == dbShippingItem.IsMeasured && shippingItem.IsMeasurable == dbShippingItem.IsMeasurable && shippingItem.MeasuredQuantity == dbShippingItem.MeasuredQuantity && // ReSharper disable once CompareOfFloatsByEqualityOperator shippingItem.MeasuredNetWeight == dbShippingItem.MeasuredNetWeight && // ReSharper disable once CompareOfFloatsByEqualityOperator shippingItem.MeasuredGrossWeight == dbShippingItem.MeasuredGrossWeight) { return true; } var productIdChanged = shippingItem.ProductId != dbShippingItem.ProductId; if (shippingItem.IsMeasured) { var quantityInc = productIdChanged ? shippingItem.MeasuredQuantity : shippingItem.MeasuredQuantity - dbShippingItem.MeasuredQuantity; //productDto!.StockQuantity += quantityInc; //if (!await UpdateProductDtoStockQuantityAsync(productDto, true)) // throw new Exception($"UpdateProductStockQuantity() == false; shippingItem! product.Id: {productDto.Id}"); var incomingQuantity = productDto!.GenericAttributes.GetValueOrNull(nameof(IIncomingQuantity.IncomingQuantity)); if (incomingQuantity != null) { await _fruitBankAttributeService.UpdateGenericAttributeAsync (productDto.Id, nameof(IIncomingQuantity.IncomingQuantity), incomingQuantity.Value - quantityInc); } var weightToChange = 0d; if (productIsMeasurable) { weightToChange = productIdChanged ? shippingItem.MeasuredNetWeight : shippingItem.MeasuredNetWeight - dbShippingItem.MeasuredNetWeight; //await _fruitBankAttributeService.InsertOrUpdateMeasuringAttributeValuesAsync(productDto.Id, weightToChange, shippingItem.IsMeasurable, true); } await UpdateStockQuantityAndWeightAsync(productDto, quantityInc, $"Áru bevételezés, shippingItem: #{shippingItem.Id}", weightToChange); //productDto!.StockQuantity += quantityInc; } //if (productIdUnchanged || !dbShippingItem.IsMeasured) return true; if (!dbShippingItem.ProductId.HasValue || (!productIdChanged && (shippingItem.IsMeasured || !dbShippingItem.IsMeasured))) return true; productDto = await ProductDtos.GetByIdAsync(dbShippingItem.ProductId!.Value, true); if (productDto != null) { productIsMeasurable = productDto.IsMeasurable; //productDto.StockQuantity -= dbShippingItem.MeasuredQuantity; //if (!await UpdateProductDtoStockQuantityAsync(productDto, true)) // throw new Exception($"UpdateProductStockQuantity() == false; dbShippingItem! product.Id: {productDto.Id}"); var incomingQuantity = productDto.GenericAttributes.GetValueOrNull(nameof(IIncomingQuantity.IncomingQuantity)); if (incomingQuantity != null) { await _fruitBankAttributeService.UpdateGenericAttributeAsync (productDto.Id, nameof(IIncomingQuantity.IncomingQuantity), incomingQuantity.Value + dbShippingItem.MeasuredQuantity); } //if (productIsMeasurable) //{ // var measuringValues = new MeasuringAttributeValues(productDto.Id, -dbShippingItem.MeasuredNetWeight, dbShippingItem.IsMeasurable); // await _fruitBankAttributeService.InsertOrUpdateMeasuringAttributeValuesAsync(measuringValues, true); //} await UpdateStockQuantityAndWeightAsync(productDto, -dbShippingItem.MeasuredQuantity, $"Áru bevételezés, ShippingItem.Id: #{shippingItem.Id}. Product.Id megváltozott, #{productDto.Id}->#{shippingItem.ProductId}!", -dbShippingItem.MeasuredNetWeight); //productDto!.StockQuantity -= dbShippingItem.MeasuredQuantity; } else Logger.Warning($"product == null; dbShippingItem.ProductId: {dbShippingItem.ProductId}"); //else //TODO: productIdUnchanged-et lekezelni! - J. return true; } catch (Exception ex) { throw new Exception($"UpdateShippingItemAsync error! {shippingItem}; ex: {ex.Message}", ex); } } private static void SetupShippingItemMeasuringValues(ShippingItem shippingItem, bool shippingItemIsMeasured) { shippingItem.MeasuredQuantity = 0; shippingItem.MeasuredNetWeight = 0; shippingItem.MeasuredGrossWeight = 0; if (!shippingItemIsMeasured) return; foreach (var shippingItemPallet in shippingItem.ShippingItemPallets!.Where(x => x.IsMeasured && x.IsValidMeasuringValues(shippingItem.IsMeasurable))) { shippingItem.MeasuredQuantity += shippingItemPallet.TrayQuantity; if (!shippingItem.IsMeasurable) continue; shippingItem.MeasuredNetWeight += shippingItemPallet.NetWeight; shippingItem.MeasuredGrossWeight += shippingItemPallet.GrossWeight; } shippingItem.MeasuredNetWeight = double.Round(shippingItem.MeasuredNetWeight, 1); shippingItem.MeasuredGrossWeight = double.Round(shippingItem.MeasuredGrossWeight, 1); //if (shippingItem.MeasuredQuantity < 0) shippingItem.MeasuredQuantity = 0; //if (!shippingItem.IsMeasurable || shippingItem.MeasuredNetWeight < 0) shippingItem.MeasuredNetWeight = 0; //if (!shippingItem.IsMeasurable || shippingItem.MeasuredGrossWeight < 0) shippingItem.MeasuredGrossWeight = 0; } public async Task AddShippingItemPalletAsync(ShippingItemPallet shippingItemPallet) { if (!await SetupShippingItemPalletMeauringValues(shippingItemPallet)) return null; await ShippingItemPallets.InsertAsync(shippingItemPallet); var shippingItem = await ShippingItems.GetByIdAsync(shippingItemPallet.ShippingItemId, false); await UpdateShippingItemAsync(shippingItem); return shippingItemPallet; } public Task AddShippingItemPalletSafeAsync(ShippingItemPallet shippingItemPallet) => TransactionSafeAsync(async _ => await AddShippingItemPalletAsync(shippingItemPallet) != null); public async Task UpdateShippingItemPalletAsync(ShippingItemPallet shippingItemPallet) { if (!await SetupShippingItemPalletMeauringValues(shippingItemPallet)) return null; await ShippingItemPallets.UpdateAsync(shippingItemPallet); var shippingItem = await ShippingItems.GetByIdAsync(shippingItemPallet.ShippingItemId, false); await UpdateShippingItemAsync(shippingItem); return shippingItemPallet; } public Task UpdateShippingItemPalletSafeAsync(ShippingItemPallet shippingItemPallet) => TransactionSafeAsync(async _ => await UpdateShippingItemPalletAsync(shippingItemPallet) != null); public Task AddOrUpdateShippingItemPalletsSafeAsync(ShippingItem shippingItem) => AddOrUpdateShippingItemPalletsSafeAsync(shippingItem.ShippingItemPallets!, shippingItem); public Task AddOrUpdateShippingItemPalletsSafeAsync(IEnumerable shippingItemPallets, ShippingItem parentShippingItem) { return TransactionSafeAsync(async _ => { await AddOrUpdateShippingItemPalletAsync(shippingItemPallets, parentShippingItem); return true; }); } public Task AddOrUpdateShippingItemPalletAsync(ShippingItem shippingItem) => AddOrUpdateShippingItemPalletAsync(shippingItem.ShippingItemPallets!, shippingItem); public async Task AddOrUpdateShippingItemPalletAsync(IEnumerable shippingItemPallets, ShippingItem parentShippingItem) { foreach (var shippingItemPallet in shippingItemPallets) { shippingItemPallet.ShippingItem = parentShippingItem; if (await AddOrUpdateShippingItemPalletAsync(shippingItemPallet) == null) throw new Exception($"AddOrUpdateShippingItemPalletAsync->AddOrUpdateShippingItemPalletAsync() == null"); } } public async Task AddOrUpdateShippingItemPalletSafeAsync(ShippingItemPallet shippingItemPallet) => await TransactionSafeAsync(async _ => await AddOrUpdateShippingItemPalletAsync(shippingItemPallet) != null); public async Task AddOrUpdateShippingItemPalletAsync(ShippingItemPallet shippingItemPallet) { if (shippingItemPallet.Id <= 0) return await AddShippingItemPalletAsync(shippingItemPallet); return await UpdateShippingItemPalletAsync(shippingItemPallet); } public async Task DeleteShippingItemPalletSafeAsync(ShippingItemPallet shippingItemPallet) { await TransactionSafeAsync(async _ => { await ShippingItemPallets.DeleteAsync(shippingItemPallet, false); return true; }); } public async Task StartMeasuringSafeAsync(int orderId, int revisorId) => await TransactionSafeAsync(async _ => await StartMeasuringAsync(orderId, revisorId) != null); public async Task StartMeasuringAsync(int orderId, int customerId) { if (customerId <= 0) return null; var orderDto = await OrderDtos.GetByIdAsync(orderId, true); if (orderDto == null || orderDto.MeasurementOwnerId > 0) return orderDto; await _fruitBankAttributeService.InsertOrUpdateGenericAttributeAsync(orderDto.Id, nameof(IOrderDto.MeasurementOwnerId), customerId); return orderDto; } public async Task SetOrderStatusToCompleteSafeAsync(int orderId, int revisorId) => await TransactionSafeAsync(async _ => await SetOrderStatusToCompleteAsync(orderId, revisorId) != null); public async Task SetOrderStatusToCompleteAsync(int orderId, int revisorId) { if (revisorId <= 0) return null; var orderDto = await OrderDtos.GetByIdAsync(orderId, true); if (orderDto == null) return null; if (!orderDto.IsMeasuredAndValid() || orderDto.OrderStatus == OrderStatus.Complete) return null; //throw new Exception($"SetOrderDtoToComplete; orderDto.IsMeasured == false; {orderDto}"); //var prevOrderStatus = orderDto.OrderStatus; orderDto.OrderStatus = OrderStatus.Complete; await OrderDtos.UpdateAsync(orderDto); await _fruitBankAttributeService.InsertOrUpdateGenericAttributeAsync(orderDto.Id, nameof(IOrderDto.RevisorId), revisorId); foreach (var orderItemDto in orderDto.OrderItemDtos) { if (orderItemDto.TrayQuantity != orderItemDto.Quantity) return null; foreach (var orderItemPallet in orderItemDto.OrderItemPallets.Where(oip => oip.RevisorId <= 0)) { orderItemPallet.RevisorId = revisorId; await OrderItemPallets.UpdateAsync(orderItemPallet, false); } if (!orderItemDto.IsMeasurable) continue; var prevOrderItemNetWeightFromGa = orderItemDto.GenericAttributes.GetValueOrDefault(nameof(IMeasuringNetWeight.NetWeight), 0); //var gaNetWeight = CommonHelper.To(orderItemDto.GenericAttributes.FirstOrDefault(x => x.Key == nameof(IMeasuringNetWeight.NetWeight))?.Value ?? "0"); await _fruitBankAttributeService.InsertOrUpdateGenericAttributeAsync(orderItemDto.Id, nameof(IMeasuringNetWeight.NetWeight), orderItemDto.NetWeight); var productWeightToChange = -(orderItemDto.NetWeight - prevOrderItemNetWeightFromGa); //await _fruitBankAttributeService.InsertOrUpdateMeasuringAttributeValuesAsync(orderItemDto.ProductId, productWeightToChange, orderItemDto.IsMeasurable, true); await UpdateStockQuantityAndWeightAsync(orderItemDto.ProductId, 0, $"Áru kiadás, OrderStatus set to complete. Rendelés: #{orderDto.Id}, rendelés tétel: #{orderItemDto.Id}", productWeightToChange); } //await _eventPublisher.PublishAsync(new OrderStatusChangedEvent(order, prevOrderStatus)); return orderDto; } public async Task SetOrderStatusToPendingSafeAsync(Order order) => await TransactionSafeAsync(async _ => await SetOrderStatusToPendingAsync(order)); public async Task SetOrderStatusToPendingAsync(Order order) { if (order.OrderStatus == OrderStatus.Pending) return true; var prevOrderStatus = order.OrderStatus; order.OrderStatus = OrderStatus.Pending; await Orders.UpdateAsync(order, false); await _eventPublisher.PublishAsync(new OrderStatusChangedEvent(order, prevOrderStatus)); return true; } public Task DeleteOrderItemConstraintsSafeAsync(OrderItem orderItem, bool publishEvent = false) { return TransactionSafeAsync(async _ => { await DeleteOrderItemConstraintsAsync(orderItem, publishEvent); return true; }); } public async Task DeleteOrderItemConstraintsAsync(OrderItem orderItem, bool publishEvent = false) { //Itt nincs már OrderItemDto!!!! - J. var storeId = _storeContext.GetCurrentStore().Id; var orderItemGenericAttributes = await GenericAttributes.Table.Where(x => x.EntityId == orderItem.Id && x.KeyGroup == nameof(OrderItem) && x.StoreId == storeId).ToListAsync(); var validOrderItemNetWeight = orderItemGenericAttributes.GetValueOrDefault(nameof(IMeasuringNetWeight.NetWeight), 0); if (validOrderItemNetWeight != 0) { var productDto = await ProductDtos.GetByIdAsync(orderItem.ProductId, true); if (productDto != null && productDto.IsMeasurable) { var newProductNetWeight = productDto.NetWeight + validOrderItemNetWeight; await _fruitBankAttributeService.InsertOrUpdateGenericAttributeAsync(productDto.Id, nameof(IMeasuringNetWeight.NetWeight), newProductNetWeight); Logger.Info($"DbContext->DeleteOrderItemConstraintsAsync(); Product netWeight updated! productId: {productDto.Id}; newNetWeight: {newProductNetWeight}; oldNetWeight: {productDto.NetWeight}; deleted orderItemNetWeight: {validOrderItemNetWeight}; orderItem.Id: {orderItem.Id};"); } } await _fruitBankAttributeService.DeleteGenericAttributesAsync(orderItemGenericAttributes); var deletedPalletCount = await OrderItemPallets.DeleteAsync(x => x.OrderItemId == orderItem.Id); var order = await Orders.GetByIdAsync(orderItem.OrderId); // await _customPriceCalculationService.CheckAndUpdateOrderTotalPrice(order); Logger.Info($"DbContext->DeleteOrderItemConstraintsAsync(); OrderItem constraints deleted! deletedPalletCount: {deletedPalletCount}; deletedAttributesCount: {orderItemGenericAttributes.Count}; orderItem.Id: {orderItem.Id};"); } public async Task AddOrderItemPalletAsync(OrderItemPallet orderItemPallet) { if (!await SetupOrderItemPalletMeauringValues(orderItemPallet)) return null; await OrderItemPallets.InsertAsync(orderItemPallet); return orderItemPallet; } public async Task UpdateOrderItemPalletAsync(OrderItemPallet orderItemPallet) { if (!await SetupOrderItemPalletMeauringValues(orderItemPallet)) return null; await OrderItemPallets.UpdateAsync(orderItemPallet); return orderItemPallet; } public async Task AddOrUpdateOrderItemPalletSafeAsync(OrderItemPallet orderItemPallet) => await TransactionSafeAsync(async _ => await AddOrUpdateOrderItemPalletAsync(orderItemPallet) != null); public async Task AddOrUpdateOrderItemPalletAsync(OrderItemPallet orderItemPallet) { if (orderItemPallet.Id <= 0) return await AddOrderItemPalletAsync(orderItemPallet); return await UpdateOrderItemPalletAsync(orderItemPallet); } private async Task SetupShippingItemPalletMeauringValues(ShippingItemPallet shippingItemPallet) { var shippingItem = shippingItemPallet.ShippingItem ?? await ShippingItems.GetByIdAsync(shippingItemPallet.ShippingItemId, false); if (shippingItem == null || shippingItemPallet.ShippingItemId != shippingItem.Id) return false; shippingItemPallet.SetupCustomItemPalletMeauringValues(shippingItem.IsMeasurable); return true; } private async Task SetupOrderItemPalletMeauringValues(OrderItemPallet orderItemPallet) { var orderItemDto = await OrderItemDtos.GetByIdAsync(orderItemPallet.OrderItemId, true); if (orderItemDto == null || orderItemPallet.OrderItemId != orderItemDto.Id || //orderItemDto.IsOtherMeasuringInProgress(orderItemPallet.CreatorId) || orderItemPallet.TrayQuantity > orderItemDto.Quantity || !orderItemPallet.IsValidSafeMeasuringValues()) return false; orderItemDto.OrderItemPallets.UpdateCollection(orderItemPallet, false); if (orderItemDto.TrayQuantity > orderItemDto.Quantity) return false; orderItemPallet.SetupCustomItemPalletMeauringValues(orderItemDto.IsMeasurable); return true; } //private async Task UpdateProductDtoStockQuantityAsync(int productDtoId, bool publishEvent) //{ // var productDto = await ProductDtos.GetByIdAsync(productDtoId, false); // if (productDto != null) return await UpdateProductDtoStockQuantityAsync(productDto, publishEvent); // Logger.Error($"product == null; id: {productDtoId}"); // return await Task.FromResult(false); //} //private async Task UpdateProductDtoStockQuantityAsync(ProductDto productDto, bool publishEvent) //{ // //TODO: !!!!!!!!!!!!!!!! - J. // //await _productService.AdjustInventoryAsync(product, quantityInc, string.Empty, ""); // await ProductDtos.UpdateAsync(productDto, publishEvent); // return await Task.FromResult(true); // //var updatedRowsCount = await DataProvider.ExecuteNonQueryAsync($"update product set {nameof(Product.StockQuantity)} = {product.StockQuantity} where {nameof(Product.Id)} = {product.Id}"); // //if (updatedRowsCount == 1) return await Task.FromResult(true); // //Logger.Error($"Product updatedRowsCount != 1; id: {product.Id}"); // //return await Task.FromResult(false); //} public async Task UpdateStockQuantityAndWeightAsync(int productId, int quantityToChange, string message, double weightToChange = 0) { if (quantityToChange == 0 && weightToChange == 0) return; var product = await Products.GetByIdAsync(productId); await UpdateStockQuantityAndWeightAsync(product, quantityToChange, message, weightToChange); } public async Task UpdateStockQuantityAndWeightAsync(ProductDto productDto, int quantityToChange, string message, double weightToChange = 0) { if (quantityToChange == 0 && weightToChange == 0) return; await UpdateStockQuantityAndWeightAsync(productDto.Id, quantityToChange, message, weightToChange); productDto.StockQuantity += quantityToChange; if (weightToChange == 0) return; productDto.GenericAttributes = await GenericAttributes.Table.Where(x => x.EntityId == productDto.Id && x.KeyGroup == nameof(Product) && x.StoreId == _storeContext.GetCurrentStore().Id).ToListAsync(); } public async Task UpdateStockQuantityAndWeightAsync(Product product, int quantityToChange, string message, double weightToChange = 0) { weightToChange = double.Round(weightToChange, 1); if (quantityToChange == 0 && weightToChange == 0) return; var latStockQuantityHistoryId = 0; if (quantityToChange != 0) await _productService.AdjustInventoryAsync(product, quantityToChange, string.Empty, message); else if (weightToChange != 0) { //Vizsgálja, h a quantityToChange != 0... - J. //await _productService.AddStockQuantityHistoryEntryAsync(product, 0, product.StockQuantity, product.WarehouseId, message); var historyEntry = new StockQuantityHistory { ProductId = product.Id, CombinationId = null, WarehouseId = product.WarehouseId > 0 ? product.WarehouseId : null, QuantityAdjustment = 0, StockQuantity = product.StockQuantity, Message = message, CreatedOnUtc = DateTime.UtcNow }; await StockQuantityHistories.InsertAsync(historyEntry); latStockQuantityHistoryId = historyEntry.Id; } if (weightToChange == 0) return; var storeId = (await _storeContext.GetCurrentStoreAsync()).Id; var newStockWeight = await _fruitBankAttributeService.InsertOrUpdateNetWeightAsync(product.Id, weightToChange, true, storeId); if (latStockQuantityHistoryId <= 0) { //A LastOrDefaultAsync elszáll! - J. latStockQuantityHistoryId = await StockQuantityHistories.Table.Where(x => x.ProductId == product.Id).MaxAsync(x => x.Id); if (latStockQuantityHistoryId == 0) { Logger.Error($"UpdateStockQuantityAndWeightAsync(); (latStockQuantityHistory == 0). product.Id: {product.Id}"); return; } } //var stockWeight = double.Round(await _fruitBankAttributeService.GetGenericAttributeValueAsync(product.Id, nameof(IMeasuringNetWeight.NetWeight), storeId), 1); var lastStockQuantityHistoryExtNetWeight = await StockQuantityHistoryDtos.Table.Where(x => x.ProductId == product.Id && x.StockQuantityHistoryExt != null).Select(x => x.StockQuantityHistoryExt!.NetWeight).FirstOrDefaultAsync(netWeight => netWeight != null); var stockQuantityHistoryExt = new StockQuantityHistoryExt { StockQuantityHistoryId = latStockQuantityHistoryId, NetWeightAdjustment = weightToChange, NetWeight = newStockWeight, IsInconsistent = lastStockQuantityHistoryExtNetWeight != null && double.Round(lastStockQuantityHistoryExtNetWeight.Value + weightToChange, 1) != newStockWeight }; await StockQuantityHistoriesExt.InsertAsync(stockQuantityHistoryExt, false); } public async Task> GetShippingDocumentsByShippingIdAsync(int shippingId) { var list = await ShippingDocuments.GetAll(true).Where(sd => sd.ShippingId == shippingId).ToListAsync(); return list; } public async Task AddCustomerAddressMappingAsync(int customerId, int addressId) { var customerAddressMapping = new CustomerAddressMapping { CustomerId = customerId, AddressId = addressId }; await CustomerAddressMappings.InsertAsync(customerAddressMapping); return customerAddressMapping; } }