Reuse document indexes in D&D normalization

This commit is contained in:
2026-07-25 13:01:31 +00:00
parent 97cdb01357
commit 8199d95dc1
10 changed files with 48 additions and 64 deletions

View File

@@ -97,9 +97,10 @@ func (n *Normalizer) Normalize(ctx context.Context, req contracts.TypedNormalize
return contracts.TypedNormalizeResult[dnd.SpellList]{}, normalizerErrorf("context error before normalize: %w", err)
}
order := shared.NewSourceRefOrder(req.Source)
index := source.NewDocumentIndex(req.Source)
order := shared.NewSourceRefOrderWithIndex(req.Source, index)
value, warnings := normalizeSpellList(req.MergeOutput.Value, n.effectiveCatalog, order)
value, duplicateWarnings := collapseDuplicateSpellCasts(value, req.Source, n.effectiveCatalog)
value, duplicateWarnings := collapseDuplicateSpellCasts(value, index, n.effectiveCatalog)
warnings = append(warnings, duplicateWarnings...)
return contracts.TypedNormalizeResult[dnd.SpellList]{Value: value, Warnings: warnings}, nil
}
@@ -173,7 +174,7 @@ type duplicateGroup struct {
removed []int
}
func collapseDuplicateSpellCasts(input dnd.SpellList, doc *source.SourceDocument, catalog spellcatalog.EffectiveCatalog) (dnd.SpellList, []contracts.Warning) {
func collapseDuplicateSpellCasts(input dnd.SpellList, documentIndex source.DocumentIndex, catalog spellcatalog.EffectiveCatalog) (dnd.SpellList, []contracts.Warning) {
if len(input.SpellCasts) == 0 {
return input, nil
}
@@ -182,7 +183,7 @@ func collapseDuplicateSpellCasts(input dnd.SpellList, doc *source.SourceDocument
groups := make([]duplicateGroup, 0)
groupByKey := make(map[string]int)
for index, cast := range input.SpellCasts {
key, eligible := duplicateKey(cast, doc, catalog)
key, eligible := duplicateKey(cast, documentIndex, catalog)
if !eligible {
keep[index] = true
continue
@@ -225,13 +226,13 @@ func collapseDuplicateSpellCasts(input dnd.SpellList, doc *source.SourceDocument
return output, warnings
}
func duplicateKey(cast dnd.SpellCast, doc *source.SourceDocument, catalog spellcatalog.EffectiveCatalog) (string, bool) {
func duplicateKey(cast dnd.SpellCast, documentIndex source.DocumentIndex, catalog spellcatalog.EffectiveCatalog) (string, bool) {
canonicalName, resolved := catalog.Lookup(cast.Spell)
if !resolved || len(cast.SourceRefs) == 0 {
return "", false
}
for _, ref := range cast.SourceRefs {
if source.ValidateRef(doc, ref) != nil {
if documentIndex.ValidateRef(ref) != nil {
return "", false
}
}