688 lines
28 KiB
C#
688 lines
28 KiB
C#
using Nop.Core;
|
||
using Nop.Core.Domain.Catalog;
|
||
using Nop.Core.Domain.Customers;
|
||
using Nop.Core.Domain.Orders;
|
||
using Nop.Plugin.Misc.AuctionPlugin.Domains.DataLayer;
|
||
using Nop.Plugin.Misc.AuctionPlugin.Domains.Dtos;
|
||
using Nop.Plugin.Misc.AuctionPlugin.Domains.Entities;
|
||
using Nop.Plugin.Misc.AuctionPlugin.Domains.Enums;
|
||
using Nop.Services.Catalog;
|
||
using Nop.Services.Logging;
|
||
using Nop.Services.Orders;
|
||
using Nop.Services.Payments;
|
||
using System.Linq;
|
||
using System.Xml;
|
||
using System.Xml.Serialization;
|
||
using Nop.Core.Domain.Common;
|
||
using Nop.Core.Domain.Payments;
|
||
using Nop.Core.Domain.Shipping;
|
||
using Nop.Core.Domain.Stores;
|
||
using Nop.Core.Domain.Tax;
|
||
using Nop.Services.Common;
|
||
using Nop.Services.Customers;
|
||
using Nop.Services.Shipping;
|
||
using NUglify.Helpers;
|
||
using Nop.Plugin.Misc.AuctionPlugin.Domains.Entities.Interfaces;
|
||
|
||
namespace Nop.Plugin.Misc.AuctionPlugin.Services;
|
||
|
||
/// <summary>
|
||
/// Store pickup point service
|
||
/// </summary>
|
||
public class AuctionService(
|
||
AuctionDbContext ctx,
|
||
IProductService productService,
|
||
IWorkContext workContext,
|
||
//IOrderProcessingService orderProcessingService,
|
||
//IShoppingCartService shoppingCartService,
|
||
//IPaymentService paymentService,
|
||
IStoreContext storeContext,
|
||
IAddressService addressService,
|
||
ICustomerService customerService,
|
||
IOrderService orderService,
|
||
ILogger logger,
|
||
ICategoryService categoryService) : IAuctionService
|
||
{
|
||
#region AuctionHub
|
||
|
||
public async Task<ResponseType> UpdateProductToAuctionStatusIfValidAsync(AuctionStatus newProductToAuctionStatus, Auction auction, ProductToAuctionMapping productToAuction, Customer customer, bool updateInDatabase = true)
|
||
{
|
||
if (!IsValidRequestAuctionStatus(newProductToAuctionStatus, productToAuction.AuctionStatus))
|
||
{
|
||
logger.Error($"AuctionHub.UpdateProductToAuctionStatusIfValidAsync(); RequestAuctionStatusIsValid() == false; newStatus: {newProductToAuctionStatus}; oldStatus: {productToAuction.AuctionStatus}", null, customer);
|
||
|
||
return ResponseType.ToCaller;
|
||
}
|
||
|
||
if (newProductToAuctionStatus == AuctionStatus.None) await ResetProductToAuction(productToAuction, auction.CategoryId);
|
||
else
|
||
{
|
||
switch (newProductToAuctionStatus)
|
||
{
|
||
case AuctionStatus.Active:
|
||
productToAuction.AuctionStatus = AuctionStatus.Active;
|
||
await UpdateProductCategoryIsFeaturedAsync(productToAuction.ProductId, auction.CategoryId, true);
|
||
break;
|
||
|
||
case AuctionStatus.FirstWarning:
|
||
case AuctionStatus.SecondWarning:
|
||
productToAuction.AuctionStatus = newProductToAuctionStatus;
|
||
break;
|
||
|
||
case AuctionStatus.Sold:
|
||
case AuctionStatus.NotSold:
|
||
var lastAuctionBid = await GetLastAuctionBidByProductToAuctionIdAsync(productToAuction.Id);
|
||
if (lastAuctionBid == null || lastAuctionBid.BidPrice < productToAuction.MinimumPrice) productToAuction.AuctionStatus = AuctionStatus.NotSold;
|
||
else
|
||
{
|
||
productToAuction.AuctionStatus = AuctionStatus.Sold;
|
||
productToAuction.CurrentPrice = lastAuctionBid.BidPrice;
|
||
productToAuction.WinnerCustomerId = lastAuctionBid.CustomerId;
|
||
|
||
var placeOrderResult = await CreateOrderForWinnerAsync(productToAuction);
|
||
if (placeOrderResult == null || placeOrderResult.Id == 0)
|
||
{
|
||
logger.Error($"AuctionHub.UpdateProductToAuctionStatusIfValidAsync(); (placeOrderResult == null || placeOrderResult.Id == 0)", null, customer);
|
||
//return; //TODO: EGYELŐRE HAGYJUK LEZÁRNI AKKOR IS, HA NEM SIKERÜLT AZ ORDERPLACE()! - J.
|
||
}
|
||
}
|
||
|
||
await UpdateProductCategoryIsFeaturedAsync(productToAuction.ProductId, auction.CategoryId, false);
|
||
break;
|
||
|
||
case AuctionStatus.Pause:
|
||
productToAuction.AuctionStatus = AuctionStatus.Pause;
|
||
break;
|
||
|
||
default:
|
||
logger.Error($"AuctionHub.UpdateProductToAuctionStatusIfValidAsync(); AuctionStatus not found; (newStatus == {newProductToAuctionStatus})", null, customer);
|
||
return ResponseType.ToCaller;
|
||
}
|
||
|
||
if (updateInDatabase)
|
||
await UpdateProductToAuctionAsync(productToAuction);
|
||
}
|
||
|
||
return ResponseType.ToAllClients;
|
||
}
|
||
|
||
public async Task<(Auction auction, ProductToAuctionMapping productToAuction, ResponseType responseType)> GetAndUpdateProductToAuctionStatusIfValidAsync(int productToAuctionId, AuctionStatus newProductToAuctionStatus, Customer customer)
|
||
{
|
||
var productToAuction = await GetProductToAuctionMappingByIdAsync(productToAuctionId);
|
||
if (productToAuction == null)
|
||
{
|
||
logger.Error($"AuctionHub.GetAndUpdateProductToAuctionStatusIfValidAsync(); (productToAuction == null); productToAuctionId: {productToAuctionId}", null, customer);
|
||
return (null, null, ResponseType.None);
|
||
}
|
||
|
||
var auction = await GetAuctionByIdAsync(productToAuction.AuctionId);
|
||
if (auction == null || auction.Closed)
|
||
{
|
||
logger.Error($"AuctionHub.GetAndUpdateProductToAuctionStatusIfValidAsync(); (auction == null || auction.Closed); Closed: {auction?.Closed}; auctionId: {productToAuction.AuctionId}", null, customer);
|
||
return (null, null, ResponseType.None);
|
||
}
|
||
|
||
var responseType = await UpdateProductToAuctionStatusIfValidAsync(newProductToAuctionStatus, auction, productToAuction, customer);
|
||
return (auction, productToAuction, responseType);
|
||
}
|
||
|
||
public async Task ResetProductToAuction(ProductToAuctionMapping productToAuction, int? categoryId = null)
|
||
{
|
||
productToAuction.AuctionStatus = AuctionStatus.None;
|
||
await ResetProductToAuctionAsync(productToAuction, productToAuction.StartingPrice);
|
||
|
||
categoryId ??= (await GetAuctionByIdAsync(productToAuction.AuctionId))?.CategoryId;
|
||
await UpdateProductCategoryIsFeaturedAsync(productToAuction.ProductId, categoryId, false);
|
||
}
|
||
|
||
public async Task UpdateProductCategoryIsFeaturedAsync(int productId, int? categoryId, bool isFeatured)
|
||
{
|
||
//Leszarjuk ha elszáll, az aukció menjen tovább... - J.
|
||
try
|
||
{
|
||
if (categoryId.GetValueOrDefault(0) == 0) return;
|
||
|
||
var productCategory = (await categoryService.GetProductCategoriesByProductIdAsync(productId)).FirstOrDefault(x => x.CategoryId == categoryId);
|
||
if (productCategory == null) return;
|
||
|
||
if (productCategory.IsFeaturedProduct == isFeatured) return;
|
||
|
||
productCategory.IsFeaturedProduct = isFeatured;
|
||
await categoryService.UpdateProductCategoryAsync(productCategory);
|
||
}
|
||
catch (Exception ex)
|
||
{
|
||
logger.Error($"AuctionHub.UpdateProductCategoryIsFeaturedAsync(); categoryId: {categoryId}; productId: {productId}; isFeatured: {isFeatured}", ex);
|
||
}
|
||
}
|
||
|
||
public bool IsValidRequestAuctionStatus(AuctionStatus newStatus, AuctionStatus oldStatus)
|
||
{
|
||
switch (oldStatus)
|
||
{
|
||
case AuctionStatus.None:
|
||
return newStatus is AuctionStatus.Active or AuctionStatus.Pause;
|
||
case AuctionStatus.Active:
|
||
return newStatus is AuctionStatus.FirstWarning or AuctionStatus.Pause;
|
||
case AuctionStatus.FirstWarning:
|
||
return newStatus is AuctionStatus.SecondWarning or AuctionStatus.Pause;
|
||
case AuctionStatus.SecondWarning:
|
||
return newStatus is AuctionStatus.Sold or AuctionStatus.Pause;
|
||
case AuctionStatus.Pause:
|
||
return newStatus is AuctionStatus.None or AuctionStatus.Active;
|
||
case AuctionStatus.Sold:
|
||
case AuctionStatus.NotSold:
|
||
default:
|
||
return false;
|
||
}
|
||
}
|
||
#endregion
|
||
|
||
#region Methods
|
||
|
||
public static decimal GetStepAmount(decimal currentPrice)
|
||
{
|
||
return currentPrice switch
|
||
{
|
||
>= 0 and < 100000 => 10000,
|
||
|
||
//100 000 - 1 000 000
|
||
>= 100000 and < 200000 => 10000,
|
||
>= 200000 and < 500000 => 20000,
|
||
>= 500000 and < 1000000 => 50000,
|
||
|
||
//1 000 000 - 10 000 000
|
||
>= 1000000 and < 2000000 => 100000,
|
||
>= 2000000 and < 5000000 => 200000,
|
||
>= 5000000 and < 10000000 => 500000,
|
||
|
||
//10 000 000 - 100 000 000
|
||
>= 10000000 and < 20000000 => 1000000,
|
||
>= 20000000 and < 50000000 => 2000000,
|
||
>= 50000000 and < 100000000 => 5000000,
|
||
|
||
//100 000 000 - ~
|
||
>= 100000000 and < 200000000 => 10000000,
|
||
_ => 20000000
|
||
};
|
||
|
||
//100 000 Ft – 200 000 Ft között 10 000 Ft-tal
|
||
//200 000 Ft – 500 000 Ft között 20 000 Ft-tal
|
||
//500 000 Ft – 1 000 000 Ft között 50 000 Ft-tal
|
||
|
||
//1 000 000 Ft – 2 000 000 Ft között 100 000 Ft-tal
|
||
//2 000 000 Ft – 5 000 000 Ft között 200 000 Ft-tal
|
||
//5 000 000 Ft – 10 000 000 Ft között 500 000 Ft-tal
|
||
|
||
//10 000 000 Ft – 20 000 000 Ft között 1 000 000 Ft-tal
|
||
//20 000 000 Ft – 50 000 000 Ft között 2 000 000 Ft-tal
|
||
//50 000 000 Ft – 100 000 000 Ft között 5 000 000 Ft-tal
|
||
|
||
//100 000 000 Ft – 200 000 000 Ft között 10 000 000 Ft-tal
|
||
//200 000 000 Ft fölött 20 000 000 Ft-tal
|
||
}
|
||
|
||
public async Task<decimal> GetNextBidPrice(decimal currentBidPrice, int productToAuctionId) => GetNextBidPrice(currentBidPrice, GetStepAmount(currentBidPrice), await HasBidByProductToAuctionIdAsync(productToAuctionId));
|
||
|
||
public static decimal GetNextBidPrice(decimal currentBidPrice, bool hasAuctionBidInDb) => GetNextBidPrice(currentBidPrice, GetStepAmount(currentBidPrice), hasAuctionBidInDb);
|
||
|
||
public static decimal GetNextBidPrice(decimal currentBidPrice, decimal stepAmount, bool hasAuctionBidInDb)
|
||
{
|
||
return hasAuctionBidInDb ? currentBidPrice + stepAmount : currentBidPrice;
|
||
}
|
||
|
||
//public async Task ResetProductToAuctionByProductId(int productId)
|
||
// => await ResetProductToAuctionAsync(await ctx.ProductToAuctions.GetByProductId(productId).FirstOrDefaultAsync());
|
||
|
||
public Task ResetProductToAuctionByIdAsync(int productToAuctionId, decimal basePrice = 0)
|
||
=> ResetProductToAuctionAsync(ctx.ProductToAuctions.GetById(productToAuctionId), basePrice);
|
||
|
||
public Task ResetProductToAuctionAsync(ProductToAuctionMapping productToAuction, decimal basePrice = 0)
|
||
=> ctx.ResetProductToAuctionAsync(productToAuction, basePrice);
|
||
|
||
public Task<List<AuctionBid>> GetAllLastBidByAuctionIdAsync(int auctionId)
|
||
=> ctx.GetAllLastBidByAuctionIdAsync(auctionId);
|
||
|
||
public Task<Dictionary<int, AuctionBid>> GetAllLastBidDictionaryByAuctionIdAsync(int auctionId)
|
||
=> ctx.GetAllLastBidDictionaryByAuctionIdAsync(auctionId);
|
||
|
||
public Task<AuctionBid> GetLastAuctionBidByProductToAuctionIdAsync(int productToAuctionId)
|
||
=> ctx.GetLastAuctionBidByProductToAuctionId(productToAuctionId);
|
||
|
||
public Task<int> GetBidsCountByProductToAuctionIdAsync(int productToAuctionId)
|
||
=> ctx.GetBidsCountByProductToAuctionIdAsync(productToAuctionId);
|
||
|
||
public Task<bool> HasBidByProductToAuctionIdAsync(int productToAuctionId)
|
||
=> ctx.HasBidByProductToAuctionIdAsync(productToAuctionId);
|
||
|
||
public Task<AuctionBid> RevertAuctionBidByProductToAuctionIdAsync(int productToAuctionId)
|
||
=> ctx.RevertAuctionBidByProductToAuctionId(productToAuctionId);
|
||
|
||
public async Task<Product> GetProductById(int productId)
|
||
{
|
||
var product = await productService.GetProductByIdAsync(productId);
|
||
if (product != null) return product;
|
||
|
||
logger.Error($"AuctionService.GetProductById(); (product == null)", null, await workContext.GetCurrentCustomerAsync());
|
||
return null;
|
||
|
||
}
|
||
|
||
/// <summary>
|
||
/// Gets all bids
|
||
/// </summary>
|
||
/// <param name="customerId">The store identifier; pass 0 to load all records</param>
|
||
/// <param name="pageIndex">Page index</param>
|
||
/// <param name="pageSize">Page size</param>
|
||
/// <returns>
|
||
/// A task that represents the asynchronous operation
|
||
/// The task result contains the bids
|
||
/// </returns>
|
||
public async Task<IPagedList<AuctionBid>> GetAllBidsAsync(int customerId = 0, int pageIndex = 0, int pageSize = int.MaxValue)
|
||
{
|
||
//TODO: megcsinálni! - J.
|
||
|
||
var rez = new List<AuctionBid>();
|
||
//var rez = await _shortTermCacheManager.GetAsync(async () => await _customerBidRepository.GetAllAsync(query =>
|
||
//{
|
||
// if (customerId > 0)
|
||
// query = query.Where(bid => bid.CustomerId == customerId || bid.CustomerId == 0);
|
||
// query = query.OrderBy(bid => bid.CreateDate).ThenBy(bid => bid.ProductId);
|
||
|
||
// return query;
|
||
//}), _pickupPointAllKey, customerId);
|
||
|
||
return new PagedList<AuctionBid>(rez, pageIndex, pageSize);
|
||
}
|
||
|
||
public async Task<AuctionBid> GetBidByIdAsync(int bidId)
|
||
{
|
||
return await ctx.AuctionBids.GetByIdAsync(bidId);
|
||
}
|
||
|
||
public async Task InsertBidAsync(AuctionBid auctionBid)
|
||
{
|
||
//if (await ValidateAuctionBid(auctionBid))
|
||
{
|
||
await ctx.AuctionBids.InsertAsync(auctionBid, false);
|
||
}
|
||
}
|
||
|
||
public async Task UpdateBidAsync(AuctionBid auctionBid)
|
||
{
|
||
//if (await ValidateAuctionBid(auctionBid))
|
||
{
|
||
await ctx.AuctionBids.UpdateAsync(auctionBid, false);
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// Deletes a pickup point
|
||
/// </summary>
|
||
/// <param name="pickupPoint">Pickup point</param>
|
||
/// <returns>A task that represents the asynchronous operation</returns>
|
||
public async Task DeleteBidAsync(AuctionBid pickupPoint)
|
||
{
|
||
await ctx.AuctionBids.DeleteAsync(pickupPoint, false);
|
||
}
|
||
|
||
private async Task<Address> InsertOrUpdateBillingAddressAsync(Customer customer)
|
||
{
|
||
try
|
||
{
|
||
var billingAddress = await customerService.GetCustomerBillingAddressAsync(customer);
|
||
if (billingAddress == null)
|
||
{
|
||
billingAddress = CreateAddressFromCustomer(customer);
|
||
await addressService.InsertAddressAsync(billingAddress);
|
||
|
||
customer.ShippingAddressId = billingAddress.Id;
|
||
customer.BillingAddressId = billingAddress.Id;
|
||
|
||
await customerService.UpdateCustomerAsync(customer);
|
||
}
|
||
else
|
||
{
|
||
billingAddress = CopyAddressFromCustomer(billingAddress, customer);
|
||
await addressService.UpdateAddressAsync(billingAddress);
|
||
}
|
||
|
||
return billingAddress;
|
||
}
|
||
catch (Exception ex)
|
||
{
|
||
logger.Error($"AuctionService.InsertOrUpdateBillingAddress()", ex, customer);
|
||
}
|
||
|
||
return null;
|
||
}
|
||
|
||
private static Address CreateAddressFromCustomer(Customer customer)
|
||
{
|
||
var address = new Address();
|
||
|
||
return CopyAddressFromCustomer(address, customer);
|
||
}
|
||
|
||
private static Address CopyAddressFromCustomer(Address intoAddress, Customer customer)
|
||
{
|
||
intoAddress.FirstName = customer.FirstName;
|
||
intoAddress.LastName = customer.LastName;
|
||
intoAddress.Email = customer.Email;
|
||
intoAddress.FaxNumber = customer.Fax;
|
||
intoAddress.PhoneNumber = customer.Phone;
|
||
|
||
intoAddress.CountryId = customer.CountryId;
|
||
intoAddress.City = customer.City;
|
||
intoAddress.County = customer.County;
|
||
intoAddress.Address1 = customer.StreetAddress;
|
||
intoAddress.Address2 = customer.StreetAddress2;
|
||
intoAddress.StateProvinceId = customer.StateProvinceId;
|
||
intoAddress.ZipPostalCode = customer.ZipPostalCode;
|
||
|
||
intoAddress.Company = customer.Company;
|
||
|
||
return intoAddress;
|
||
}
|
||
|
||
public async Task<Order> CreateOrderForWinnerAsync(ProductToAuctionMapping productToAuction)
|
||
{
|
||
if (productToAuction is not { AuctionStatus: AuctionStatus.Sold })
|
||
{
|
||
await logger.InformationAsync($"AuctionService.CreateOrderForWinnerAsync(); (productToAuction is not {{ AuctionStatus: AuctionStatus.Sold }}); productToAuctionId: {productToAuction?.Id}; status: {productToAuction?.AuctionStatus}");
|
||
return null;
|
||
}
|
||
|
||
Customer currentCustomer = null;
|
||
|
||
try
|
||
{
|
||
currentCustomer = await workContext.GetCurrentCustomerAsync();
|
||
|
||
var winnerCustomer = await customerService.GetCustomerByIdAsync(productToAuction.WinnerCustomerId);
|
||
var storeId = winnerCustomer.RegisteredInStoreId;
|
||
|
||
var billingAddress = await InsertOrUpdateBillingAddressAsync(winnerCustomer);
|
||
if (billingAddress == null)
|
||
{
|
||
logger.Error($"AuctionService.CreateOrderForWinnerAsync(); (billingAddress == null); productToAuctionId: {productToAuction.Id}", null, currentCustomer);
|
||
return null;
|
||
}
|
||
|
||
var customValues = new Dictionary<string, object>
|
||
{
|
||
{ "PTAID", $"#{productToAuction.Id}" },
|
||
{ "AUKCIÓ", $"#{productToAuction.AuctionId}" },
|
||
{ "TÉTELSZÁM", $"#{productToAuction.SortIndex}" }
|
||
};
|
||
|
||
if (productToAuction.BiddingNumber != null) customValues.Add("BIDNUM", $"#{productToAuction.BiddingNumber}");
|
||
|
||
var orderTotal = productToAuction.CurrentPrice;
|
||
|
||
var order = CreateOrder(productToAuction, orderTotal, winnerCustomer, billingAddress, storeId, customValues);
|
||
await orderService.InsertOrderAsync(order);
|
||
|
||
if (order.Id > 0) productToAuction.OrderId = order.Id;
|
||
else
|
||
{
|
||
logger.Warning($"AuctionService.CreateOrderForWinnerAsync(); (order.Id <= 0); productToAuctionId: {productToAuction.Id}", null, currentCustomer);
|
||
return null;
|
||
}
|
||
|
||
var orderItem = CreateOrderItem(productToAuction, order, orderTotal);
|
||
await orderService.InsertOrderItemAsync(orderItem);
|
||
|
||
if (orderItem.Id > 0) productToAuction.OrderItemId = orderItem.Id;
|
||
else
|
||
{
|
||
logger.Warning($"AuctionService.CreateOrderForWinnerAsync(); (orderItem.Id <= 0); productToAuctionId: {productToAuction.Id}", null, currentCustomer);
|
||
return null;
|
||
}
|
||
|
||
//var orderNote = CreateOrderNote(order, "...");
|
||
//await orderService.InsertOrderNoteAsync(orderNote);
|
||
|
||
//if (orderNote.Id <= 0) logger.Warning($"AuctionService.CreateOrderForWinnerAsync(); (orderNote.Id <= 0); productToAuctionId: {productToAuction.Id}", null, currentCustomer); //TUDATOSAN NINCS RETURN - J.
|
||
|
||
return order;
|
||
}
|
||
catch (Exception ex)
|
||
{
|
||
logger.Error($"AuctionService.CreateOrderForWinnerAsync(); Exception; productToAuctionId: {productToAuction.Id}", ex, currentCustomer);
|
||
}
|
||
|
||
return null;
|
||
}
|
||
|
||
private static OrderItem CreateOrderItem(ProductToAuctionMapping productToAuction, Order order, decimal orderTotal)
|
||
{
|
||
return new OrderItem
|
||
{
|
||
ProductId = productToAuction.ProductId,
|
||
OrderId = order.Id,
|
||
OrderItemGuid = Guid.NewGuid(),
|
||
PriceExclTax = orderTotal,
|
||
PriceInclTax = orderTotal,
|
||
UnitPriceExclTax = orderTotal,
|
||
UnitPriceInclTax = orderTotal,
|
||
Quantity = productToAuction.ProductAmount,
|
||
};
|
||
}
|
||
|
||
private static Order CreateOrder(ProductToAuctionMapping productToAuction, decimal orderTotal, Customer customer, Address billingAddress, int storeId, Dictionary<string, object> customValues)
|
||
{
|
||
return new Order
|
||
{
|
||
BillingAddressId = billingAddress.Id,
|
||
CreatedOnUtc = DateTime.UtcNow,
|
||
CurrencyRate = 1,
|
||
CustomOrderNumber = productToAuction.AuctionId + "/" + productToAuction.SortIndex,
|
||
CustomValuesXml = SerializeCustomValuesToXml(customValues),
|
||
CustomerCurrencyCode = "HUF",
|
||
CustomerId = productToAuction.WinnerCustomerId,
|
||
CustomerLanguageId = 2,
|
||
CustomerTaxDisplayType = TaxDisplayType.IncludingTax,
|
||
OrderGuid = Guid.NewGuid(),
|
||
OrderStatus = OrderStatus.Pending,
|
||
OrderTotal = orderTotal,
|
||
PaymentStatus = PaymentStatus.Pending,
|
||
PaymentMethodSystemName = "Payments.CheckMoneyOrder",
|
||
ShippingStatus = ShippingStatus.ShippingNotRequired,
|
||
StoreId = storeId,
|
||
VatNumber = customer.VatNumber,
|
||
CustomerIp = customer.LastIpAddress,
|
||
OrderSubtotalExclTax = orderTotal,
|
||
OrderSubtotalInclTax = orderTotal
|
||
};
|
||
}
|
||
|
||
private static OrderNote CreateOrderNote(Order order, string note)
|
||
{
|
||
return new OrderNote
|
||
{
|
||
CreatedOnUtc = order.CreatedOnUtc,
|
||
DisplayToCustomer = true,
|
||
OrderId = order.Id,
|
||
Note = note
|
||
};
|
||
}
|
||
|
||
private static string SerializeCustomValuesToXml(Dictionary<string, object> sourceDictionary)
|
||
{
|
||
ArgumentNullException.ThrowIfNull(sourceDictionary);
|
||
|
||
if (!sourceDictionary.Any())
|
||
return null;
|
||
|
||
var ds = new DictionarySerializer(sourceDictionary);
|
||
var xs = new XmlSerializer(typeof(DictionarySerializer));
|
||
|
||
using var textWriter = new StringWriter();
|
||
using (var xmlWriter = XmlWriter.Create(textWriter))
|
||
{
|
||
xs.Serialize(xmlWriter, ds);
|
||
}
|
||
|
||
var result = textWriter.ToString();
|
||
return result;
|
||
}
|
||
|
||
#region auctions
|
||
|
||
public async Task InsertAuctionAsync(Auction auction)
|
||
{
|
||
await ctx.Auctions.InsertAsync(auction, false);
|
||
}
|
||
|
||
public async Task UpdateAuctionAsync(Auction auction)
|
||
{
|
||
await ctx.Auctions.UpdateAsync(auction);
|
||
}
|
||
|
||
public Task<List<Auction>> GetAllAuctionsAsync() => ctx.Auctions.GetAllAuctions().ToListAsync();
|
||
public Task<List<Auction>> GetAllCurrentAutoOpenAndClosedAuctionsAsync() => ctx.Auctions.GetAllCurrentAutoOpenAndClosedAuctions().ToListAsync();
|
||
|
||
public async Task<List<ProductToAuctionMapping>> GetProductToAuctionsByAuctionIdAsync(int auctionId, bool onlyActiveItems)
|
||
=> await ctx.ProductToAuctions.GetProductToAuctionsByAuctionId(auctionId, onlyActiveItems).OrderBy(x => x.SortIndex).ToListAsync();
|
||
|
||
public Task<ProductToAuctionMapping> GetNextProductToAuctionByAuctionIdAsync(int auctionId)
|
||
=> ctx.ProductToAuctions.GetNextItemByAuctionIdAsync(auctionId);
|
||
|
||
public Task<List<ProductToAuctionMapping>> GetNotClosedProductToAuctionsByAuctionId(int auctionId)
|
||
=> ctx.ProductToAuctions.GetNotClosedItemsByAuctionId(auctionId).OrderBy(x => x.SortIndex).ToListAsync();
|
||
|
||
#endregion
|
||
|
||
#endregion
|
||
|
||
#region Dtos
|
||
|
||
public async Task<AuctionDto> GetAuctionDtoWithAuctionBids(int auctionId, bool activeProductOnly, int maxBidsCount = int.MaxValue)
|
||
{
|
||
var auctionDto = await GetAuctionDtoByIdAsync(auctionId, true, activeProductOnly);
|
||
if (auctionDto == null) return null;
|
||
|
||
foreach (var auctionDtoProductToAuctionDto in auctionDto.ProductToAuctionDtos)
|
||
{
|
||
auctionDtoProductToAuctionDto.AuctionBidDtos.AddRange(await ctx.AuctionBids.GetAllByProductToAuctionId(auctionDtoProductToAuctionDto.Id).OrderByDescending(x => x.Id).Take(maxBidsCount).Select(x => new AuctionBidDto(x)).ToListAsync());
|
||
}
|
||
|
||
return auctionDto;
|
||
}
|
||
|
||
public async Task<Auction> GetAuctionByIdAsync(int auctionId) => await ctx.Auctions.GetByIdAsync(auctionId);
|
||
|
||
public async Task<AuctionDto> GetAuctionDtoByIdAsync(int auctionId, bool widthProducts, bool activeProductOnly)
|
||
{
|
||
var auction = await GetAuctionByIdAsync(auctionId);
|
||
if (auction == null) return null;
|
||
|
||
var auctionDto = new AuctionDto(auction);
|
||
if (widthProducts) auctionDto.ProductToAuctionDtos.AddRange((await GetProductToAuctionDtosByAuctionId(auctionId, activeProductOnly)));
|
||
|
||
return auctionDto;
|
||
}
|
||
|
||
public async Task<List<ProductToAuctionDto>> GetProductToAuctionDtosByAuctionId(int auctionId, bool activeProductOnly)
|
||
{
|
||
return (await GetProductToAuctionsByAuctionIdAsync(auctionId, activeProductOnly)).Select(x => new ProductToAuctionDto(x)).ToList();
|
||
}
|
||
|
||
public async Task<AuctionDto> GetAuctionDtoWithProductByIdAsync(int auctionId, int productId, bool activeProductOnly)
|
||
{
|
||
var auction = await ctx.Auctions.GetByIdAsync(auctionId);
|
||
if (auction == null) return null;
|
||
|
||
var auctionDto = new AuctionDto(auction);
|
||
auctionDto.ProductToAuctionDtos.AddRange((await GetProductToAuctionByAuctionIdAndProductIdAsync(auctionId, productId, activeProductOnly)).Select(x => new ProductToAuctionDto(x)));
|
||
|
||
return auctionDto;
|
||
}
|
||
|
||
public async Task<ProductToAuctionDto> GetProductToAuctionDtoByIdAsync(int productToAuctionId)
|
||
{
|
||
var productToAuction = await ctx.ProductToAuctions.GetByIdAsync(productToAuctionId);
|
||
return productToAuction == null ? null : new ProductToAuctionDto(productToAuction);
|
||
}
|
||
|
||
public async Task<AuctionDto> GetAuctionDtoByProductToAuctionIdAsync(int productToAuctionId, bool includeProductToAuctionDto)
|
||
{
|
||
var productTouctionDto = await GetProductToAuctionDtoByIdAsync(productToAuctionId);
|
||
if (productTouctionDto == null) return null;
|
||
|
||
var auctionDto = await GetAuctionDtoByIdAsync(productTouctionDto.AuctionId, false, false);
|
||
|
||
if (includeProductToAuctionDto) auctionDto.ProductToAuctionDtos.Add(productTouctionDto);
|
||
return auctionDto;
|
||
}
|
||
|
||
public async Task<List<ProductToAuctionDto>> GetProductToAuctionDtosByProductIdAsync(int productId)
|
||
{
|
||
return [..await ctx.ProductToAuctions.GetByProductId(productId).Select(x => new ProductToAuctionDto(x)).ToListAsync()];
|
||
}
|
||
|
||
public async Task<AuctionBidDto> GetAuctionBidDtoByIdAsync(int auctionBidId)
|
||
{
|
||
var auctionBid = await ctx.AuctionBids.GetByIdAsync(auctionBidId);
|
||
|
||
return auctionBid == null ? null : new AuctionBidDto(auctionBid);
|
||
}
|
||
|
||
public Task<List<ProductToAuctionMapping>> GetProductToAuctionsByProductIdAsync(int productId)
|
||
=> ctx.GetProductToAuctionsByProductIdAsync(productId);
|
||
|
||
public Task<List<ProductToAuctionMapping>> GetProductToAuctionByAuctionIdAndProductIdAsync(int auctionId, int productId, bool activeProductOnly)
|
||
=> ctx.GetProductToAuctionByAuctionIdAndProductIdAsync(auctionId, productId, activeProductOnly);
|
||
|
||
|
||
public async Task<ProductToAuctionMapping> AssignProductToAuctionAsync(int productId, decimal startingPrice, decimal bidPrice, int auctionId, int sortIndex)
|
||
{
|
||
var auction = await GetAuctionDtoByIdAsync(auctionId, false, false);
|
||
if (auction == null)
|
||
return null;
|
||
|
||
//TODO: itt a ProductToAuctionMapping.Id-t kellene használni! - J.
|
||
var existedProductToAuction = (await GetProductToAuctionByAuctionIdAndProductIdAsync(auctionId, productId, false)).FirstOrDefault();
|
||
if (existedProductToAuction != null) return existedProductToAuction;
|
||
|
||
var mapping = new ProductToAuctionMapping
|
||
{
|
||
ProductId = productId,
|
||
StartingPrice = startingPrice,
|
||
CurrentPrice = bidPrice,
|
||
ProductAmount = 1,
|
||
SortIndex = sortIndex,
|
||
AuctionStatus = AuctionStatus.None,
|
||
AuctionId = auctionId
|
||
};
|
||
|
||
try
|
||
{
|
||
await ctx.ProductToAuctions.InsertAsync(mapping);
|
||
}
|
||
catch (Exception ex)
|
||
{
|
||
await logger.InformationAsync(ex.ToString());
|
||
}
|
||
|
||
return mapping;
|
||
}
|
||
|
||
public async Task<ProductToAuctionMapping> GetProductToAuctionMappingByIdAsync(int productToAuctionMappingId)
|
||
{
|
||
return await ctx.ProductToAuctions.GetByIdAsync(productToAuctionMappingId);
|
||
}
|
||
|
||
public async Task UpdateProductToAuctionAsync(ProductToAuctionMapping productToAuctionMapping)
|
||
{
|
||
await ctx.ProductToAuctions.UpdateAsync(productToAuctionMapping);
|
||
}
|
||
|
||
public async Task UpdateProductToAuctionAsync(IList<ProductToAuctionMapping> productToAuctionMappings)
|
||
{
|
||
await ctx.ProductToAuctions.UpdateAsync(productToAuctionMappings);
|
||
}
|
||
|
||
#endregion Dtos
|
||
} |