Changeset View
Changeset View
Standalone View
Standalone View
src/workflow/ArcanistAmendWorkflow.php
| Show First 20 Lines • Show All 61 Lines • ▼ Show 20 Lines | EOTEXT | ||||
| public function run() { | public function run() { | ||||
| $is_show = $this->getArgument('show'); | $is_show = $this->getArgument('show'); | ||||
| $repository_api = $this->getRepositoryAPI(); | $repository_api = $this->getRepositoryAPI(); | ||||
| if (!$is_show) { | if (!$is_show) { | ||||
| if (!$repository_api->supportsAmend()) { | if (!$repository_api->supportsAmend()) { | ||||
| throw new ArcanistUsageException( | throw new ArcanistUsageException( | ||||
| "You may only run 'arc amend' in a git or hg (version ". | pht( | ||||
| "2.2 or newer) working copy."); | "You may only run '%s' in a git or hg ". | ||||
| "(version 2.2 or newer) working copy.", | |||||
| 'arc amend')); | |||||
| } | } | ||||
| if ($this->isHistoryImmutable()) { | if ($this->isHistoryImmutable()) { | ||||
| throw new ArcanistUsageException( | throw new ArcanistUsageException( | ||||
| pht( | |||||
| 'This project is marked as adhering to a conservative history '. | 'This project is marked as adhering to a conservative history '. | ||||
| 'mutability doctrine (having an immutable local history), which '. | 'mutability doctrine (having an immutable local history), which '. | ||||
| 'precludes amending commit messages.'); | 'precludes amending commit messages.')); | ||||
| } | } | ||||
| if ($repository_api->getUncommittedChanges()) { | if ($repository_api->getUncommittedChanges()) { | ||||
| throw new ArcanistUsageException( | throw new ArcanistUsageException( | ||||
| 'You have uncommitted changes in this branch. Stage and commit (or '. | pht( | ||||
| 'revert) them before proceeding.'); | 'You have uncommitted changes in this branch. Stage and commit '. | ||||
| '(or revert) them before proceeding.')); | |||||
| } | } | ||||
| } | } | ||||
| $revision_id = null; | $revision_id = null; | ||||
| if ($this->getArgument('revision')) { | if ($this->getArgument('revision')) { | ||||
| $revision_id = $this->normalizeRevisionID($this->getArgument('revision')); | $revision_id = $this->normalizeRevisionID($this->getArgument('revision')); | ||||
| } | } | ||||
| $repository_api->setBaseCommitArgumentRules('arc:this'); | $repository_api->setBaseCommitArgumentRules('arc:this'); | ||||
| $in_working_copy = $repository_api->loadWorkingCopyDifferentialRevisions( | $in_working_copy = $repository_api->loadWorkingCopyDifferentialRevisions( | ||||
| $this->getConduit(), | $this->getConduit(), | ||||
| array( | array( | ||||
| 'status' => 'status-any', | 'status' => 'status-any', | ||||
| )); | )); | ||||
| $in_working_copy = ipull($in_working_copy, null, 'id'); | $in_working_copy = ipull($in_working_copy, null, 'id'); | ||||
| if (!$revision_id) { | if (!$revision_id) { | ||||
| if (count($in_working_copy) == 0) { | if (count($in_working_copy) == 0) { | ||||
| throw new ArcanistUsageException( | throw new ArcanistUsageException( | ||||
| "No revision specified with '--revision', and no revisions found ". | pht( | ||||
| "in the working copy. Use '--revision <id>' to specify which ". | "No revision specified with '%s', and no revisions found ". | ||||
| "revision you want to amend."); | "in the working copy. Use '%s' to specify which revision ". | ||||
| "you want to amend.", | |||||
| '--revision', | |||||
| '--revision <id>')); | |||||
| } else if (count($in_working_copy) > 1) { | } else if (count($in_working_copy) > 1) { | ||||
| $message = "More than one revision was found in the working copy:\n". | $message = pht( | ||||
| $this->renderRevisionList($in_working_copy)."\n". | "More than one revision was found in the working copy:\n%s\n". | ||||
| "Use '--revision <id>' to specify which revision you want to ". | "Use '%s' to specify which revision you want to amend.", | ||||
| "amend."; | $this->renderRevisionList($in_working_copy), | ||||
| '--revision <id>'); | |||||
| throw new ArcanistUsageException($message); | throw new ArcanistUsageException($message); | ||||
| } else { | } else { | ||||
| $revision_id = key($in_working_copy); | $revision_id = key($in_working_copy); | ||||
| $revision = $in_working_copy[$revision_id]; | $revision = $in_working_copy[$revision_id]; | ||||
| if ($revision['authorPHID'] != $this->getUserPHID()) { | if ($revision['authorPHID'] != $this->getUserPHID()) { | ||||
| $other_author = $this->getConduit()->callMethodSynchronous( | $other_author = $this->getConduit()->callMethodSynchronous( | ||||
| 'user.query', | 'user.query', | ||||
| array( | array( | ||||
| 'phids' => array($revision['authorPHID']), | 'phids' => array($revision['authorPHID']), | ||||
| )); | )); | ||||
| $other_author = ipull($other_author, 'userName', 'phid'); | $other_author = ipull($other_author, 'userName', 'phid'); | ||||
| $other_author = $other_author[$revision['authorPHID']]; | $other_author = $other_author[$revision['authorPHID']]; | ||||
| $rev_title = $revision['title']; | $rev_title = $revision['title']; | ||||
| $ok = phutil_console_confirm( | $ok = phutil_console_confirm( | ||||
| "You are amending the revision 'D{$revision_id}: {$rev_title}' ". | pht( | ||||
| "but you are not the author. Amend this revision by ". | "You are amending the revision '%s' but you are not ". | ||||
| "{$other_author}?"); | "the author. Amend this revision by %s?", | ||||
| "D{$revision_id}: {$rev_title}", | |||||
| $other_author)); | |||||
| if (!$ok) { | if (!$ok) { | ||||
| throw new ArcanistUserAbortException(); | throw new ArcanistUserAbortException(); | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| $conduit = $this->getConduit(); | $conduit = $this->getConduit(); | ||||
| try { | try { | ||||
| $message = $conduit->callMethodSynchronous( | $message = $conduit->callMethodSynchronous( | ||||
| 'differential.getcommitmessage', | 'differential.getcommitmessage', | ||||
| array( | array( | ||||
| 'revision_id' => $revision_id, | 'revision_id' => $revision_id, | ||||
| 'edit' => false, | 'edit' => false, | ||||
| )); | )); | ||||
| } catch (ConduitClientException $ex) { | } catch (ConduitClientException $ex) { | ||||
| if (strpos($ex->getMessage(), 'ERR_NOT_FOUND') === false) { | if (strpos($ex->getMessage(), 'ERR_NOT_FOUND') === false) { | ||||
| throw $ex; | throw $ex; | ||||
| } else { | } else { | ||||
| throw new ArcanistUsageException( | throw new ArcanistUsageException( | ||||
| "Revision D{$revision_id} does not exist." | pht("Revision '%s' does not exist.", "D{$revision_id}") | ||||
| ); | ); | ||||
| } | } | ||||
| } | } | ||||
| $revision = $conduit->callMethodSynchronous( | $revision = $conduit->callMethodSynchronous( | ||||
| 'differential.query', | 'differential.query', | ||||
| array( | array( | ||||
| 'ids' => array($revision_id), | 'ids' => array($revision_id), | ||||
| )); | )); | ||||
| if (empty($revision)) { | if (empty($revision)) { | ||||
| throw new Exception( | throw new Exception( | ||||
| "Failed to lookup information for 'D{$revision_id}'!"); | pht("Failed to lookup information for '%s'!", "D{$revision_id}")); | ||||
| } | } | ||||
| $revision = head($revision); | $revision = head($revision); | ||||
| $revision_title = $revision['title']; | $revision_title = $revision['title']; | ||||
| if (!$is_show) { | if (!$is_show) { | ||||
| if ($revision_id && empty($in_working_copy[$revision_id])) { | if ($revision_id && empty($in_working_copy[$revision_id])) { | ||||
| $ok = phutil_console_confirm( | $ok = phutil_console_confirm( | ||||
| "The revision 'D{$revision_id}' does not appear to be in the ". | pht( | ||||
| "working copy. Are you sure you want to amend HEAD with the ". | "The revision '%s' does not appear to be in the working copy. Are ". | ||||
| "commit message for 'D{$revision_id}: {$revision_title}'?"); | "you sure you want to amend HEAD with the commit message for '%s'?", | ||||
| "D{$revision_id}", | |||||
| "D{$revision_id}: {$revision_title}")); | |||||
| if (!$ok) { | if (!$ok) { | ||||
| throw new ArcanistUserAbortException(); | throw new ArcanistUserAbortException(); | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| if ($is_show) { | if ($is_show) { | ||||
| echo $message."\n"; | echo $message."\n"; | ||||
| } else { | } else { | ||||
| echo phutil_console_format( | echo pht( | ||||
| "Amending commit message to reflect revision **%s**.\n", | "Amending commit message to reflect revision %s.\n", | ||||
| "D{$revision_id}: {$revision_title}"); | phutil_console_format( | ||||
| '**D%d: %s**', | |||||
| $revision_id, | |||||
| $revision_title)); | |||||
| $repository_api->amendCommit($message); | $repository_api->amendCommit($message); | ||||
| } | } | ||||
| return 0; | return 0; | ||||
| } | } | ||||
| public function getSupportedRevisionControlSystems() { | public function getSupportedRevisionControlSystems() { | ||||
| return array('git', 'hg'); | return array('git', 'hg'); | ||||
| } | } | ||||
| } | } | ||||