3 final class AlmanacService
6 PhabricatorPolicyInterface
,
7 PhabricatorApplicationTransactionInterface
,
8 PhabricatorProjectInterface
,
9 AlmanacPropertyInterface
,
10 PhabricatorDestructibleInterface
,
11 PhabricatorNgramsInterface
,
12 PhabricatorConduitResultInterface
,
13 PhabricatorExtendedPolicyInterface
{
17 protected $viewPolicy;
18 protected $editPolicy;
19 protected $serviceType;
21 private $almanacProperties = self
::ATTACHABLE
;
22 private $bindings = self
::ATTACHABLE
;
23 private $activeBindings = self
::ATTACHABLE
;
24 private $serviceImplementation = self
::ATTACHABLE
;
26 public static function initializeNewService($type) {
27 $type_map = AlmanacServiceType
::getAllServiceTypes();
29 $implementation = idx($type_map, $type);
30 if (!$implementation) {
33 'No Almanac service type "%s" exists!',
37 return id(new AlmanacService())
38 ->setViewPolicy(PhabricatorPolicies
::POLICY_USER
)
39 ->setEditPolicy(PhabricatorPolicies
::POLICY_ADMIN
)
40 ->attachAlmanacProperties(array())
41 ->setServiceType($type)
42 ->attachServiceImplementation($implementation);
45 protected function getConfiguration() {
47 self
::CONFIG_AUX_PHID
=> true,
48 self
::CONFIG_COLUMN_SCHEMA
=> array(
50 'nameIndex' => 'bytes12',
51 'serviceType' => 'text64',
53 self
::CONFIG_KEY_SCHEMA
=> array(
55 'columns' => array('nameIndex'),
58 'key_nametext' => array(
59 'columns' => array('name'),
61 'key_servicetype' => array(
62 'columns' => array('serviceType'),
65 ) + parent
::getConfiguration();
68 public function getPHIDType() {
69 return AlmanacServicePHIDType
::TYPECONST
;
72 public function save() {
73 AlmanacNames
::validateName($this->getName());
75 $this->nameIndex
= PhabricatorHash
::digestForIndex($this->getName());
77 return parent
::save();
80 public function getURI() {
81 return '/almanac/service/view/'.$this->getName().'/';
84 public function getBindings() {
85 return $this->assertAttached($this->bindings
);
88 public function getActiveBindings() {
89 return $this->assertAttached($this->activeBindings
);
92 public function attachBindings(array $bindings) {
93 $active_bindings = array();
94 foreach ($bindings as $key => $binding) {
95 // Filter out disabled bindings.
96 if ($binding->getIsDisabled()) {
100 // Filter out bindings to disabled devices.
101 if ($binding->getDevice()->isDisabled()) {
105 $active_bindings[$key] = $binding;
108 $this->attachActiveBindings($active_bindings);
110 $this->bindings
= $bindings;
114 public function attachActiveBindings(array $bindings) {
115 $this->activeBindings
= $bindings;
119 public function getServiceImplementation() {
120 return $this->assertAttached($this->serviceImplementation
);
123 public function attachServiceImplementation(AlmanacServiceType
$type) {
124 $this->serviceImplementation
= $type;
128 public function isClusterService() {
129 return $this->getServiceImplementation()->isClusterServiceType();
133 /* -( AlmanacPropertyInterface )------------------------------------------- */
136 public function attachAlmanacProperties(array $properties) {
137 assert_instances_of($properties, 'AlmanacProperty');
138 $this->almanacProperties
= mpull($properties, null, 'getFieldName');
142 public function getAlmanacProperties() {
143 return $this->assertAttached($this->almanacProperties
);
146 public function hasAlmanacProperty($key) {
147 $this->assertAttached($this->almanacProperties
);
148 return isset($this->almanacProperties
[$key]);
151 public function getAlmanacProperty($key) {
152 return $this->assertAttachedKey($this->almanacProperties
, $key);
155 public function getAlmanacPropertyValue($key, $default = null) {
156 if ($this->hasAlmanacProperty($key)) {
157 return $this->getAlmanacProperty($key)->getFieldValue();
163 public function getAlmanacPropertyFieldSpecifications() {
164 return $this->getServiceImplementation()->getFieldSpecifications();
167 public function getBindingFieldSpecifications(AlmanacBinding
$binding) {
168 $impl = $this->getServiceImplementation();
169 return $impl->getBindingFieldSpecifications($binding);
172 public function newAlmanacPropertyEditEngine() {
173 return new AlmanacServicePropertyEditEngine();
176 public function getAlmanacPropertySetTransactionType() {
177 return AlmanacServiceSetPropertyTransaction
::TRANSACTIONTYPE
;
180 public function getAlmanacPropertyDeleteTransactionType() {
181 return AlmanacServiceDeletePropertyTransaction
::TRANSACTIONTYPE
;
185 /* -( PhabricatorPolicyInterface )----------------------------------------- */
188 public function getCapabilities() {
190 PhabricatorPolicyCapability
::CAN_VIEW
,
191 PhabricatorPolicyCapability
::CAN_EDIT
,
195 public function getPolicy($capability) {
196 switch ($capability) {
197 case PhabricatorPolicyCapability
::CAN_VIEW
:
198 return $this->getViewPolicy();
199 case PhabricatorPolicyCapability
::CAN_EDIT
:
200 return $this->getEditPolicy();
204 public function hasAutomaticCapability($capability, PhabricatorUser
$viewer) {
209 /* -( PhabricatorExtendedPolicyInterface )--------------------------------- */
212 public function getExtendedPolicy($capability, PhabricatorUser
$viewer) {
213 switch ($capability) {
214 case PhabricatorPolicyCapability
::CAN_EDIT
:
215 if ($this->isClusterService()) {
218 new PhabricatorAlmanacApplication(),
219 AlmanacManageClusterServicesCapability
::CAPABILITY
,
230 /* -( PhabricatorApplicationTransactionInterface )------------------------- */
233 public function getApplicationTransactionEditor() {
234 return new AlmanacServiceEditor();
237 public function getApplicationTransactionTemplate() {
238 return new AlmanacServiceTransaction();
242 /* -( PhabricatorDestructibleInterface )----------------------------------- */
245 public function destroyObjectPermanently(
246 PhabricatorDestructionEngine
$engine) {
248 $bindings = id(new AlmanacBindingQuery())
249 ->setViewer($engine->getViewer())
250 ->withServicePHIDs(array($this->getPHID()))
252 foreach ($bindings as $binding) {
253 $engine->destroyObject($binding);
260 /* -( PhabricatorNgramsInterface )----------------------------------------- */
263 public function newNgrams() {
265 id(new AlmanacServiceNameNgrams())
266 ->setValue($this->getName()),
271 /* -( PhabricatorConduitResultInterface )---------------------------------- */
274 public function getFieldSpecificationsForConduit() {
276 id(new PhabricatorConduitSearchFieldSpecification())
279 ->setDescription(pht('The name of the service.')),
280 id(new PhabricatorConduitSearchFieldSpecification())
281 ->setKey('serviceType')
283 ->setDescription(pht('The service type constant.')),
287 public function getFieldValuesForConduit() {
289 'name' => $this->getName(),
290 'serviceType' => $this->getServiceType(),
294 public function getConduitSearchAttachments() {
296 id(new AlmanacPropertiesSearchEngineAttachment())
297 ->setAttachmentKey('properties'),
298 id(new AlmanacBindingsSearchEngineAttachment())
299 ->setAttachmentKey('bindings'),
300 id(new AlmanacBindingsSearchEngineAttachment())
302 ->setAttachmentKey('activeBindings'),