Add phase 1 critical import tool
This commit is contained in:
133
src/RolemasterDb.ImportTool/CriticalImportLoader.cs
Normal file
133
src/RolemasterDb.ImportTool/CriticalImportLoader.cs
Normal file
@@ -0,0 +1,133 @@
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
|
||||
using RolemasterDb.App.Data;
|
||||
using RolemasterDb.App.Domain;
|
||||
using RolemasterDb.ImportTool.Parsing;
|
||||
|
||||
namespace RolemasterDb.ImportTool;
|
||||
|
||||
public sealed class CriticalImportLoader(string databasePath)
|
||||
{
|
||||
public async Task<int> ResetCriticalsAsync(CancellationToken cancellationToken = default)
|
||||
{
|
||||
await using var dbContext = CreateDbContext();
|
||||
await dbContext.Database.EnsureCreatedAsync(cancellationToken);
|
||||
|
||||
var removedTableCount = await dbContext.CriticalTables.CountAsync(cancellationToken);
|
||||
await using var transaction = await dbContext.Database.BeginTransactionAsync(cancellationToken);
|
||||
|
||||
await dbContext.CriticalResults.ExecuteDeleteAsync(cancellationToken);
|
||||
await dbContext.CriticalGroups.ExecuteDeleteAsync(cancellationToken);
|
||||
await dbContext.CriticalColumns.ExecuteDeleteAsync(cancellationToken);
|
||||
await dbContext.CriticalRollBands.ExecuteDeleteAsync(cancellationToken);
|
||||
await dbContext.CriticalTables.ExecuteDeleteAsync(cancellationToken);
|
||||
|
||||
await transaction.CommitAsync(cancellationToken);
|
||||
return removedTableCount;
|
||||
}
|
||||
|
||||
public async Task<ImportCommandResult> LoadAsync(ParsedCriticalTable table, CancellationToken cancellationToken = default)
|
||||
{
|
||||
await using var dbContext = CreateDbContext();
|
||||
await dbContext.Database.EnsureCreatedAsync(cancellationToken);
|
||||
await using var transaction = await dbContext.Database.BeginTransactionAsync(cancellationToken);
|
||||
|
||||
await DeleteTableAsync(dbContext, table.Slug, cancellationToken);
|
||||
|
||||
var entity = new CriticalTable
|
||||
{
|
||||
Slug = table.Slug,
|
||||
DisplayName = table.DisplayName,
|
||||
Family = table.Family,
|
||||
SourceDocument = table.SourceDocument,
|
||||
Notes = table.Notes
|
||||
};
|
||||
|
||||
entity.Columns = table.Columns
|
||||
.Select(item => new CriticalColumn
|
||||
{
|
||||
ColumnKey = item.ColumnKey,
|
||||
Label = item.Label,
|
||||
Role = item.Role,
|
||||
SortOrder = item.SortOrder
|
||||
})
|
||||
.ToList();
|
||||
|
||||
entity.RollBands = table.RollBands
|
||||
.Select(item => new CriticalRollBand
|
||||
{
|
||||
Label = item.Label,
|
||||
MinRoll = item.MinRoll,
|
||||
MaxRoll = item.MaxRoll,
|
||||
SortOrder = item.SortOrder
|
||||
})
|
||||
.ToList();
|
||||
|
||||
var columnsByKey = entity.Columns.ToDictionary(item => item.ColumnKey, StringComparer.OrdinalIgnoreCase);
|
||||
var rollBandsByLabel = entity.RollBands.ToDictionary(item => item.Label, StringComparer.OrdinalIgnoreCase);
|
||||
|
||||
entity.Results = table.Results
|
||||
.Select(item => new CriticalResult
|
||||
{
|
||||
CriticalColumn = columnsByKey[item.ColumnKey],
|
||||
CriticalRollBand = rollBandsByLabel[item.RollBandLabel],
|
||||
RawCellText = item.RawCellText,
|
||||
DescriptionText = item.DescriptionText,
|
||||
RawAffixText = item.RawAffixText,
|
||||
ParsedJson = "{}",
|
||||
ParseStatus = "raw"
|
||||
})
|
||||
.ToList();
|
||||
|
||||
dbContext.CriticalTables.Add(entity);
|
||||
await dbContext.SaveChangesAsync(cancellationToken);
|
||||
await transaction.CommitAsync(cancellationToken);
|
||||
|
||||
return new ImportCommandResult(entity.Slug, entity.Columns.Count, entity.RollBands.Count, entity.Results.Count);
|
||||
}
|
||||
|
||||
private RolemasterDbContext CreateDbContext()
|
||||
{
|
||||
var options = new DbContextOptionsBuilder<RolemasterDbContext>()
|
||||
.UseSqlite($"Data Source={databasePath}")
|
||||
.Options;
|
||||
|
||||
return new RolemasterDbContext(options);
|
||||
}
|
||||
|
||||
private static async Task DeleteTableAsync(
|
||||
RolemasterDbContext dbContext,
|
||||
string slug,
|
||||
CancellationToken cancellationToken)
|
||||
{
|
||||
var tableId = await dbContext.CriticalTables
|
||||
.Where(item => item.Slug == slug)
|
||||
.Select(item => (int?)item.Id)
|
||||
.SingleOrDefaultAsync(cancellationToken);
|
||||
|
||||
if (tableId is null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
await dbContext.CriticalResults
|
||||
.Where(item => item.CriticalTableId == tableId.Value)
|
||||
.ExecuteDeleteAsync(cancellationToken);
|
||||
|
||||
await dbContext.CriticalGroups
|
||||
.Where(item => item.CriticalTableId == tableId.Value)
|
||||
.ExecuteDeleteAsync(cancellationToken);
|
||||
|
||||
await dbContext.CriticalColumns
|
||||
.Where(item => item.CriticalTableId == tableId.Value)
|
||||
.ExecuteDeleteAsync(cancellationToken);
|
||||
|
||||
await dbContext.CriticalRollBands
|
||||
.Where(item => item.CriticalTableId == tableId.Value)
|
||||
.ExecuteDeleteAsync(cancellationToken);
|
||||
|
||||
await dbContext.CriticalTables
|
||||
.Where(item => item.Id == tableId.Value)
|
||||
.ExecuteDeleteAsync(cancellationToken);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user