diff --git a/src/applications/differential/xaction/DifferentialRevisionCommandeerTransaction.php b/src/applications/differential/xaction/DifferentialRevisionCommandeerTransaction.php index 5aafa536f3..a296597bc7 100644 --- a/src/applications/differential/xaction/DifferentialRevisionCommandeerTransaction.php +++ b/src/applications/differential/xaction/DifferentialRevisionCommandeerTransaction.php @@ -1,98 +1,108 @@ getAuthorPHID(); } public function generateNewValue($object, $value) { $actor = $this->getActor(); return $actor->getPHID(); } public function applyInternalEffects($object, $value) { $object->setAuthorPHID($value); } protected function validateAction($object, PhabricatorUser $viewer) { - if ($object->isClosed()) { + // If a revision has already landed, we generally want to discourage + // reopening and reusing it since this tends to create a big mess (users + // should create a new revision instead). Thus, we stop you from + // commandeering closed revisions. + + // See PHI985. If the revision was abandoned, there's no peril in allowing + // the commandeer since the change (likely) never actually landed. So + // it's okay to commandeer abandoned revisions. + + if ($object->isClosed() && !$object->isAbandoned()) { throw new Exception( pht( 'You can not commandeer this revision because it has already '. - 'been closed. You can only commandeer open revisions.')); + 'been closed. You can only commandeer open or abandoned '. + 'revisions.')); } if ($this->isViewerRevisionAuthor($object, $viewer)) { throw new Exception( pht( 'You can not commandeer this revision because you are already '. 'the author.')); } } public function getTitle() { return pht( '%s commandeered this revision.', $this->renderAuthor()); } public function getTitleForFeed() { return pht( '%s commandeered %s.', $this->renderAuthor(), $this->renderObject()); } public function getTransactionTypeForConduit($xaction) { return 'commandeer'; } public function getFieldValuesForConduit($object, $data) { return array(); } }