Add category ladders

This commit is contained in:
Mbucari 2023-07-17 16:50:45 -06:00
parent 90eccbf2f6
commit ea6adeb58f
23 changed files with 983 additions and 122 deletions

View file

@ -99,20 +99,6 @@ namespace DtoImporterService
.Select(n => contributorImporter.Cache[n.Name])
.ToList();
// categories are laid out for a breadcrumb. category is 1st, subcategory is 2nd
// absence of categories is also possible
// CATEGORY HACK: only use the 1st 2 categories
// after we support full arbitrary-depth category trees and multiple categories per book, the real impl will be something like this
// var lastCategory = item.Categories.LastOrDefault()?.CategoryId ?? "";
var lastCategory
= item.Categories.Length == 0 ? ""
: item.Categories.Length == 1 ? item.Categories[0].CategoryId
// 2+
: item.Categories[1].CategoryId;
var category = categoryImporter.Cache[lastCategory];
Book book;
try
{
@ -125,7 +111,6 @@ namespace DtoImporterService
contentType,
authors,
narrators,
category,
importItem.LocaleName)
).Entity;
Cache.Add(book.AudibleProductId, book);
@ -140,7 +125,6 @@ namespace DtoImporterService
contentType,
QtyAuthors = authors?.Count,
QtyNarrators = narrators?.Count,
Category = category?.Name,
importItem.LocaleName
});
throw;
@ -201,6 +185,17 @@ namespace DtoImporterService
book.UpsertSeries(series, seriesEntry.Sequence);
}
}
if (item.CategoryLadders is not null)
{
foreach (var ladder in item.CategoryLadders.Select(cl => cl.Ladder).Where(l => l?.Length > 0))
{
var categoryIds = ladder.Select(l => l.CategoryId).ToList();
var cata = categoryImporter.LadderCache.Single(c => c.Equals(categoryIds));
book.UpsertCategories(cata);
}
}
}
private static DataLayer.ContentType GetContentType(Item item)

View file

@ -12,7 +12,8 @@ namespace DtoImporterService
{
protected override IValidator Validator => new CategoryValidator();
public Dictionary<string, Category> Cache { get; private set; } = new();
private Dictionary<string, Category> Cache { get; set; } = new();
public HashSet<DataLayer.CategoryLadder> LadderCache { get; private set; } = new();
public CategoryImporter(LibationContext context) : base(context) { }
@ -30,44 +31,39 @@ namespace DtoImporterService
loadLocal_categories(categoryIds);
// upsert
var categoryPairs = importItems
.Select(i => i.DtoItem)
.GetCategoryPairsDistinct()
var categoryLadders = importItems
.SelectMany(i => i.DtoItem.CategoryLadders)
.Select(cl => cl.Ladder)
.Where(l => l?.Length > 0)
.ToList();
var qtyNew = upsertCategories(categoryPairs);
var qtyNew = upsertCategories(categoryLadders);
return qtyNew;
}
private void loadLocal_categories(List<string> categoryIds)
{
// must include default/empty/missing
categoryIds.Add(Category.GetEmpty().AudibleCategoryId);
// load existing => local
Cache = DbContext.Categories
.Where(c => categoryIds.Contains(c.AudibleCategoryId))
.ToDictionarySafe(c => c.AudibleCategoryId);
LadderCache = DbContext.CategoryLadders.ToHashSet();
}
// only use after loading contributors => local
private int upsertCategories(List<Ladder[]> categoryPairs)
private int upsertCategories(List<Ladder[]> ladders)
{
var qtyNew = 0;
foreach (var pair in categoryPairs)
foreach (var ladder in ladders)
{
for (var i = 0; i < pair.Length; i++)
var categories = new List<Category>(ladder.Length);
for (var i = 0; i < ladder.Length; i++)
{
// CATEGORY HACK: not yet supported: depth beyond 0 and 1
if (i > 1)
break;
var id = pair[i].CategoryId;
var name = pair[i].CategoryName;
Category parentCategory = null;
if (i == 1)
Cache.TryGetValue(pair[0].CategoryId, out parentCategory);
var id = ladder[i].CategoryId;
var name = ladder[i].CategoryName;
if (!Cache.TryGetValue(id, out var category))
{
@ -75,13 +71,37 @@ namespace DtoImporterService
qtyNew++;
}
category.UpdateParentCategory(parentCategory);
categories.Add(category);
}
var categoryLadder = new DataLayer.CategoryLadder(categories);
if (!LadderCache.Contains(categoryLadder))
{
addCategoryLadder(categoryLadder);
qtyNew++;
}
}
return qtyNew;
}
private DataLayer.CategoryLadder addCategoryLadder(DataLayer.CategoryLadder categoryList)
{
try
{
var entityEntry = DbContext.CategoryLadders.Add(categoryList);
var entity = entityEntry.Entity;
LadderCache.Add(entity);
return entity;
}
catch (Exception ex)
{
Serilog.Log.Logger.Error(ex, "Error adding category ladder. {@DebugInfo}", categoryList);
throw;
}
}
private Category addCategory(string id, string name)
{
try