From 6983479e4f60d31fc16e10d25ea26c4027b872a3 Mon Sep 17 00:00:00 2001 From: epriestley Date: Mon, 9 Apr 2018 10:00:13 -0700 Subject: [PATCH] Allow "almanac.service.edit" to create services Summary: Depends on D19317. Ref T13120. Ref T12414. See PHI145. See PHI473. This adds a Conduit-only "type" transaction for Almanac services. This is very similar to the approach in D18849 for Drydock blueprints. Test Plan: - Tried to create an empty service via "almanac.service.edit", was told to pick a type. - Tried to pick a bad type, was told to pick a good type. - Created a new Almanac service via "almanac.service.edit". - Tried to edit the service to change the type, wasn't allowed to. - Created and edited via the web UI, nothing changed from before. Reviewers: amckinley Reviewed By: amckinley Maniphest Tasks: T13120, T12414 Differential Revision: https://secure.phabricator.com/D19318 --- src/__phutil_library_map__.php | 2 + .../editor/AlmanacServiceEditEngine.php | 41 ++++++++++++++ .../xaction/AlmanacServiceNameTransaction.php | 4 +- .../xaction/AlmanacServiceTypeTransaction.php | 55 +++++++++++++++++++ 4 files changed, 100 insertions(+), 2 deletions(-) create mode 100644 src/applications/almanac/xaction/AlmanacServiceTypeTransaction.php diff --git a/src/__phutil_library_map__.php b/src/__phutil_library_map__.php index fe8e000041..5d68c3b0c6 100644 --- a/src/__phutil_library_map__.php +++ b/src/__phutil_library_map__.php @@ -126,6 +126,7 @@ phutil_register_library_map(array( 'AlmanacServiceType' => 'applications/almanac/servicetype/AlmanacServiceType.php', 'AlmanacServiceTypeDatasource' => 'applications/almanac/typeahead/AlmanacServiceTypeDatasource.php', 'AlmanacServiceTypeTestCase' => 'applications/almanac/servicetype/__tests__/AlmanacServiceTypeTestCase.php', + 'AlmanacServiceTypeTransaction' => 'applications/almanac/xaction/AlmanacServiceTypeTransaction.php', 'AlmanacServiceViewController' => 'applications/almanac/controller/AlmanacServiceViewController.php', 'AlmanacTransaction' => 'applications/almanac/storage/AlmanacTransaction.php', 'AlmanacTransactionType' => 'applications/almanac/xaction/AlmanacTransactionType.php', @@ -5331,6 +5332,7 @@ phutil_register_library_map(array( 'AlmanacServiceType' => 'Phobject', 'AlmanacServiceTypeDatasource' => 'PhabricatorTypeaheadDatasource', 'AlmanacServiceTypeTestCase' => 'PhabricatorTestCase', + 'AlmanacServiceTypeTransaction' => 'AlmanacServiceTransactionType', 'AlmanacServiceViewController' => 'AlmanacServiceController', 'AlmanacTransaction' => 'PhabricatorApplicationTransaction', 'AlmanacTransactionType' => 'PhabricatorModularTransactionType', diff --git a/src/applications/almanac/editor/AlmanacServiceEditEngine.php b/src/applications/almanac/editor/AlmanacServiceEditEngine.php index 8cf7b97991..93912fad8b 100644 --- a/src/applications/almanac/editor/AlmanacServiceEditEngine.php +++ b/src/applications/almanac/editor/AlmanacServiceEditEngine.php @@ -41,6 +41,37 @@ final class AlmanacServiceEditEngine return AlmanacService::initializeNewService($service_type); } + protected function newEditableObjectFromConduit(array $raw_xactions) { + $type = null; + foreach ($raw_xactions as $raw_xaction) { + if ($raw_xaction['type'] !== 'type') { + continue; + } + + $type = $raw_xaction['value']; + } + + if ($type === null) { + throw new Exception( + pht( + 'When creating a new Almanac service via the Conduit API, you '. + 'must provide a "type" transaction to select a type.')); + } + + $map = AlmanacServiceType::getAllServiceTypes(); + if (!isset($map[$type])) { + throw new Exception( + pht( + 'Service type "%s" is unrecognized. Valid types are: %s.', + $type, + implode(', ', array_keys($map)))); + } + + $this->setServiceType($type); + + return $this->newEditableObject(); + } + protected function newEditableObjectForDocumentation() { $service_type = new AlmanacCustomServiceType(); $this->setServiceType($service_type->getServiceTypeConstant()); @@ -101,6 +132,16 @@ final class AlmanacServiceEditEngine ->setTransactionType(AlmanacServiceNameTransaction::TRANSACTIONTYPE) ->setIsRequired(true) ->setValue($object->getName()), + id(new PhabricatorTextEditField()) + ->setKey('type') + ->setLabel(pht('Type')) + ->setIsConduitOnly(true) + ->setTransactionType( + AlmanacServiceTypeTransaction::TRANSACTIONTYPE) + ->setDescription(pht('When creating a service, set the type.')) + ->setConduitDescription(pht('Set the service type.')) + ->setConduitTypeDescription(pht('Service type.')) + ->setValue($object->getServiceType()), ); } diff --git a/src/applications/almanac/xaction/AlmanacServiceNameTransaction.php b/src/applications/almanac/xaction/AlmanacServiceNameTransaction.php index 24d9857bfa..ea1ccb8faa 100644 --- a/src/applications/almanac/xaction/AlmanacServiceNameTransaction.php +++ b/src/applications/almanac/xaction/AlmanacServiceNameTransaction.php @@ -16,7 +16,7 @@ final class AlmanacServiceNameTransaction public function getTitle() { return pht( '%s renamed this service from %s to %s.', - $this->renderAuthorLink(), + $this->renderAuthor(), $this->renderOldValue(), $this->renderNewValue()); } @@ -24,7 +24,7 @@ final class AlmanacServiceNameTransaction public function getTitleForFeed() { return pht( '%s renamed %s from %s to %s.', - $this->renderAuthorLink(), + $this->renderAuthor(), $this->renderObject(), $this->renderOldValue(), $this->renderNewValue()); diff --git a/src/applications/almanac/xaction/AlmanacServiceTypeTransaction.php b/src/applications/almanac/xaction/AlmanacServiceTypeTransaction.php new file mode 100644 index 0000000000..1b1c63d040 --- /dev/null +++ b/src/applications/almanac/xaction/AlmanacServiceTypeTransaction.php @@ -0,0 +1,55 @@ +getServiceType(); + } + + public function applyInternalEffects($object, $value) { + $object->setServiceType($value); + } + + public function getTitle() { + // This transaction can only be applied during object creation via + // Conduit and never generates a timeline event. + return null; + } + + public function validateTransactions($object, array $xactions) { + $errors = array(); + + if ($this->isEmptyTextTransaction($object->getServiceType(), $xactions)) { + $errors[] = $this->newRequiredError( + pht('You must select a service type when creating a service.')); + } + + $map = AlmanacServiceType::getAllServiceTypes(); + + foreach ($xactions as $xaction) { + if (!$this->isNewObject()) { + $errors[] = $this->newInvalidError( + pht( + 'The type of a service can not be changed once it has '. + 'been created.'), + $xaction); + continue; + } + + $new = $xaction->getNewValue(); + if (!isset($map[$new])) { + $errors[] = $this->newInvalidError( + pht( + 'Service type "%s" is not valid. Valid types are: %s.', + $new, + implode(', ', array_keys($map)))); + continue; + } + } + + return $errors; + } +}