1. Use 'hg log -r 0:source --prune dest' to find common parent for pulled and local changes. Otherwise locally committed files were in the tree.
2. IDEA-68774 : if revisions passed to 'hg status' are equal, then there was nothing to update => don't get the changed files.
3. Remove adding to MODIFIED, LOCALLY_DELETED groups since they are nothing to do with Update Info.
[reviewed by irengrig]
--- /dev/null
+/*
+ * Copyright 2000-2011 JetBrains s.r.o.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.zmlx.hg4idea.command;
+
+import com.intellij.openapi.project.Project;
+import org.zmlx.hg4idea.HgRevisionNumber;
+
+import java.util.List;
+
+/**
+ * Returns the changesets which are about to be merged.
+ * Equivalent to "hg merge --preview" or "hg log -r 0:source --prune dest"
+ * but the latest allows templates.
+ *
+ * @author Kirill Likhodedov
+ */
+public class HgMergePreviewCommand extends HgChangesetsCommand {
+
+ private final HgRevisionNumber mySource;
+ private final HgRevisionNumber myDest;
+ private final int myLimit;
+
+ public HgMergePreviewCommand(Project project, HgRevisionNumber source, HgRevisionNumber dest, int limit) {
+ super(project, "log");
+ mySource = source;
+ myDest = dest;
+ myLimit = limit;
+ }
+
+ @Override
+ protected void addArguments(List<String> args) {
+ args.add("-r");
+ args.add("0:" + mySource.getChangeset());
+ args.add("--prune");
+ args.add(myDest.getChangeset());
+ args.add("--limit");
+ args.add(String.valueOf(myLimit));
+ }
+
+}
* @param silent pass true if this command shouldn't be mentioned in the VCS console.
* @return List of revisions.
*/
- private List<HgRevisionNumber> getRevisions(@NotNull VirtualFile repo,
+ public @NotNull List<HgRevisionNumber> getRevisions(@NotNull VirtualFile repo,
@NotNull String command,
@Nullable FilePath file,
@Nullable HgRevisionNumber revision,
import com.intellij.openapi.project.Project;
import com.intellij.openapi.vcs.VcsException;
import com.intellij.openapi.vcs.history.VcsRevisionNumber;
-import com.intellij.openapi.vcs.update.FileGroup;
import com.intellij.openapi.vcs.update.UpdatedFiles;
import com.intellij.openapi.vfs.VirtualFile;
import org.jetbrains.annotations.NotNull;
-import org.zmlx.hg4idea.HgChange;
-import org.zmlx.hg4idea.HgFile;
-import org.zmlx.hg4idea.util.HgUtil;
-import org.zmlx.hg4idea.HgVcs;
-import org.zmlx.hg4idea.execution.HgCommandResult;
import org.zmlx.hg4idea.command.HgMergeCommand;
-import org.zmlx.hg4idea.command.HgStatusCommand;
+import org.zmlx.hg4idea.execution.HgCommandResult;
+import org.zmlx.hg4idea.util.HgUtil;
import java.lang.reflect.InvocationTargetException;
-import java.util.Set;
import static org.zmlx.hg4idea.HgErrorHandler.ensureSuccess;
throwException(e);
}
- HgStatusCommand hgStatusCommand = new HgStatusCommand(project);
- hgStatusCommand.setIncludeIgnored(false);
- hgStatusCommand.setIncludeUnknown(false);
- Set<HgChange> changes = hgStatusCommand.execute(repo);
- if (!changes.isEmpty()) {
- for (HgChange change : changes) {
- HgFile afterFile = change.afterFile();
- HgFile beforeFile = change.beforeFile();
- String fileGroupId = null;
- String filePath = null;
- if (afterFile != null && beforeFile != null) {
- fileGroupId = FileGroup.MODIFIED_ID;
- filePath = afterFile.getFile().getAbsolutePath();
- } else if (beforeFile != null) {
- fileGroupId = FileGroup.LOCALLY_REMOVED_ID;
- filePath = beforeFile.getFile().getAbsolutePath();
- } else if (afterFile != null) {
- fileGroupId = FileGroup.LOCALLY_ADDED_ID;
- filePath = afterFile.getFile().getAbsolutePath();
- }
- if (fileGroupId != null && filePath != null) {
- updatedFiles.getGroupById(fileGroupId).add(filePath, HgVcs.VCS_NAME, revisionNumber);
- }
- }
- }
return commandResult;
}
import com.intellij.openapi.vfs.VirtualFile;
import org.apache.commons.lang.StringUtils;
import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
import org.zmlx.hg4idea.*;
import org.zmlx.hg4idea.command.*;
import org.zmlx.hg4idea.execution.HgCommandException;
return true;
}
- private List<HgRevisionNumber> determingRemainingOriginalBranchHeads(List<HgRevisionNumber> branchHeadsBeforePull, List<HgRevisionNumber> branchHeadsAfterPull) {
+ private List<HgRevisionNumber> determingRemainingOriginalBranchHeads(List<HgRevisionNumber> branchHeadsBeforePull, List<HgRevisionNumber> branchHeadsAfterPull) {
List<HgRevisionNumber> originalBranchHeadsRemaining = new ArrayList<HgRevisionNumber>();
for (HgRevisionNumber headAfterPull : branchHeadsAfterPull) {
if (branchHeadsBeforePull.contains(headAfterPull)) {
updateCommand.setClean(true);
updateCommand.execute();
- HgRevisionNumber parentAfterUpdate = new HgWorkingCopyRevisionsCommand(project).firstParent(repo);
- addUpdatedFiles(repo, updatedFiles, parentBeforeUpdate, parentAfterUpdate);
+ HgRevisionNumber commonParent = findCommonParent(newHead, parentBeforeUpdate);
+ addUpdatedFiles(repo, updatedFiles, commonParent, newHead);
+ }
+
+ private @Nullable HgRevisionNumber findCommonParent(HgRevisionNumber newHead, HgRevisionNumber parentBeforeUpdate) {
+ // hg log -r 0:source --prune dest --limit 1
+ final List<HgRevisionNumber> pulledRevisions = new HgMergePreviewCommand(project, newHead, parentBeforeUpdate, 1).execute(repository);
+ if (pulledRevisions == null || pulledRevisions.isEmpty()) {
+ return null;
+ }
+ HgRevisionNumber pulledRevision = pulledRevisions.get(0);
+ final List<HgRevisionNumber> parentRevisions = new HgWorkingCopyRevisionsCommand(project).getRevisions(repository, "parent", null, pulledRevision, true);
+ if (parentRevisions.isEmpty()) {
+ return null;
+ }
+ return parentRevisions.get(0);
}
private void commitOrWarnAboutConflicts(List<VcsException> exceptions, HgCommandResult mergeResult) throws VcsException {
throw new VcsException(e);
}
} else {
- reportWarning(exceptions, HgVcsMessages.message("hg4idea.update.warning.merge.conflicts", repository.getPath()));
+ reportWarning(exceptions, HgVcsMessages.message("hg4idea.update.warning.merge.conflicts", repository.getPath()));
+ }
}
- }
private HgCommandResult doMerge(UpdatedFiles updatedFiles, ProgressIndicator indicator, List<VcsException> exceptions, HgRevisionNumber headToMerge) throws VcsException {
indicator.setText2(HgVcsMessages.message("hg4idea.update.progress.merging"));
//two heads in this branch
// mergeCommand.setRevision(headToMerge.getRevision());
HgCommandResult mergeResult = new HgHeadMerger(project, mergeCommand).merge(repository, updatedFiles, headToMerge);
- handlePossibleWarning(exceptions, mergeResult.getWarnings());
return mergeResult;
}
}
private void addUpdatedFiles(VirtualFile repo, UpdatedFiles updatedFiles, HgRevisionNumber parentBeforeUpdate, HgRevisionNumber parentAfterUpdate) {
+ if (parentAfterUpdate == null || parentBeforeUpdate == null) {
+ return;
+ }
+ if (parentAfterUpdate.equals(parentBeforeUpdate)) { // nothing to update => returning not to capture local uncommitted changes
+ return;
+ }
HgStatusCommand statusCommand = new HgStatusCommand(project);
statusCommand.setBaseRevision(parentBeforeUpdate);
statusCommand.setTargetRevision(parentAfterUpdate);