1
0
Fork 0
mirror of https://we.phorge.it/source/phorge.git synced 2024-12-23 22:10:55 +01:00

Modular Transactions for Badges

Summary: Ref T12270. This converts Badges to modular transactions for editing and awarding.

Test Plan: Add Badge, edit badge, award and revoke... Still going to test this some more but feel free to comment on anything obviously wrong?

Reviewers: epriestley

Reviewed By: epriestley

Subscribers: Korvin

Maniphest Tasks: T12270

Differential Revision: https://secure.phabricator.com/D17402
This commit is contained in:
Chad Little 2017-02-23 14:22:43 -08:00
parent ee2d8ce94b
commit 3eae9a368d
17 changed files with 488 additions and 438 deletions

View file

@ -2012,7 +2012,16 @@ phutil_register_library_map(array(
'PhabricatorBadgesAwardController' => 'applications/badges/controller/PhabricatorBadgesAwardController.php',
'PhabricatorBadgesAwardQuery' => 'applications/badges/query/PhabricatorBadgesAwardQuery.php',
'PhabricatorBadgesBadge' => 'applications/badges/storage/PhabricatorBadgesBadge.php',
'PhabricatorBadgesBadgeAwardTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeAwardTransaction.php',
'PhabricatorBadgesBadgeDescriptionTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeDescriptionTransaction.php',
'PhabricatorBadgesBadgeFlavorTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeFlavorTransaction.php',
'PhabricatorBadgesBadgeIconTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeIconTransaction.php',
'PhabricatorBadgesBadgeNameNgrams' => 'applications/badges/storage/PhabricatorBadgesBadgeNameNgrams.php',
'PhabricatorBadgesBadgeNameTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeNameTransaction.php',
'PhabricatorBadgesBadgeQualityTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeQualityTransaction.php',
'PhabricatorBadgesBadgeRevokeTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeRevokeTransaction.php',
'PhabricatorBadgesBadgeStatusTransaction' => 'applications/badges/xaction/PhabricatorBadgesBadgeStatusTransaction.php',
'PhabricatorBadgesBadgeTransactionType' => 'applications/badges/xaction/PhabricatorBadgesBadgeTransactionType.php',
'PhabricatorBadgesCommentController' => 'applications/badges/controller/PhabricatorBadgesCommentController.php',
'PhabricatorBadgesController' => 'applications/badges/controller/PhabricatorBadgesController.php',
'PhabricatorBadgesCreateCapability' => 'applications/badges/capability/PhabricatorBadgesCreateCapability.php',
@ -6954,7 +6963,16 @@ phutil_register_library_map(array(
'PhabricatorConduitResultInterface',
'PhabricatorNgramsInterface',
),
'PhabricatorBadgesBadgeAwardTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeDescriptionTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeFlavorTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeIconTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeNameNgrams' => 'PhabricatorSearchNgrams',
'PhabricatorBadgesBadgeNameTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeQualityTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeRevokeTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeStatusTransaction' => 'PhabricatorBadgesBadgeTransactionType',
'PhabricatorBadgesBadgeTransactionType' => 'PhabricatorModularTransactionType',
'PhabricatorBadgesCommentController' => 'PhabricatorBadgesController',
'PhabricatorBadgesController' => 'PhabricatorController',
'PhabricatorBadgesCreateCapability' => 'PhabricatorPolicyCapability',
@ -6980,7 +6998,7 @@ phutil_register_library_map(array(
'PhabricatorBadgesSchemaSpec' => 'PhabricatorConfigSchemaSpec',
'PhabricatorBadgesSearchConduitAPIMethod' => 'PhabricatorSearchEngineAPIMethod',
'PhabricatorBadgesSearchEngine' => 'PhabricatorApplicationSearchEngine',
'PhabricatorBadgesTransaction' => 'PhabricatorApplicationTransaction',
'PhabricatorBadgesTransaction' => 'PhabricatorModularTransaction',
'PhabricatorBadgesTransactionComment' => 'PhabricatorApplicationTransactionComment',
'PhabricatorBadgesTransactionQuery' => 'PhabricatorApplicationTransactionQuery',
'PhabricatorBadgesViewController' => 'PhabricatorBadgesProfileController',

View file

@ -32,7 +32,8 @@ final class PhabricatorBadgesArchiveController
$xactions = array();
$xactions[] = id(new PhabricatorBadgesTransaction())
->setTransactionType(PhabricatorBadgesTransaction::TYPE_STATUS)
->setTransactionType(
PhabricatorBadgesBadgeStatusTransaction::TRANSACTIONTYPE)
->setNewValue($new_status);
id(new PhabricatorBadgesEditor())

View file

@ -37,7 +37,8 @@ final class PhabricatorBadgesAwardController
foreach ($badges as $badge) {
$xactions = array();
$xactions[] = id(new PhabricatorBadgesTransaction())
->setTransactionType(PhabricatorBadgesTransaction::TYPE_AWARD)
->setTransactionType(
PhabricatorBadgesBadgeAwardTransaction::TRANSACTIONTYPE)
->setNewValue($award_phids);
$editor = id(new PhabricatorBadgesEditor())

View file

@ -37,7 +37,8 @@ final class PhabricatorBadgesEditRecipientsController
}
$xactions[] = id(new PhabricatorBadgesTransaction())
->setTransactionType(PhabricatorBadgesTransaction::TYPE_AWARD)
->setTransactionType(
PhabricatorBadgesBadgeAwardTransaction::TRANSACTIONTYPE)
->setNewValue($award_phids);
$editor = id(new PhabricatorBadgesEditor())

View file

@ -34,7 +34,8 @@ final class PhabricatorBadgesRemoveRecipientsController
if ($request->isFormPost()) {
$xactions = array();
$xactions[] = id(new PhabricatorBadgesTransaction())
->setTransactionType(PhabricatorBadgesTransaction::TYPE_REVOKE)
->setTransactionType(
PhabricatorBadgesBadgeRevokeTransaction::TRANSACTIONTYPE)
->setNewValue(array($remove_phid));
$editor = id(new PhabricatorBadgesEditor())

View file

@ -86,20 +86,24 @@ final class PhabricatorBadgesEditEngine
->setLabel(pht('Name'))
->setDescription(pht('Badge name.'))
->setConduitTypeDescription(pht('New badge name.'))
->setTransactionType(PhabricatorBadgesTransaction::TYPE_NAME)
->setValue($object->getName()),
->setTransactionType(
PhabricatorBadgesBadgeNameTransaction::TRANSACTIONTYPE)
->setValue($object->getName())
->setIsRequired(true),
id(new PhabricatorTextEditField())
->setKey('flavor')
->setLabel(pht('Flavor text'))
->setDescription(pht('Short description of the badge.'))
->setConduitTypeDescription(pht('New badge flavor.'))
->setValue($object->getFlavor())
->setTransactionType(PhabricatorBadgesTransaction::TYPE_FLAVOR),
->setTransactionType(
PhabricatorBadgesBadgeFlavorTransaction::TRANSACTIONTYPE),
id(new PhabricatorIconSetEditField())
->setKey('icon')
->setLabel(pht('Icon'))
->setIconSet(new PhabricatorBadgesIconSet())
->setTransactionType(PhabricatorBadgesTransaction::TYPE_ICON)
->setTransactionType(
PhabricatorBadgesBadgeIconTransaction::TRANSACTIONTYPE)
->setConduitDescription(pht('Change the badge icon.'))
->setConduitTypeDescription(pht('New badge icon.'))
->setValue($object->getIcon()),
@ -109,14 +113,16 @@ final class PhabricatorBadgesEditEngine
->setDescription(pht('Color and rarity of the badge.'))
->setConduitTypeDescription(pht('New badge quality.'))
->setValue($object->getQuality())
->setTransactionType(PhabricatorBadgesTransaction::TYPE_QUALITY)
->setTransactionType(
PhabricatorBadgesBadgeQualityTransaction::TRANSACTIONTYPE)
->setOptions(PhabricatorBadgesQuality::getDropdownQualityMap()),
id(new PhabricatorRemarkupEditField())
->setKey('description')
->setLabel(pht('Description'))
->setDescription(pht('Badge long description.'))
->setConduitTypeDescription(pht('New badge description.'))
->setTransactionType(PhabricatorBadgesTransaction::TYPE_DESCRIPTION)
->setTransactionType(
PhabricatorBadgesBadgeDescriptionTransaction::TRANSACTIONTYPE)
->setValue($object->getDescription()),
);
}

View file

@ -11,22 +11,20 @@ final class PhabricatorBadgesEditor
return pht('Badges');
}
public function getCreateObjectTitle($author, $object) {
return pht('%s created this badge.', $author);
}
public function getCreateObjectTitleForFeed($author, $object) {
return pht('%s created %s.', $author, $object);
}
protected function supportsSearch() {
return true;
}
public function getTransactionTypes() {
$types = parent::getTransactionTypes();
$types[] = PhabricatorBadgesTransaction::TYPE_NAME;
$types[] = PhabricatorBadgesTransaction::TYPE_FLAVOR;
$types[] = PhabricatorBadgesTransaction::TYPE_DESCRIPTION;
$types[] = PhabricatorBadgesTransaction::TYPE_ICON;
$types[] = PhabricatorBadgesTransaction::TYPE_STATUS;
$types[] = PhabricatorBadgesTransaction::TYPE_QUALITY;
$types[] = PhabricatorBadgesTransaction::TYPE_AWARD;
$types[] = PhabricatorBadgesTransaction::TYPE_REVOKE;
$types[] = PhabricatorTransactions::TYPE_COMMENT;
$types[] = PhabricatorTransactions::TYPE_EDGE;
$types[] = PhabricatorTransactions::TYPE_EDIT_POLICY;
@ -34,159 +32,6 @@ final class PhabricatorBadgesEditor
return $types;
}
protected function getCustomTransactionOldValue(
PhabricatorLiskDAO $object,
PhabricatorApplicationTransaction $xaction) {
switch ($xaction->getTransactionType()) {
case PhabricatorBadgesTransaction::TYPE_NAME:
return $object->getName();
case PhabricatorBadgesTransaction::TYPE_FLAVOR:
return $object->getFlavor();
case PhabricatorBadgesTransaction::TYPE_DESCRIPTION:
return $object->getDescription();
case PhabricatorBadgesTransaction::TYPE_ICON:
return $object->getIcon();
case PhabricatorBadgesTransaction::TYPE_QUALITY:
return (int)$object->getQuality();
case PhabricatorBadgesTransaction::TYPE_STATUS:
return $object->getStatus();
case PhabricatorBadgesTransaction::TYPE_AWARD:
$award_phids = mpull($object->getAwards(), 'getRecipientPHID');
return $award_phids;
case PhabricatorBadgesTransaction::TYPE_REVOKE:
return null;
}
return parent::getCustomTransactionOldValue($object, $xaction);
}
protected function getCustomTransactionNewValue(
PhabricatorLiskDAO $object,
PhabricatorApplicationTransaction $xaction) {
switch ($xaction->getTransactionType()) {
case PhabricatorBadgesTransaction::TYPE_NAME:
case PhabricatorBadgesTransaction::TYPE_FLAVOR:
case PhabricatorBadgesTransaction::TYPE_DESCRIPTION:
case PhabricatorBadgesTransaction::TYPE_ICON:
case PhabricatorBadgesTransaction::TYPE_STATUS:
case PhabricatorBadgesTransaction::TYPE_AWARD:
case PhabricatorBadgesTransaction::TYPE_REVOKE:
return $xaction->getNewValue();
case PhabricatorBadgesTransaction::TYPE_QUALITY:
return (int)$xaction->getNewValue();
}
return parent::getCustomTransactionNewValue($object, $xaction);
}
protected function applyCustomInternalTransaction(
PhabricatorLiskDAO $object,
PhabricatorApplicationTransaction $xaction) {
$type = $xaction->getTransactionType();
switch ($type) {
case PhabricatorBadgesTransaction::TYPE_NAME:
$object->setName($xaction->getNewValue());
return;
case PhabricatorBadgesTransaction::TYPE_FLAVOR:
$object->setFlavor($xaction->getNewValue());
return;
case PhabricatorBadgesTransaction::TYPE_DESCRIPTION:
$object->setDescription($xaction->getNewValue());
return;
case PhabricatorBadgesTransaction::TYPE_ICON:
$object->setIcon($xaction->getNewValue());
return;
case PhabricatorBadgesTransaction::TYPE_QUALITY:
$object->setQuality($xaction->getNewValue());
return;
case PhabricatorBadgesTransaction::TYPE_STATUS:
$object->setStatus($xaction->getNewValue());
return;
case PhabricatorBadgesTransaction::TYPE_AWARD:
case PhabricatorBadgesTransaction::TYPE_REVOKE:
return;
}
return parent::applyCustomInternalTransaction($object, $xaction);
}
protected function applyCustomExternalTransaction(
PhabricatorLiskDAO $object,
PhabricatorApplicationTransaction $xaction) {
$type = $xaction->getTransactionType();
switch ($type) {
case PhabricatorBadgesTransaction::TYPE_NAME:
case PhabricatorBadgesTransaction::TYPE_FLAVOR:
case PhabricatorBadgesTransaction::TYPE_DESCRIPTION:
case PhabricatorBadgesTransaction::TYPE_ICON:
case PhabricatorBadgesTransaction::TYPE_STATUS:
case PhabricatorBadgesTransaction::TYPE_QUALITY:
return;
case PhabricatorBadgesTransaction::TYPE_REVOKE:
$revoked_recipient_phids = $xaction->getNewValue();
$awards = $object->getAwards();
$awards = mpull($awards, null, 'getRecipientPHID');
foreach ($revoked_recipient_phids as $phid) {
$awards[$phid]->delete();
}
$object->attachAwards($awards);
return;
case PhabricatorBadgesTransaction::TYPE_AWARD:
$recipient_phids = $xaction->getNewValue();
$awards = $object->getAwards();
$awards = mpull($awards, null, 'getRecipientPHID');
foreach ($recipient_phids as $phid) {
$award = idx($awards, $phid);
if (!$award) {
$award = PhabricatorBadgesAward::initializeNewBadgesAward(
$this->getActor(),
$object,
$phid);
$award->save();
$awards[] = $award;
}
}
$object->attachAwards($awards);
return;
}
return parent::applyCustomExternalTransaction($object, $xaction);
}
protected function validateTransaction(
PhabricatorLiskDAO $object,
$type,
array $xactions) {
$errors = parent::validateTransaction($object, $type, $xactions);
switch ($type) {
case PhabricatorBadgesTransaction::TYPE_NAME:
$missing = $this->validateIsEmptyTextField(
$object->getName(),
$xactions);
if ($missing) {
$error = new PhabricatorApplicationTransactionValidationError(
$type,
pht('Required'),
pht('Badge name is required.'),
nonempty(last($xactions), null));
$error->setIsMissingFieldError(true);
$errors[] = $error;
}
break;
}
return $errors;
}
protected function shouldSendMail(
PhabricatorLiskDAO $object,
array $xactions) {

View file

@ -1,16 +1,7 @@
<?php
final class PhabricatorBadgesTransaction
extends PhabricatorApplicationTransaction {
const TYPE_NAME = 'badges:name';
const TYPE_DESCRIPTION = 'badges:description';
const TYPE_QUALITY = 'badges:quality';
const TYPE_ICON = 'badges:icon';
const TYPE_STATUS = 'badges:status';
const TYPE_FLAVOR = 'badges:flavor';
const TYPE_AWARD = 'badges:award';
const TYPE_REVOKE = 'badges:revoke';
extends PhabricatorModularTransaction {
const MAILTAG_DETAILS = 'badges:details';
const MAILTAG_COMMENT = 'badges:comment';
@ -28,209 +19,8 @@ final class PhabricatorBadgesTransaction
return new PhabricatorBadgesTransactionComment();
}
public function getTitle() {
$author_phid = $this->getAuthorPHID();
$object_phid = $this->getObjectPHID();
$old = $this->getOldValue();
$new = $this->getNewValue();
$type = $this->getTransactionType();
switch ($type) {
case PhabricatorTransactions::TYPE_CREATE:
return pht(
'%s created this badge.',
$this->renderHandleLink($author_phid));
case self::TYPE_NAME:
if ($old === null) {
return pht(
'%s created this badge.',
$this->renderHandleLink($author_phid));
} else {
return pht(
'%s renamed this badge from "%s" to "%s".',
$this->renderHandleLink($author_phid),
$old,
$new);
}
break;
case self::TYPE_FLAVOR:
if ($old === null) {
return pht(
'%s set the flavor text for this badge.',
$this->renderHandleLink($author_phid));
} else {
return pht(
'%s updated the flavor text for this badge.',
$this->renderHandleLink($author_phid));
}
break;
case self::TYPE_DESCRIPTION:
if ($old === null) {
return pht(
'%s set the description for this badge.',
$this->renderHandleLink($author_phid));
} else {
return pht(
'%s updated the description for this badge.',
$this->renderHandleLink($author_phid));
}
break;
case self::TYPE_STATUS:
switch ($new) {
case PhabricatorBadgesBadge::STATUS_ACTIVE:
return pht(
'%s activated this badge.',
$this->renderHandleLink($author_phid));
case PhabricatorBadgesBadge::STATUS_ARCHIVED:
return pht(
'%s archived this badge.',
$this->renderHandleLink($author_phid));
}
break;
case self::TYPE_ICON:
if ($old === null) {
return pht(
'%s set the icon for this badge as "%s".',
$this->renderHandleLink($author_phid),
$new);
} else {
$set = new PhabricatorBadgesIconSet();
$icon_old = $set->getIconLabel($old);
$icon_new = $set->getIconLabel($new);
return pht(
'%s updated the icon for this badge from "%s" to "%s".',
$this->renderHandleLink($author_phid),
$icon_old,
$icon_new);
}
break;
case self::TYPE_QUALITY:
$qual_new = PhabricatorBadgesQuality::getQualityName($new);
$qual_old = PhabricatorBadgesQuality::getQualityName($old);
if ($old === null) {
return pht(
'%s set the quality for this badge as "%s".',
$this->renderHandleLink($author_phid),
$qual_new);
} else {
return pht(
'%s updated the quality for this badge from "%s" to "%s".',
$this->renderHandleLink($author_phid),
$qual_old,
$qual_new);
}
break;
case self::TYPE_AWARD:
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s awarded this badge to %s recipient(s): %s.',
$this->renderHandleLink($author_phid),
new PhutilNumber(count($new)),
$handles);
case self::TYPE_REVOKE:
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s revoked this badge from %s recipient(s): %s.',
$this->renderHandleLink($author_phid),
new PhutilNumber(count($new)),
$handles);
}
return parent::getTitle();
}
public function getTitleForFeed() {
$author_phid = $this->getAuthorPHID();
$object_phid = $this->getObjectPHID();
$old = $this->getOldValue();
$new = $this->getNewValue();
$type = $this->getTransactionType();
switch ($type) {
case self::TYPE_NAME:
if ($old === null) {
return pht(
'%s created %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
} else {
return pht(
'%s renamed %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
}
break;
case self::TYPE_FLAVOR:
return pht(
'%s updated the flavor text for %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
case self::TYPE_ICON:
return pht(
'%s updated the icon for %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
case self::TYPE_QUALITY:
return pht(
'%s updated the quality level for %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
case self::TYPE_DESCRIPTION:
return pht(
'%s updated the description for %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
case self::TYPE_STATUS:
switch ($new) {
case PhabricatorBadgesBadge::STATUS_ACTIVE:
return pht(
'%s activated %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
case PhabricatorBadgesBadge::STATUS_ARCHIVED:
return pht(
'%s archived %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid));
}
break;
case self::TYPE_AWARD:
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s awarded %s to %s recipient(s): %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid),
new PhutilNumber(count($new)),
$handles);
case self::TYPE_REVOKE:
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s revoked %s from %s recipient(s): %s.',
$this->renderHandleLink($author_phid),
$this->renderHandleLink($object_phid),
new PhutilNumber(count($new)),
$handles);
}
return parent::getTitleForFeed();
public function getBaseTransactionClass() {
return 'PhabricatorBadgesBadgeTransactionType';
}
public function getMailTags() {
@ -240,14 +30,16 @@ final class PhabricatorBadgesTransaction
case PhabricatorTransactions::TYPE_COMMENT:
$tags[] = self::MAILTAG_COMMENT;
break;
case self::TYPE_NAME:
case self::TYPE_DESCRIPTION:
case self::TYPE_FLAVOR:
case self::TYPE_ICON:
case self::TYPE_STATUS:
case self::TYPE_QUALITY:
case PhabricatorBadgesBadgeNameTransaction::TRANSACTIONTYPE:
case PhabricatorBadgesBadgeDescriptionTransaction::TRANSACTIONTYPE:
case PhabricatorBadgesBadgeFlavorTransaction::TRANSACTIONTYPE:
case PhabricatorBadgesBadgeIconTransaction::TRANSACTIONTYPE:
case PhabricatorBadgesBadgeStatusTransaction::TRANSACTIONTYPE:
case PhabricatorBadgesBadgeQualityTransaction::TRANSACTIONTYPE:
$tags[] = self::MAILTAG_DETAILS;
break;
case PhabricatorBadgesBadgeAwardTransaction::TRANSACTIONTYPE:
case PhabricatorBadgesBadgeRevokeTransaction::TRANSACTIONTYPE:
default:
$tags[] = self::MAILTAG_OTHER;
break;
@ -255,49 +47,4 @@ final class PhabricatorBadgesTransaction
return $tags;
}
public function shouldHide() {
$old = $this->getOldValue();
switch ($this->getTransactionType()) {
case self::TYPE_DESCRIPTION:
return ($old === null);
}
return parent::shouldHide();
}
public function hasChangeDetails() {
switch ($this->getTransactionType()) {
case self::TYPE_DESCRIPTION:
return ($this->getOldValue() !== null);
}
return parent::hasChangeDetails();
}
public function renderChangeDetails(PhabricatorUser $viewer) {
return $this->renderTextCorpusChangeDetails(
$viewer,
$this->getOldValue(),
$this->getNewValue());
}
public function getRequiredHandlePHIDs() {
$phids = parent::getRequiredHandlePHIDs();
$type = $this->getTransactionType();
switch ($type) {
case self::TYPE_AWARD:
case self::TYPE_REVOKE:
$new = $this->getNewValue();
if (!is_array($new)) {
$new = array();
}
foreach ($new as $phid) {
$phids[] = $phid;
}
break;
}
return $phids;
}
}

View file

@ -0,0 +1,62 @@
<?php
final class PhabricatorBadgesBadgeAwardTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badge.award';
public function generateOldValue($object) {
return mpull($object->getAwards(), 'getRecipientPHID');
}
public function applyExternalEffects($object, $value) {
$awards = $object->getAwards();
$awards = mpull($awards, null, 'getRecipientPHID');
foreach ($value as $phid) {
$award = idx($awards, $phid);
if (!$award) {
$award = PhabricatorBadgesAward::initializeNewBadgesAward(
$this->getActor(),
$object,
$phid);
$award->save();
$awards[] = $award;
}
}
$object->attachAwards($awards);
return;
}
public function getTitle() {
$new = $this->getNewValue();
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s awarded this badge to %s recipient(s): %s.',
$this->renderAuthor(),
new PhutilNumber(count($new)),
$handles);
}
public function getTitleForFeed() {
$new = $this->getNewValue();
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s awarded %s to %s recipient(s): %s.',
$this->renderAuthor(),
$this->renderObject(),
new PhutilNumber(count($new)),
$handles);
}
public function getIcon() {
return 'fa-user-plus';
}
}

View file

@ -0,0 +1,57 @@
<?php
final class PhabricatorBadgesBadgeDescriptionTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badge.description';
public function generateOldValue($object) {
return $object->getDescription();
}
public function applyInternalEffects($object, $value) {
$object->setDescription($value);
}
public function getTitle() {
return pht(
'%s updated the badge description.',
$this->renderAuthor());
}
public function getTitleForFeed() {
return pht(
'%s updated the badge description for %s.',
$this->renderAuthor(),
$this->renderObject());
}
public function hasChangeDetailView() {
return true;
}
public function getMailDiffSectionHeader() {
return pht('CHANGES TO BADGE DESCRIPTION');
}
public function newChangeDetailView() {
$viewer = $this->getViewer();
return id(new PhabricatorApplicationTransactionTextDiffDetailView())
->setViewer($viewer)
->setOldText($this->getOldValue())
->setNewText($this->getNewValue());
}
public function newRemarkupChanges() {
$changes = array();
$changes[] = $this->newRemarkupChange()
->setOldValue($this->getOldValue())
->setNewValue($this->getNewValue());
return $changes;
}
}

View file

@ -0,0 +1,33 @@
<?php
final class PhabricatorBadgesBadgeFlavorTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badge.flavor';
public function generateOldValue($object) {
return $object->getFlavor();
}
public function applyInternalEffects($object, $value) {
$object->setFlavor($value);
}
public function getTitle() {
return pht(
'%s updated the flavor from %s to %s.',
$this->renderAuthor(),
$this->renderOldValue(),
$this->renderNewValue());
}
public function getTitleForFeed() {
return pht(
'%s updated %s flavor text from %s to %s.',
$this->renderAuthor(),
$this->renderObject(),
$this->renderOldValue(),
$this->renderNewValue());
}
}

View file

@ -0,0 +1,56 @@
<?php
final class PhabricatorBadgesBadgeIconTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badge.icon';
public function generateOldValue($object) {
return $object->getIcon();
}
public function applyInternalEffects($object, $value) {
$object->setIcon($value);
}
public function shouldHide() {
if ($this->isCreateTransaction()) {
return true;
}
return false;
}
public function getTitle() {
$old = $this->getIconLabel($this->getOldValue());
$new = $this->getIconLabel($this->getNewValue());
return pht(
'%s changed the badge icon from %s to %s.',
$this->renderAuthor(),
$this->renderValue($old),
$this->renderValue($new));
}
public function getTitleForFeed() {
$old = $this->getIconLabel($this->getOldValue());
$new = $this->getIconLabel($this->getNewValue());
return pht(
'%s changed the badge icon for %s from %s to %s.',
$this->renderAuthor(),
$this->renderObject(),
$this->renderValue($old),
$this->renderValue($new));
}
private function getIconLabel($icon) {
$set = new PhabricatorBadgesIconSet();
return $set->getIconLabel($icon);
}
public function getIcon() {
return $this->getNewValue();
}
}

View file

@ -0,0 +1,44 @@
<?php
final class PhabricatorBadgesBadgeNameTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badge.name';
public function generateOldValue($object) {
return $object->getName();
}
public function applyInternalEffects($object, $value) {
$object->setName($value);
}
public function getTitle() {
return pht(
'%s renamed this badge from %s to %s.',
$this->renderAuthor(),
$this->renderOldValue(),
$this->renderNewValue());
}
public function getTitleForFeed() {
return pht(
'%s renamed %s badge %s to %s.',
$this->renderAuthor(),
$this->renderObject(),
$this->renderOldValue(),
$this->renderNewValue());
}
public function validateTransactions($object, array $xactions) {
$errors = array();
if ($this->isEmptyTextTransaction($object->getName(), $xactions)) {
$errors[] = $this->newRequiredError(
pht('Badges must have a name.'));
}
return $errors;
}
}

View file

@ -0,0 +1,70 @@
<?php
final class PhabricatorBadgesBadgeQualityTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badge.quality';
public function generateOldValue($object) {
return $object->getQuality();
}
public function applyInternalEffects($object, $value) {
$object->setQuality($value);
}
public function shouldHide() {
if ($this->isCreateTransaction()) {
return true;
}
return false;
}
public function getTitle() {
$old = $this->getQualityLabel($this->getOldValue());
$new = $this->getQualityLabel($this->getNewValue());
return pht(
'%s updated the quality from %s to %s.',
$this->renderAuthor(),
$old,
$new);
}
public function getTitleForFeed() {
$old = $this->getQualityLabel($this->getOldValue());
$new = $this->getQualityLabel($this->getNewValue());
return pht(
'%s updated %s quality from %s to %s.',
$this->renderAuthor(),
$this->renderObject(),
$new,
$old);
}
public function validateTransactions($object, array $xactions) {
$errors = array();
if ($this->isEmptyTextTransaction($object->getQuality(), $xactions)) {
$errors[] = $this->newRequiredError(
pht('Badge quality must be set.'));
}
$map = PhabricatorBadgesQuality::getQualityMap();
if (!$map[$object->getQuality()]) {
$errors[] = $this->newRequiredError(
pht('Badge quality is not valid.'));
}
return $errors;
}
private function getQualityLabel($quality) {
$map = PhabricatorBadgesQuality::getQualityMap();
$name = $map[$quality]['name'];
return $this->renderValue($name);
}
}

View file

@ -0,0 +1,54 @@
<?php
final class PhabricatorBadgesBadgeRevokeTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badge.revoke';
public function generateOldValue($object) {
return null;
}
public function applyExternalEffects($object, $value) {
$awards = $object->getAwards();
$awards = mpull($awards, null, 'getRecipientPHID');
foreach ($value as $phid) {
$awards[$phid]->delete();
}
$object->attachAwards($awards);
return;
}
public function getTitle() {
$new = $this->getNewValue();
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s revoked this badge from %s recipient(s): %s.',
$this->renderAuthor(),
new PhutilNumber(count($new)),
$handles);
}
public function getTitleForFeed() {
$new = $this->getNewValue();
if (!is_array($new)) {
$new = array();
}
$handles = $this->renderHandleList($new);
return pht(
'%s revoked %s from %s recipient(s): %s.',
$this->renderAuthor(),
$this->renderObject(),
new PhutilNumber(count($new)),
$handles);
}
public function getIcon() {
return 'fa-user-times';
}
}

View file

@ -0,0 +1,50 @@
<?php
final class PhabricatorBadgesBadgeStatusTransaction
extends PhabricatorBadgesBadgeTransactionType {
const TRANSACTIONTYPE = 'badges.status';
public function generateOldValue($object) {
return $object->getStatus();
}
public function applyInternalEffects($object, $value) {
$object->setStatus($value);
}
public function getTitle() {
if ($this->getNewValue() == PhabricatorBadgesBadge::STATUS_ARCHIVED) {
return pht(
'%s disabled this badge.',
$this->renderAuthor());
} else {
return pht(
'%s enabled this badge.',
$this->renderAuthor());
}
}
public function getTitleForFeed() {
if ($this->getNewValue() == PhabricatorBadgesBadge::STATUS_ARCHIVED) {
return pht(
'%s disabled the badge %s.',
$this->renderAuthor(),
$this->renderObject());
} else {
return pht(
'%s enabled the badge %s.',
$this->renderAuthor(),
$this->renderObject());
}
}
public function getIcon() {
if ($this->getNewValue() == PhabricatorBadgesBadge::STATUS_ARCHIVED) {
return 'fa-ban';
} else {
return 'fa-check';
}
}
}

View file

@ -0,0 +1,4 @@
<?php
abstract class PhabricatorBadgesBadgeTransactionType
extends PhabricatorModularTransactionType {}