Re-adding BasketQueryService
This commit is contained in:
12
src/ApplicationCore/Interfaces/IBasketQueryService.cs
Normal file
12
src/ApplicationCore/Interfaces/IBasketQueryService.cs
Normal file
@@ -0,0 +1,12 @@
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Microsoft.eShopWeb.ApplicationCore.Interfaces;
|
||||
|
||||
/// <summary>
|
||||
/// Specific query used to fetch count without running in memory
|
||||
/// </summary>
|
||||
public interface IBasketQueryService
|
||||
{
|
||||
Task<int> CountTotalBasketItems(string username);
|
||||
}
|
||||
|
||||
31
src/Infrastructure/Data/Queries/BasketQueryService.cs
Normal file
31
src/Infrastructure/Data/Queries/BasketQueryService.cs
Normal file
@@ -0,0 +1,31 @@
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using Microsoft.eShopWeb.ApplicationCore.Interfaces;
|
||||
|
||||
namespace Microsoft.eShopWeb.Infrastructure.Data.Queries;
|
||||
|
||||
public class BasketQueryService : IBasketQueryService
|
||||
{
|
||||
private readonly CatalogContext _dbContext;
|
||||
|
||||
public BasketQueryService(CatalogContext dbContext)
|
||||
{
|
||||
_dbContext = dbContext;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This method performs the sum on the database rather than in memory
|
||||
/// </summary>
|
||||
/// <param name="username"></param>
|
||||
/// <returns></returns>
|
||||
public async Task<int> CountTotalBasketItems(string username)
|
||||
{
|
||||
var totalItems = await _dbContext.Baskets
|
||||
.Where(basket => basket.BuyerId == username)
|
||||
.SelectMany(item => item.Items)
|
||||
.SumAsync(sum => sum.Quantity);
|
||||
|
||||
return totalItems;
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,7 @@
|
||||
using Microsoft.eShopWeb.ApplicationCore.Interfaces;
|
||||
using Microsoft.eShopWeb.ApplicationCore.Services;
|
||||
using Microsoft.eShopWeb.Infrastructure.Data;
|
||||
using Microsoft.eShopWeb.Infrastructure.Data.Queries;
|
||||
using Microsoft.eShopWeb.Infrastructure.Logging;
|
||||
using Microsoft.eShopWeb.Infrastructure.Services;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
@@ -18,6 +19,7 @@ public static class ConfigureCoreServices
|
||||
|
||||
services.AddScoped<IBasketService, BasketService>();
|
||||
services.AddScoped<IOrderService, OrderService>();
|
||||
services.AddScoped<IBasketQueryService, BasketQueryService>();
|
||||
services.AddSingleton<IUriComposer>(new UriComposer(configuration.Get<CatalogSettings>()));
|
||||
services.AddScoped(typeof(IAppLogger<>), typeof(LoggerAdapter<>));
|
||||
services.AddTransient<IEmailSender, EmailSender>();
|
||||
|
||||
@@ -7,5 +7,6 @@ namespace Microsoft.eShopWeb.Web.Interfaces;
|
||||
public interface IBasketViewModelService
|
||||
{
|
||||
Task<BasketViewModel> GetOrCreateBasketForUser(string userName);
|
||||
Task<int> CountTotalBasketItems(string username);
|
||||
Task<BasketViewModel> Map(Basket basket);
|
||||
}
|
||||
|
||||
@@ -2,27 +2,21 @@
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNetCore.Identity;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.eShopWeb.ApplicationCore.Interfaces;
|
||||
using Microsoft.eShopWeb.ApplicationCore.Specifications;
|
||||
using Microsoft.eShopWeb.Infrastructure.Identity;
|
||||
using Microsoft.eShopWeb.Web.Interfaces;
|
||||
using Microsoft.eShopWeb.Web.ViewModels;
|
||||
using BasketEntity = Microsoft.eShopWeb.ApplicationCore.Entities.BasketAggregate.Basket;
|
||||
|
||||
namespace Microsoft.eShopWeb.Web.Pages.Shared.Components.BasketComponent;
|
||||
|
||||
public class Basket : ViewComponent
|
||||
{
|
||||
private readonly IBasketViewModelService _basketViewModelService;
|
||||
private readonly IReadRepository<BasketEntity> _basketRepository;
|
||||
private readonly IBasketViewModelService _basketService;
|
||||
private readonly SignInManager<ApplicationUser> _signInManager;
|
||||
|
||||
public Basket(IBasketViewModelService basketViewModelService,
|
||||
IReadRepository<BasketEntity> basketRepository,
|
||||
public Basket(IBasketViewModelService basketService,
|
||||
SignInManager<ApplicationUser> signInManager)
|
||||
{
|
||||
_basketViewModelService = basketViewModelService;
|
||||
_basketRepository = basketRepository;
|
||||
_basketService = basketService;
|
||||
_signInManager = signInManager;
|
||||
}
|
||||
|
||||
@@ -39,26 +33,18 @@ public class Basket : ViewComponent
|
||||
{
|
||||
if (_signInManager.IsSignedIn(HttpContext.User))
|
||||
{
|
||||
var userNameSpec = new BasketWithItemsSpecification(User.Identity.Name);
|
||||
|
||||
var userBasket = await _basketRepository.GetBySpecAsync(userNameSpec);
|
||||
if (userBasket == null) return 0;
|
||||
return userBasket.TotalItems;
|
||||
return await _basketService.CountTotalBasketItems(User.Identity.Name);
|
||||
}
|
||||
|
||||
string anonymousId = GetAnnonymousIdFromCookie();
|
||||
if (anonymousId == null)
|
||||
return 0;
|
||||
|
||||
var anonymousSpec = new BasketWithItemsSpecification(anonymousId);
|
||||
var anonymousBasket = await _basketRepository.GetBySpecAsync(anonymousSpec);
|
||||
if (anonymousBasket == null) return 0;
|
||||
return anonymousBasket.TotalItems;
|
||||
return await _basketService.CountTotalBasketItems(anonymousId);
|
||||
}
|
||||
|
||||
private string GetAnnonymousIdFromCookie()
|
||||
{
|
||||
// TODO: Add a prefix to anonymous cookie values so they cannot collide with user names
|
||||
if (Request.Cookies.ContainsKey(Constants.BASKET_COOKIENAME))
|
||||
{
|
||||
var id = Request.Cookies[Constants.BASKET_COOKIENAME];
|
||||
|
||||
@@ -14,14 +14,17 @@ public class BasketViewModelService : IBasketViewModelService
|
||||
{
|
||||
private readonly IRepository<Basket> _basketRepository;
|
||||
private readonly IUriComposer _uriComposer;
|
||||
private readonly IReadRepository<CatalogItem> _itemRepository;
|
||||
private readonly IBasketQueryService _basketQueryService;
|
||||
private readonly IRepository<CatalogItem> _itemRepository;
|
||||
|
||||
public BasketViewModelService(IRepository<Basket> basketRepository,
|
||||
IReadRepository<CatalogItem> itemRepository,
|
||||
IUriComposer uriComposer)
|
||||
IRepository<CatalogItem> itemRepository,
|
||||
IUriComposer uriComposer,
|
||||
IBasketQueryService basketQueryService)
|
||||
{
|
||||
_basketRepository = basketRepository;
|
||||
_uriComposer = uriComposer;
|
||||
_basketQueryService = basketQueryService;
|
||||
_itemRepository = itemRepository;
|
||||
}
|
||||
|
||||
@@ -83,4 +86,11 @@ public class BasketViewModelService : IBasketViewModelService
|
||||
Items = await GetBasketItems(basket.Items)
|
||||
};
|
||||
}
|
||||
|
||||
public async Task<int> CountTotalBasketItems(string username)
|
||||
{
|
||||
var counter = await _basketQueryService.CountTotalBasketItems(username);
|
||||
|
||||
return counter;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user