List<CommitChange> (@NotNull Collection<Change> changes) { List<CommitChange> result = new ArrayList<>(); MultiMap<VirtualFile, CommitChange> map = new MultiMap<>(); for (Change change : changes) { CommitChange commitChange = createCommitChange(change); if (commitChange.virtualFile != null) { map.putValue(commitChange.virtualFile, commitChange); } else { result.add(commitChange); } } for (Map.Entry<VirtualFile, Collection<CommitChange>> entry : map.entrySet()) { VirtualFile virtualFile = entry.getKey(); Collection<CommitChange> fileCommitChanges = entry.getValue(); if (fileCommitChanges.size() < 2) { result.addAll(fileCommitChanges); continue; } boolean hasSpecificChangelists = exists(fileCommitChanges, change -> change.changelistIds != null); if (!hasSpecificChangelists) { result.addAll(fileCommitChanges); continue; } boolean hasNonChangelists = exists(fileCommitChanges, change -> change.changelistIds == null); boolean hasDeletions = exists(fileCommitChanges, change -> change.afterPath == null); boolean hasAdditions = exists(fileCommitChanges, change -> change.beforePath == null); if (hasNonChangelists || hasDeletions) { LOG.warn(String.format("Ignoring changelists on commit of %s: %s", virtualFile, fileCommitChanges)); result.addAll(map(fileCommitChanges, change -> new CommitChange(change.beforePath, change.afterPath, change.beforeRevision, change.afterRevision, null, change.virtualFile))); continue; } CommitChange firstChange = getFirstItem(fileCommitChanges); FilePath beforePath = hasAdditions ? null : firstChange.beforePath; FilePath afterPath = firstChange.afterPath; VcsRevisionNumber beforeRevision = firstChange.beforeRevision; VcsRevisionNumber afterRevision = firstChange.afterRevision; Set<String> combinedChangeListIds = new HashSet<>(); boolean hasMismatch = false; for (CommitChange change : fileCommitChanges) { combinedChangeListIds.addAll(notNullize(change.changelistIds)); if (!Objects.equals(beforePath, change.beforePath) || !Objects.equals(afterPath, change.afterPath)) { // VcsRevisionNumber mismatch is not that important hasMismatch = true; } } if (hasMismatch) { LOG.error(String.format("Change mismatch on commit of %s: %s", virtualFile, fileCommitChanges)); } result.add(new CommitChange(beforePath, afterPath, beforeRevision, afterRevision, new ArrayList<>(combinedChangeListIds), virtualFile)); } return result; }