diff --git a/src/main/java/org/codetracker/BlockTrackerChangeHistory.java b/src/main/java/org/codetracker/BlockTrackerChangeHistory.java index bffe2905177..9523d4c7495 100644 --- a/src/main/java/org/codetracker/BlockTrackerChangeHistory.java +++ b/src/main/java/org/codetracker/BlockTrackerChangeHistory.java @@ -8,6 +8,7 @@ import java.util.Set; import java.util.function.Predicate; +import org.apache.commons.lang3.tuple.Pair; import org.codetracker.api.History; import org.codetracker.api.History.HistoryInfo; import org.codetracker.api.Version; @@ -126,6 +127,63 @@ public boolean checkClassDiffForBlockChange(Version currentVersion, Version pare return false; } + public boolean isMergeMultiMapping(Version currentVersion, Version parentVersion, Predicate equalMethod, Block rightBlock, List refactorings) { + Set> mappings = new LinkedHashSet<>(); + AbstractCodeFragment fragment2 = null; + int fragment2Matches = 0; + MergeOperationRefactoring mergeOperationRefactoring = null; + for (Refactoring refactoring : refactorings) { + switch (refactoring.getRefactoringType()) { + case MERGE_OPERATION: { + mergeOperationRefactoring = (MergeOperationRefactoring) refactoring; + Method methodAfter = Method.of(mergeOperationRefactoring.getNewMethodAfterMerge(), currentVersion); + if (equalMethod.test(methodAfter)) { + for (UMLOperationBodyMapper bodyMapper : mergeOperationRefactoring.getMappers()) { + for (AbstractCodeMapping mapping : bodyMapper.getMappings()) { + if (mapping instanceof CompositeStatementObjectMapping) { + Block matchedBlockInsideMergedMethodBody = Block.of((CompositeStatementObject) mapping.getFragment2(), bodyMapper.getContainer2(), currentVersion); + if (matchedBlockInsideMergedMethodBody.equalIdentifierIgnoringVersion(rightBlock)) { + Block blockBefore = Block.of((CompositeStatementObject) mapping.getFragment1(), bodyMapper.getContainer1(), parentVersion); + mappings.add(Pair.of(blockBefore, matchedBlockInsideMergedMethodBody)); + if (fragment2 == null) { + fragment2 = mapping.getFragment2(); + } + else if (fragment2.equals(mapping.getFragment2())) { + fragment2Matches++; + } + } + } + else if (mapping instanceof LeafMapping && mapping.getFragment1() instanceof StatementObject && mapping.getFragment2() instanceof StatementObject) { + Block matchedBlockInsideMergedMethodBody = Block.of((StatementObject) mapping.getFragment2(), bodyMapper.getContainer2(), currentVersion); + if (matchedBlockInsideMergedMethodBody.equalIdentifierIgnoringVersion(rightBlock)) { + Block blockBefore = Block.of((StatementObject) mapping.getFragment1(), bodyMapper.getContainer1(), parentVersion); + mappings.add(Pair.of(blockBefore, matchedBlockInsideMergedMethodBody)); + if (fragment2 == null) { + fragment2 = mapping.getFragment2(); + } + else if (fragment2.equals(mapping.getFragment2())) { + fragment2Matches++; + } + } + } + } + } + } + break; + } + } + } + if (mappings.size() > 1 && mappings.size() == fragment2Matches + 1) { + for (Pair pair : mappings) { + blockChangeHistory.handleAdd(pair.getLeft(), pair.getRight(), mergeOperationRefactoring.toString()); + elements.add(pair.getLeft()); + } + blockChangeHistory.connectRelatedNodes(); + return true; + } + return false; + } + public boolean checkForExtractionOrInline(Version currentVersion, Version parentVersion, Predicate equalMethod, Block rightBlock, List refactorings) { int extractMatches = 0; for (Refactoring refactoring : refactorings) { diff --git a/src/main/java/org/codetracker/FileTrackerImpl.java b/src/main/java/org/codetracker/FileTrackerImpl.java index 04e94ba469d..7d723ea0e11 100644 --- a/src/main/java/org/codetracker/FileTrackerImpl.java +++ b/src/main/java/org/codetracker/FileTrackerImpl.java @@ -983,7 +983,11 @@ private void processLocallyRefactoredMethods(Map