AnalysisScoreDiff.java
package com.taxonomy.portfolio.service;
import com.taxonomy.dto.AnalysisResult;
import com.taxonomy.dto.AnalysisScoreDetail;
import com.taxonomy.dto.AnalysisScoreKind;
import com.taxonomy.portfolio.dto.PortfolioDtos.ScoreChange;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.TreeSet;
/** Builds a deterministic snapshot diff over effective values and their complete score meaning. */
final class AnalysisScoreDiff {
private AnalysisScoreDiff() {
}
static Map<String, ScoreChange> between(
AnalysisResult older,
AnalysisResult newer) {
Map<String, Integer> oldEffective = safeScores(older == null ? null : older.getScores());
Map<String, Integer> newEffective = safeScores(newer == null ? null : newer.getScores());
Map<String, Integer> oldRaw = safeScores(older == null ? null : older.getRawScores());
Map<String, Integer> newRaw = safeScores(newer == null ? null : newer.getRawScores());
Map<String, AnalysisScoreDetail> oldDetails =
safeDetails(older == null ? null : older.getScoreDetails());
Map<String, AnalysisScoreDetail> newDetails =
safeDetails(newer == null ? null : newer.getScoreDetails());
Set<String> codes = new TreeSet<>();
codes.addAll(oldEffective.keySet());
codes.addAll(newEffective.keySet());
codes.addAll(oldRaw.keySet());
codes.addAll(newRaw.keySet());
codes.addAll(oldDetails.keySet());
codes.addAll(newDetails.keySet());
Map<String, ScoreChange> changes = new LinkedHashMap<>();
for (String code : codes) {
AnalysisScoreDetail oldDetail = oldDetails.get(code);
AnalysisScoreDetail newDetail = newDetails.get(code);
Integer oldEffectiveValue = oldEffective.get(code);
Integer newEffectiveValue = newEffective.get(code);
Integer oldRawValue = rawValue(oldRaw.get(code), oldDetail);
Integer newRawValue = rawValue(newRaw.get(code), newDetail);
AnalysisScoreKind oldKind = oldDetail == null ? null : oldDetail.kind();
AnalysisScoreKind newKind = newDetail == null ? null : newDetail.kind();
String oldParentCode = oldDetail == null ? null : oldDetail.parentCode();
String newParentCode = newDetail == null ? null : newDetail.parentCode();
Integer oldParentScore = oldDetail == null ? null : oldDetail.parentScore();
Integer newParentScore = newDetail == null ? null : newDetail.parentScore();
if (Objects.equals(oldEffectiveValue, newEffectiveValue)
&& Objects.equals(oldRawValue, newRawValue)
&& oldKind == newKind
&& Objects.equals(oldParentCode, newParentCode)
&& Objects.equals(oldParentScore, newParentScore)) {
continue;
}
changes.put(code, new ScoreChange(
oldEffectiveValue,
newEffectiveValue,
oldRawValue,
newRawValue,
oldKind,
newKind,
oldParentCode,
newParentCode,
oldParentScore,
newParentScore));
}
return Collections.unmodifiableMap(new LinkedHashMap<>(changes));
}
private static Integer rawValue(
Integer rawScore,
AnalysisScoreDetail detail) {
if (detail != null) {
return detail.rawScore();
}
return rawScore;
}
private static Map<String, Integer> safeScores(Map<String, Integer> scores) {
return scores == null ? Map.of() : scores;
}
private static Map<String, AnalysisScoreDetail> safeDetails(
Map<String, AnalysisScoreDetail> details) {
return details == null ? Map.of() : details;
}
}