1
0
Fork 0
mirror of https://we.phorge.it/source/phorge.git synced 2024-11-30 02:32:42 +01:00

Allow tasks to be searched by subtype

Summary:
Ref T12314. Allow tasks to be queried by subtype using a typeahead.

Open to a better default icon. I'll probably let you configure them later.

Just hide this constraint if there's only one subtype.

Test Plan:
  - Searched for subtypes.
  - Verified that the control hides if there is only one subtype.

{F3492293}

Reviewers: chad

Reviewed By: chad

Maniphest Tasks: T12314

Differential Revision: https://secure.phabricator.com/D17444
This commit is contained in:
epriestley 2017-03-01 16:49:41 -08:00
parent 4a061b1def
commit 4948a21959
5 changed files with 97 additions and 0 deletions

View file

@ -1525,6 +1525,7 @@ phutil_register_library_map(array(
'ManiphestTaskStatusHeraldAction' => 'applications/maniphest/herald/ManiphestTaskStatusHeraldAction.php', 'ManiphestTaskStatusHeraldAction' => 'applications/maniphest/herald/ManiphestTaskStatusHeraldAction.php',
'ManiphestTaskStatusHeraldField' => 'applications/maniphest/herald/ManiphestTaskStatusHeraldField.php', 'ManiphestTaskStatusHeraldField' => 'applications/maniphest/herald/ManiphestTaskStatusHeraldField.php',
'ManiphestTaskStatusTestCase' => 'applications/maniphest/constants/__tests__/ManiphestTaskStatusTestCase.php', 'ManiphestTaskStatusTestCase' => 'applications/maniphest/constants/__tests__/ManiphestTaskStatusTestCase.php',
'ManiphestTaskSubtypeDatasource' => 'applications/maniphest/typeahead/ManiphestTaskSubtypeDatasource.php',
'ManiphestTaskTestCase' => 'applications/maniphest/__tests__/ManiphestTaskTestCase.php', 'ManiphestTaskTestCase' => 'applications/maniphest/__tests__/ManiphestTaskTestCase.php',
'ManiphestTaskTitleHeraldField' => 'applications/maniphest/herald/ManiphestTaskTitleHeraldField.php', 'ManiphestTaskTitleHeraldField' => 'applications/maniphest/herald/ManiphestTaskTitleHeraldField.php',
'ManiphestTransaction' => 'applications/maniphest/storage/ManiphestTransaction.php', 'ManiphestTransaction' => 'applications/maniphest/storage/ManiphestTransaction.php',
@ -6424,6 +6425,7 @@ phutil_register_library_map(array(
'ManiphestTaskStatusHeraldAction' => 'HeraldAction', 'ManiphestTaskStatusHeraldAction' => 'HeraldAction',
'ManiphestTaskStatusHeraldField' => 'ManiphestTaskHeraldField', 'ManiphestTaskStatusHeraldField' => 'ManiphestTaskHeraldField',
'ManiphestTaskStatusTestCase' => 'PhabricatorTestCase', 'ManiphestTaskStatusTestCase' => 'PhabricatorTestCase',
'ManiphestTaskSubtypeDatasource' => 'PhabricatorTypeaheadDatasource',
'ManiphestTaskTestCase' => 'PhabricatorTestCase', 'ManiphestTaskTestCase' => 'PhabricatorTestCase',
'ManiphestTaskTitleHeraldField' => 'ManiphestTaskHeraldField', 'ManiphestTaskTitleHeraldField' => 'ManiphestTaskHeraldField',
'ManiphestTransaction' => 'PhabricatorApplicationTransaction', 'ManiphestTransaction' => 'PhabricatorApplicationTransaction',

View file

@ -44,6 +44,11 @@ final class ManiphestTaskSearchEngine
} }
protected function buildCustomSearchFields() { protected function buildCustomSearchFields() {
// Hide the "Subtypes" constraint from the web UI if the install only
// defines one task subtype, since it isn't of any use in this case.
$subtype_map = id(new ManiphestTask())->newEditEngineSubtypeMap();
$hide_subtypes = (count($subtype_map) == 1);
return array( return array(
id(new PhabricatorOwnersSearchField()) id(new PhabricatorOwnersSearchField())
->setLabel(pht('Assigned To')) ->setLabel(pht('Assigned To'))
@ -73,6 +78,14 @@ final class ManiphestTaskSearchEngine
pht('Search for tasks with given priorities.')) pht('Search for tasks with given priorities.'))
->setConduitParameterType(new ConduitIntListParameterType()) ->setConduitParameterType(new ConduitIntListParameterType())
->setDatasource(new ManiphestTaskPriorityDatasource()), ->setDatasource(new ManiphestTaskPriorityDatasource()),
id(new PhabricatorSearchDatasourceField())
->setLabel(pht('Subtypes'))
->setKey('subtypes')
->setAliases(array('subtype'))
->setDescription(
pht('Search for tasks with given subtypes.'))
->setDatasource(new ManiphestTaskSubtypeDatasource())
->setIsHidden($hide_subtypes),
id(new PhabricatorSearchTextField()) id(new PhabricatorSearchTextField())
->setLabel(pht('Contains Words')) ->setLabel(pht('Contains Words'))
->setKey('fulltext'), ->setKey('fulltext'),
@ -130,6 +143,7 @@ final class ManiphestTaskSearchEngine
'subscriberPHIDs', 'subscriberPHIDs',
'statuses', 'statuses',
'priorities', 'priorities',
'subtypes',
'fulltext', 'fulltext',
'hasParents', 'hasParents',
'hasSubtasks', 'hasSubtasks',
@ -178,6 +192,10 @@ final class ManiphestTaskSearchEngine
$query->withPriorities($map['priorities']); $query->withPriorities($map['priorities']);
} }
if ($map['subtypes']) {
$query->withSubtypes($map['subtypes']);
}
if ($map['createdStart']) { if ($map['createdStart']) {
$query->withDateCreatedAfter($map['createdStart']); $query->withDateCreatedAfter($map['createdStart']);
} }

View file

@ -0,0 +1,44 @@
<?php
final class ManiphestTaskSubtypeDatasource
extends PhabricatorTypeaheadDatasource {
public function getBrowseTitle() {
return pht('Browse Subtypes');
}
public function getPlaceholderText() {
return pht('Type a task subtype name...');
}
public function getDatasourceApplicationClass() {
return 'PhabricatorManiphestApplication';
}
public function loadResults() {
$results = $this->buildResults();
return $this->filterResultsAgainstTokens($results);
}
protected function renderSpecialTokens(array $values) {
return $this->renderTokensFromResults($this->buildResults(), $values);
}
private function buildResults() {
$results = array();
$subtype_map = id(new ManiphestTask())->newEditEngineSubtypeMap();
foreach ($subtype_map as $key => $subtype) {
$result = id(new PhabricatorTypeaheadResult())
->setIcon($subtype->getIcon())
->setPHID($key)
->setName($subtype->getName());
$results[$key] = $result;
}
return $results;
}
}

View file

@ -17,6 +17,7 @@ abstract class PhabricatorSearchField extends Phobject {
private $aliases = array(); private $aliases = array();
private $errors = array(); private $errors = array();
private $description; private $description;
private $isHidden;
/* -( Configuring Fields )------------------------------------------------- */ /* -( Configuring Fields )------------------------------------------------- */
@ -188,6 +189,30 @@ abstract class PhabricatorSearchField extends Phobject {
} }
/**
* Hide this field from the web UI.
*
* @param bool True to hide the field from the web UI.
* @return this
* @task config
*/
public function setIsHidden($is_hidden) {
$this->isHidden = $is_hidden;
return $this;
}
/**
* Should this field be hidden from the web UI?
*
* @return bool True to hide the field in the web UI.
* @task config
*/
public function getIsHidden() {
return $this->isHidden;
}
/* -( Handling Errors )---------------------------------------------------- */ /* -( Handling Errors )---------------------------------------------------- */
@ -273,6 +298,10 @@ abstract class PhabricatorSearchField extends Phobject {
protected function renderControl() { protected function renderControl() {
if ($this->getIsHidden()) {
return null;
}
$control = $this->newControl(); $control = $this->newControl();
if (!$control) { if (!$control) {

View file

@ -27,6 +27,10 @@ final class PhabricatorEditEngineSubtype
return $this->name; return $this->name;
} }
public function getIcon() {
return 'fa-drivers-license-o';
}
public static function validateSubtypeKey($subtype) { public static function validateSubtypeKey($subtype) {
if (strlen($subtype) > 64) { if (strlen($subtype) > 64) {
throw new Exception( throw new Exception(