Page Menu
Home
Phabricator
Search
Configure Global Search
Log In
Files
F15331585
D21396.id.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Flag For Later
Size
9 KB
Referenced Files
None
Subscribers
None
D21396.id.diff
View Options
diff --git a/src/repository/marker/ArcanistMarkerRef.php b/src/repository/marker/ArcanistMarkerRef.php
--- a/src/repository/marker/ArcanistMarkerRef.php
+++ b/src/repository/marker/ArcanistMarkerRef.php
@@ -9,6 +9,8 @@
const TYPE_BRANCH = 'branch';
const TYPE_BOOKMARK = 'bookmark';
+ const TYPE_COMMIT_STATE = 'commit-state';
+ const TYPE_BRANCH_STATE = 'branch-state';
private $name;
private $markerType;
@@ -148,6 +150,14 @@
return ($this->getMarkerType() === self::TYPE_BRANCH);
}
+ public function isCommitState() {
+ return ($this->getMarkerType() === self::TYPE_COMMIT_STATE);
+ }
+
+ public function isBranchState() {
+ return ($this->getMarkerType() === self::TYPE_BRANCH_STATE);
+ }
+
public function attachCommitRef(ArcanistCommitRef $ref) {
return $this->attachHardpoint(self::HARDPOINT_COMMITREF, $ref);
}
diff --git a/src/repository/marker/ArcanistMercurialRepositoryMarkerQuery.php b/src/repository/marker/ArcanistMercurialRepositoryMarkerQuery.php
--- a/src/repository/marker/ArcanistMercurialRepositoryMarkerQuery.php
+++ b/src/repository/marker/ArcanistMercurialRepositoryMarkerQuery.php
@@ -71,10 +71,6 @@
}
$node = $item['node'];
- if (!$node) {
- // NOTE: For now, we ignore the virtual "current branch" marker.
- continue;
- }
switch ($item['type']) {
case 'branch':
@@ -83,8 +79,11 @@
case 'bookmark':
$marker_type = ArcanistMarkerRef::TYPE_BOOKMARK;
break;
- case 'commit':
- $marker_type = null;
+ case 'commit-state':
+ $marker_type = ArcanistMarkerRef::TYPE_COMMIT_STATE;
+ break;
+ case 'branch-state':
+ $marker_type = ArcanistMarkerRef::TYPE_BRANCH_STATE;
break;
default:
throw new Exception(
@@ -94,11 +93,6 @@
$item['type']));
}
- if ($marker_type === null) {
- // NOTE: For now, we ignore the virtual "head" marker.
- continue;
- }
-
$commit_ref = $api->newCommitRef()
->setCommitHash($node);
diff --git a/src/repository/state/ArcanistMercurialLocalState.php b/src/repository/state/ArcanistMercurialLocalState.php
--- a/src/repository/state/ArcanistMercurialLocalState.php
+++ b/src/repository/state/ArcanistMercurialLocalState.php
@@ -5,40 +5,105 @@
private $localCommit;
private $localBranch;
+ private $localBookmark;
protected function executeSaveLocalState() {
$api = $this->getRepositoryAPI();
$log = $this->getWorkflow()->getLogEngine();
- // TODO: Both of these can be pulled from "hg arc-ls-markers" more
- // efficiently.
-
- $this->localCommit = $api->getCanonicalRevisionName('.');
-
- list($branch) = $api->execxLocal('branch');
- $this->localBranch = trim($branch);
-
- $log->writeTrace(
- pht('SAVE STATE'),
- pht(
+ $markers = $api->newMarkerRefQuery()
+ ->execute();
+
+ $local_commit = null;
+ foreach ($markers as $marker) {
+ if ($marker->isCommitState()) {
+ $local_commit = $marker->getCommitHash();
+ }
+ }
+
+ if ($local_commit === null) {
+ throw new Exception(
+ pht(
+ 'Unable to identify the current commit in the working copy.'));
+ }
+
+ $this->localCommit = $local_commit;
+
+ $local_branch = null;
+ foreach ($markers as $marker) {
+ if ($marker->isBranchState()) {
+ $local_branch = $marker->getName();
+ break;
+ }
+ }
+
+ if ($local_branch === null) {
+ throw new Exception(
+ pht(
+ 'Unable to identify the current branch in the working copy.'));
+ }
+
+ if ($local_branch !== null) {
+ $this->localBranch = $local_branch;
+ }
+
+ $local_bookmark = null;
+ foreach ($markers as $marker) {
+ if ($marker->isBookmark()) {
+ if ($marker->getIsActive()) {
+ $local_bookmark = $marker->getName();
+ break;
+ }
+ }
+ }
+
+ if ($local_bookmark !== null) {
+ $this->localBookmark = $local_bookmark;
+ }
+
+ $has_bookmark = ($this->localBookmark !== null);
+
+ if ($has_bookmark) {
+ $location = pht(
+ 'Saving local state (at "%s" on branch "%s", bookmarked as "%s").',
+ $api->getDisplayHash($this->localCommit),
+ $this->localBranch,
+ $this->localBookmark);
+ } else {
+ $location = pht(
'Saving local state (at "%s" on branch "%s").',
$api->getDisplayHash($this->localCommit),
- $this->localBranch));
+ $this->localBranch);
+ }
+
+ $log->writeTrace(pht('SAVE STATE'), $location);
}
protected function executeRestoreLocalState() {
$api = $this->getRepositoryAPI();
$log = $this->getWorkflow()->getLogEngine();
- $log->writeStatus(
- pht('LOAD STATE'),
- pht(
+ if ($this->localBookmark !== null) {
+ $location = pht(
+ 'Restoring local state (at "%s" on branch "%s", bookmarked as "%s").',
+ $api->getDisplayHash($this->localCommit),
+ $this->localBranch,
+ $this->localBookmark);
+ } else {
+ $location = pht(
'Restoring local state (at "%s" on branch "%s").',
$api->getDisplayHash($this->localCommit),
- $this->localBranch));
+ $this->localBranch);
+ }
+
+ $log->writeStatus(pht('LOAD STATE'), $location);
$api->execxLocal('update -- %s', $this->localCommit);
$api->execxLocal('branch --force -- %s', $this->localBranch);
+
+ if ($this->localBookmark !== null) {
+ $api->execxLocal('bookmark --force -- %s', $this->localBookmark);
+ }
}
protected function executeDiscardLocalState() {
@@ -70,6 +135,12 @@
'hg branch --force -- %s',
$this->localBranch);
+ if ($this->localBookmark !== null) {
+ $commands[] = csprintf(
+ 'hg bookmark --force -- %s',
+ $this->localBookmark);
+ }
+
return $commands;
}
diff --git a/support/hg/arc-hg.py b/support/hg/arc-hg.py
--- a/support/hg/arc-hg.py
+++ b/support/hg/arc-hg.py
@@ -85,21 +85,17 @@
active_node = repo[b'.'].node()
all_heads = set(repo.heads())
current_name = repo.dirstate.branch()
- saw_current = False
- saw_active = False
branch_list = repo.branchmap().iterbranches()
for branch_name, branch_heads, tip_node, is_closed in branch_list:
for head_node in branch_heads:
- is_active = (head_node == active_node)
- is_tip = (head_node == tip_node)
- is_current = (branch_name == current_name)
- if is_current:
- saw_current = True
+ is_active = False
+ if branch_name == current_name:
+ if head_node == active_node:
+ is_active = True
- if is_active:
- saw_active = True
+ is_tip = (head_node == tip_node)
if is_closed:
head_closed = True
@@ -115,26 +111,9 @@
'isActive': is_active,
'isClosed': head_closed,
'isTip': is_tip,
- 'isCurrent': is_current,
'description': description,
})
- # If the current branch (selected with "hg branch X") is not reflected in
- # the list of heads we selected, add a virtual head for it so callers get
- # a complete picture of repository marker state.
-
- if not saw_current:
- markers.append({
- 'type': 'branch',
- 'name': current_name,
- 'node': None,
- 'isActive': False,
- 'isClosed': False,
- 'isTip': False,
- 'isCurrent': True,
- 'description': None,
- })
-
bookmarks = repo._bookmarks
active_bookmark = repo._activebookmark
@@ -142,9 +121,6 @@
is_active = (active_bookmark == bookmark_name)
description = repo[bookmark_node].description()
- if is_active:
- saw_active = True
-
markers.append({
'type': 'bookmark',
'name': bookmark_name,
@@ -153,21 +129,36 @@
'description': description,
})
- # If the current working copy state is not the head of a branch and there is
- # also no active bookmark, add a virtual marker for it so callers can figure
- # out exactly where we are.
-
- if not saw_active:
- markers.append({
- 'type': 'commit',
- 'name': None,
- 'node': node.hex(active_node),
- 'isActive': False,
- 'isClosed': False,
- 'isTip': False,
- 'isCurrent': True,
- 'description': repo[b'.'].description(),
- })
+ # Add virtual markers for the current commit state and current branch state
+ # so callers can figure out exactly where we are.
+
+ # Common cases where this matters include:
+
+ # You run "hg update 123" to update to an older revision. Your working
+ # copy commit will not be a branch head or a bookmark.
+
+ # You run "hg branch X" to create a new branch, but have not made any commits
+ # yet. Your working copy branch will not be reflected in any commits.
+
+ markers.append({
+ 'type': 'branch-state',
+ 'name': current_name,
+ 'node': None,
+ 'isActive': True,
+ 'isClosed': False,
+ 'isTip': False,
+ 'description': None,
+ })
+
+ markers.append({
+ 'type': 'commit-state',
+ 'name': None,
+ 'node': node.hex(active_node),
+ 'isActive': True,
+ 'isClosed': False,
+ 'isTip': False,
+ 'description': repo[b'.'].description(),
+ })
return markers
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Sat, Mar 8, 11:40 AM (2 w, 2 d ago)
Storage Engine
blob
Storage Format
Encrypted (AES-256-CBC)
Storage Handle
7381797
Default Alt Text
D21396.id.diff (9 KB)
Attached To
Mode
D21396: When saving and restoring local state in Mercurial, also save and restore bookmarks
Attached
Detach File
Event Timeline
Log In to Comment