mirror of
https://we.phorge.it/source/phorge.git
synced 2024-12-30 01:10:58 +01:00
Move Maniphest list rendering to SearchEngine
Summary: Ref T4986. Moves Maniphest over. Nothing tricky here, just a complex block of rendering. Test Plan: Viewed Maniphest list. Created Maniphest panel. Used batch editor, drag-and-drop. Reviewers: btrahan Reviewed By: btrahan Subscribers: epriestley Maniphest Tasks: T4986 Differential Revision: https://secure.phabricator.com/D9139
This commit is contained in:
parent
d653fa13de
commit
e5e95352c7
4 changed files with 326 additions and 270 deletions
|
@ -932,6 +932,7 @@ phutil_register_library_map(array(
|
||||||
'ManiphestTaskProject' => 'applications/maniphest/storage/ManiphestTaskProject.php',
|
'ManiphestTaskProject' => 'applications/maniphest/storage/ManiphestTaskProject.php',
|
||||||
'ManiphestTaskProjectsView' => 'applications/maniphest/view/ManiphestTaskProjectsView.php',
|
'ManiphestTaskProjectsView' => 'applications/maniphest/view/ManiphestTaskProjectsView.php',
|
||||||
'ManiphestTaskQuery' => 'applications/maniphest/query/ManiphestTaskQuery.php',
|
'ManiphestTaskQuery' => 'applications/maniphest/query/ManiphestTaskQuery.php',
|
||||||
|
'ManiphestTaskResultListView' => 'applications/maniphest/view/ManiphestTaskResultListView.php',
|
||||||
'ManiphestTaskSearchEngine' => 'applications/maniphest/query/ManiphestTaskSearchEngine.php',
|
'ManiphestTaskSearchEngine' => 'applications/maniphest/query/ManiphestTaskSearchEngine.php',
|
||||||
'ManiphestTaskStatus' => 'applications/maniphest/constants/ManiphestTaskStatus.php',
|
'ManiphestTaskStatus' => 'applications/maniphest/constants/ManiphestTaskStatus.php',
|
||||||
'ManiphestTaskStatusTestCase' => 'applications/maniphest/constants/__tests__/ManiphestTaskStatusTestCase.php',
|
'ManiphestTaskStatusTestCase' => 'applications/maniphest/constants/__tests__/ManiphestTaskStatusTestCase.php',
|
||||||
|
@ -3649,11 +3650,7 @@ phutil_register_library_map(array(
|
||||||
'ManiphestTaskDescriptionPreviewController' => 'ManiphestController',
|
'ManiphestTaskDescriptionPreviewController' => 'ManiphestController',
|
||||||
'ManiphestTaskDetailController' => 'ManiphestController',
|
'ManiphestTaskDetailController' => 'ManiphestController',
|
||||||
'ManiphestTaskEditController' => 'ManiphestController',
|
'ManiphestTaskEditController' => 'ManiphestController',
|
||||||
'ManiphestTaskListController' =>
|
'ManiphestTaskListController' => 'ManiphestController',
|
||||||
array(
|
|
||||||
0 => 'ManiphestController',
|
|
||||||
1 => 'PhabricatorApplicationSearchResultsControllerInterface',
|
|
||||||
),
|
|
||||||
'ManiphestTaskListView' => 'ManiphestView',
|
'ManiphestTaskListView' => 'ManiphestView',
|
||||||
'ManiphestTaskMailReceiver' => 'PhabricatorObjectMailReceiver',
|
'ManiphestTaskMailReceiver' => 'PhabricatorObjectMailReceiver',
|
||||||
'ManiphestTaskOwner' => 'ManiphestConstants',
|
'ManiphestTaskOwner' => 'ManiphestConstants',
|
||||||
|
@ -3661,6 +3658,7 @@ phutil_register_library_map(array(
|
||||||
'ManiphestTaskProject' => 'ManiphestDAO',
|
'ManiphestTaskProject' => 'ManiphestDAO',
|
||||||
'ManiphestTaskProjectsView' => 'ManiphestView',
|
'ManiphestTaskProjectsView' => 'ManiphestView',
|
||||||
'ManiphestTaskQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
|
'ManiphestTaskQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
|
||||||
|
'ManiphestTaskResultListView' => 'ManiphestView',
|
||||||
'ManiphestTaskSearchEngine' => 'PhabricatorApplicationSearchEngine',
|
'ManiphestTaskSearchEngine' => 'PhabricatorApplicationSearchEngine',
|
||||||
'ManiphestTaskStatus' => 'ManiphestConstants',
|
'ManiphestTaskStatus' => 'ManiphestConstants',
|
||||||
'ManiphestTaskStatusTestCase' => 'PhabricatorTestCase',
|
'ManiphestTaskStatusTestCase' => 'PhabricatorTestCase',
|
||||||
|
@ -4635,11 +4633,7 @@ phutil_register_library_map(array(
|
||||||
'PhabricatorPasteDAO' => 'PhabricatorLiskDAO',
|
'PhabricatorPasteDAO' => 'PhabricatorLiskDAO',
|
||||||
'PhabricatorPasteEditController' => 'PhabricatorPasteController',
|
'PhabricatorPasteEditController' => 'PhabricatorPasteController',
|
||||||
'PhabricatorPasteEditor' => 'PhabricatorApplicationTransactionEditor',
|
'PhabricatorPasteEditor' => 'PhabricatorApplicationTransactionEditor',
|
||||||
'PhabricatorPasteListController' =>
|
'PhabricatorPasteListController' => 'PhabricatorPasteController',
|
||||||
array(
|
|
||||||
0 => 'PhabricatorPasteController',
|
|
||||||
1 => 'PhabricatorApplicationSearchResultsControllerInterface',
|
|
||||||
),
|
|
||||||
'PhabricatorPastePHIDTypePaste' => 'PhabricatorPHIDType',
|
'PhabricatorPastePHIDTypePaste' => 'PhabricatorPHIDType',
|
||||||
'PhabricatorPasteQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
|
'PhabricatorPasteQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
|
||||||
'PhabricatorPasteRemarkupRule' => 'PhabricatorRemarkupRuleObject',
|
'PhabricatorPasteRemarkupRule' => 'PhabricatorRemarkupRuleObject',
|
||||||
|
@ -4658,18 +4652,10 @@ phutil_register_library_map(array(
|
||||||
'PhabricatorPeopleEmpowerController' => 'PhabricatorPeopleController',
|
'PhabricatorPeopleEmpowerController' => 'PhabricatorPeopleController',
|
||||||
'PhabricatorPeopleHovercardEventListener' => 'PhabricatorEventListener',
|
'PhabricatorPeopleHovercardEventListener' => 'PhabricatorEventListener',
|
||||||
'PhabricatorPeopleLdapController' => 'PhabricatorPeopleController',
|
'PhabricatorPeopleLdapController' => 'PhabricatorPeopleController',
|
||||||
'PhabricatorPeopleListController' =>
|
'PhabricatorPeopleListController' => 'PhabricatorPeopleController',
|
||||||
array(
|
|
||||||
0 => 'PhabricatorPeopleController',
|
|
||||||
1 => 'PhabricatorApplicationSearchResultsControllerInterface',
|
|
||||||
),
|
|
||||||
'PhabricatorPeopleLogQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
|
'PhabricatorPeopleLogQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
|
||||||
'PhabricatorPeopleLogSearchEngine' => 'PhabricatorApplicationSearchEngine',
|
'PhabricatorPeopleLogSearchEngine' => 'PhabricatorApplicationSearchEngine',
|
||||||
'PhabricatorPeopleLogsController' =>
|
'PhabricatorPeopleLogsController' => 'PhabricatorPeopleController',
|
||||||
array(
|
|
||||||
0 => 'PhabricatorPeopleController',
|
|
||||||
1 => 'PhabricatorApplicationSearchResultsControllerInterface',
|
|
||||||
),
|
|
||||||
'PhabricatorPeopleNewController' => 'PhabricatorPeopleController',
|
'PhabricatorPeopleNewController' => 'PhabricatorPeopleController',
|
||||||
'PhabricatorPeoplePHIDTypeExternal' => 'PhabricatorPHIDType',
|
'PhabricatorPeoplePHIDTypeExternal' => 'PhabricatorPHIDType',
|
||||||
'PhabricatorPeoplePHIDTypeUser' => 'PhabricatorPHIDType',
|
'PhabricatorPeoplePHIDTypeUser' => 'PhabricatorPHIDType',
|
||||||
|
|
|
@ -1,8 +1,7 @@
|
||||||
<?php
|
<?php
|
||||||
|
|
||||||
final class ManiphestTaskListController
|
final class ManiphestTaskListController
|
||||||
extends ManiphestController
|
extends ManiphestController {
|
||||||
implements PhabricatorApplicationSearchResultsControllerInterface {
|
|
||||||
|
|
||||||
private $queryKey;
|
private $queryKey;
|
||||||
|
|
||||||
|
@ -18,257 +17,12 @@ final class ManiphestTaskListController
|
||||||
$request = $this->getRequest();
|
$request = $this->getRequest();
|
||||||
$controller = id(new PhabricatorApplicationSearchController($request))
|
$controller = id(new PhabricatorApplicationSearchController($request))
|
||||||
->setQueryKey($this->queryKey)
|
->setQueryKey($this->queryKey)
|
||||||
->setSearchEngine(new ManiphestTaskSearchEngine())
|
->setSearchEngine(
|
||||||
|
id(new ManiphestTaskSearchEngine())
|
||||||
|
->setShowBatchControls(true))
|
||||||
->setNavigation($this->buildSideNavView());
|
->setNavigation($this->buildSideNavView());
|
||||||
|
|
||||||
return $this->delegateToController($controller);
|
return $this->delegateToController($controller);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function renderResultsList(
|
|
||||||
array $tasks,
|
|
||||||
PhabricatorSavedQuery $query) {
|
|
||||||
assert_instances_of($tasks, 'ManiphestTask');
|
|
||||||
|
|
||||||
$viewer = $this->getRequest()->getUser();
|
|
||||||
|
|
||||||
// If we didn't match anything, just pick up the default empty state.
|
|
||||||
if (!$tasks) {
|
|
||||||
return id(new PHUIObjectItemListView())
|
|
||||||
->setUser($viewer);
|
|
||||||
}
|
|
||||||
|
|
||||||
$group_parameter = nonempty($query->getParameter('group'), 'priority');
|
|
||||||
$order_parameter = nonempty($query->getParameter('order'), 'priority');
|
|
||||||
|
|
||||||
$handles = ManiphestTaskListView::loadTaskHandles($viewer, $tasks);
|
|
||||||
$groups = $this->groupTasks(
|
|
||||||
$tasks,
|
|
||||||
$group_parameter,
|
|
||||||
$handles);
|
|
||||||
|
|
||||||
$can_edit_priority = $this->hasApplicationCapability(
|
|
||||||
ManiphestCapabilityEditPriority::CAPABILITY);
|
|
||||||
|
|
||||||
$can_drag = ($order_parameter == 'priority') &&
|
|
||||||
($can_edit_priority) &&
|
|
||||||
($group_parameter == 'none' || $group_parameter == 'priority');
|
|
||||||
|
|
||||||
if (!$viewer->isLoggedIn()) {
|
|
||||||
// TODO: (T603) Eventually, we conceivably need to make each task
|
|
||||||
// draggable individually, since the user may be able to edit some but
|
|
||||||
// not others.
|
|
||||||
$can_drag = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
$result = array();
|
|
||||||
|
|
||||||
$lists = array();
|
|
||||||
foreach ($groups as $group => $list) {
|
|
||||||
$task_list = new ManiphestTaskListView();
|
|
||||||
$task_list->setShowBatchControls(true);
|
|
||||||
if ($can_drag) {
|
|
||||||
$task_list->setShowSubpriorityControls(true);
|
|
||||||
}
|
|
||||||
$task_list->setUser($viewer);
|
|
||||||
$task_list->setTasks($list);
|
|
||||||
$task_list->setHandles($handles);
|
|
||||||
|
|
||||||
$header = javelin_tag(
|
|
||||||
'h1',
|
|
||||||
array(
|
|
||||||
'class' => 'maniphest-task-group-header',
|
|
||||||
'sigil' => 'task-group',
|
|
||||||
'meta' => array(
|
|
||||||
'priority' => head($list)->getPriority(),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
pht('%s (%s)', $group, new PhutilNumber(count($list))));
|
|
||||||
|
|
||||||
$lists[] = phutil_tag(
|
|
||||||
'div',
|
|
||||||
array(
|
|
||||||
'class' => 'maniphest-task-group'
|
|
||||||
),
|
|
||||||
array(
|
|
||||||
$header,
|
|
||||||
$task_list,
|
|
||||||
));
|
|
||||||
}
|
|
||||||
|
|
||||||
if ($can_drag) {
|
|
||||||
Javelin::initBehavior(
|
|
||||||
'maniphest-subpriority-editor',
|
|
||||||
array(
|
|
||||||
'uri' => '/maniphest/subpriority/',
|
|
||||||
));
|
|
||||||
}
|
|
||||||
|
|
||||||
return phutil_tag(
|
|
||||||
'div',
|
|
||||||
array(
|
|
||||||
'class' => 'maniphest-list-container',
|
|
||||||
),
|
|
||||||
array(
|
|
||||||
$lists,
|
|
||||||
$this->renderBatchEditor($query),
|
|
||||||
));
|
|
||||||
}
|
|
||||||
|
|
||||||
private function groupTasks(array $tasks, $group, array $handles) {
|
|
||||||
assert_instances_of($tasks, 'ManiphestTask');
|
|
||||||
assert_instances_of($handles, 'PhabricatorObjectHandle');
|
|
||||||
|
|
||||||
$groups = $this->getTaskGrouping($tasks, $group);
|
|
||||||
|
|
||||||
$results = array();
|
|
||||||
foreach ($groups as $label_key => $tasks) {
|
|
||||||
$label = $this->getTaskLabelName($group, $label_key, $handles);
|
|
||||||
$results[$label][] = $tasks;
|
|
||||||
}
|
|
||||||
foreach ($results as $label => $task_groups) {
|
|
||||||
$results[$label] = array_mergev($task_groups);
|
|
||||||
}
|
|
||||||
|
|
||||||
return $results;
|
|
||||||
}
|
|
||||||
|
|
||||||
private function getTaskGrouping(array $tasks, $group) {
|
|
||||||
switch ($group) {
|
|
||||||
case 'priority':
|
|
||||||
return mgroup($tasks, 'getPriority');
|
|
||||||
case 'status':
|
|
||||||
return mgroup($tasks, 'getStatus');
|
|
||||||
case 'assigned':
|
|
||||||
return mgroup($tasks, 'getOwnerPHID');
|
|
||||||
case 'project':
|
|
||||||
return mgroup($tasks, 'getGroupByProjectPHID');
|
|
||||||
default:
|
|
||||||
return array(pht('Tasks') => $tasks);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private function getTaskLabelName($group, $label_key, array $handles) {
|
|
||||||
switch ($group) {
|
|
||||||
case 'priority':
|
|
||||||
return ManiphestTaskPriority::getTaskPriorityName($label_key);
|
|
||||||
case 'status':
|
|
||||||
return ManiphestTaskStatus::getTaskStatusFullName($label_key);
|
|
||||||
case 'assigned':
|
|
||||||
if ($label_key) {
|
|
||||||
return $handles[$label_key]->getFullName();
|
|
||||||
} else {
|
|
||||||
return pht('(Not Assigned)');
|
|
||||||
}
|
|
||||||
case 'project':
|
|
||||||
if ($label_key) {
|
|
||||||
return $handles[$label_key]->getFullName();
|
|
||||||
} else {
|
|
||||||
return pht('(No Project)');
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
return pht('Tasks');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private function renderBatchEditor(PhabricatorSavedQuery $saved_query) {
|
|
||||||
$user = $this->getRequest()->getUser();
|
|
||||||
|
|
||||||
$batch_capability = ManiphestCapabilityBulkEdit::CAPABILITY;
|
|
||||||
if (!$this->hasApplicationCapability($batch_capability)) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!$user->isLoggedIn()) {
|
|
||||||
// Don't show the batch editor or excel export for logged-out users.
|
|
||||||
// Technically we //could// let them export, but ehh.
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
Javelin::initBehavior(
|
|
||||||
'maniphest-batch-selector',
|
|
||||||
array(
|
|
||||||
'selectAll' => 'batch-select-all',
|
|
||||||
'selectNone' => 'batch-select-none',
|
|
||||||
'submit' => 'batch-select-submit',
|
|
||||||
'status' => 'batch-select-status-cell',
|
|
||||||
'idContainer' => 'batch-select-id-container',
|
|
||||||
'formID' => 'batch-select-form',
|
|
||||||
));
|
|
||||||
|
|
||||||
$select_all = javelin_tag(
|
|
||||||
'a',
|
|
||||||
array(
|
|
||||||
'href' => '#',
|
|
||||||
'mustcapture' => true,
|
|
||||||
'class' => 'grey button',
|
|
||||||
'id' => 'batch-select-all',
|
|
||||||
),
|
|
||||||
pht('Select All'));
|
|
||||||
|
|
||||||
$select_none = javelin_tag(
|
|
||||||
'a',
|
|
||||||
array(
|
|
||||||
'href' => '#',
|
|
||||||
'mustcapture' => true,
|
|
||||||
'class' => 'grey button',
|
|
||||||
'id' => 'batch-select-none',
|
|
||||||
),
|
|
||||||
pht('Clear Selection'));
|
|
||||||
|
|
||||||
$submit = phutil_tag(
|
|
||||||
'button',
|
|
||||||
array(
|
|
||||||
'id' => 'batch-select-submit',
|
|
||||||
'disabled' => 'disabled',
|
|
||||||
'class' => 'disabled',
|
|
||||||
),
|
|
||||||
pht("Batch Edit Selected \xC2\xBB"));
|
|
||||||
|
|
||||||
$export = javelin_tag(
|
|
||||||
'a',
|
|
||||||
array(
|
|
||||||
'href' => '/maniphest/export/'.$saved_query->getQueryKey().'/',
|
|
||||||
'class' => 'grey button',
|
|
||||||
),
|
|
||||||
pht('Export to Excel'));
|
|
||||||
|
|
||||||
$hidden = phutil_tag(
|
|
||||||
'div',
|
|
||||||
array(
|
|
||||||
'id' => 'batch-select-id-container',
|
|
||||||
),
|
|
||||||
'');
|
|
||||||
|
|
||||||
$editor = hsprintf(
|
|
||||||
'<div class="maniphest-batch-editor">'.
|
|
||||||
'<div class="batch-editor-header">%s</div>'.
|
|
||||||
'<table class="maniphest-batch-editor-layout">'.
|
|
||||||
'<tr>'.
|
|
||||||
'<td>%s%s</td>'.
|
|
||||||
'<td>%s</td>'.
|
|
||||||
'<td id="batch-select-status-cell">%s</td>'.
|
|
||||||
'<td class="batch-select-submit-cell">%s%s</td>'.
|
|
||||||
'</tr>'.
|
|
||||||
'</table>'.
|
|
||||||
'</div>',
|
|
||||||
pht('Batch Task Editor'),
|
|
||||||
$select_all,
|
|
||||||
$select_none,
|
|
||||||
$export,
|
|
||||||
'',
|
|
||||||
$submit,
|
|
||||||
$hidden);
|
|
||||||
|
|
||||||
$editor = phabricator_form(
|
|
||||||
$user,
|
|
||||||
array(
|
|
||||||
'method' => 'POST',
|
|
||||||
'action' => '/maniphest/batch/',
|
|
||||||
'id' => 'batch-select-form',
|
|
||||||
),
|
|
||||||
$editor);
|
|
||||||
|
|
||||||
return $editor;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,17 @@
|
||||||
final class ManiphestTaskSearchEngine
|
final class ManiphestTaskSearchEngine
|
||||||
extends PhabricatorApplicationSearchEngine {
|
extends PhabricatorApplicationSearchEngine {
|
||||||
|
|
||||||
|
private $showBatchControls;
|
||||||
|
|
||||||
|
public function setShowBatchControls($show_batch_controls) {
|
||||||
|
$this->showBatchControls = $show_batch_controls;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getApplicationClassName() {
|
||||||
|
return 'PhabricatorApplicationManiphest';
|
||||||
|
}
|
||||||
|
|
||||||
public function getCustomFieldObject() {
|
public function getCustomFieldObject() {
|
||||||
return new ManiphestTask();
|
return new ManiphestTask();
|
||||||
}
|
}
|
||||||
|
@ -473,4 +484,30 @@ final class ManiphestTaskSearchEngine
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected function renderResultList(
|
||||||
|
array $tasks,
|
||||||
|
PhabricatorSavedQuery $saved,
|
||||||
|
array $handles) {
|
||||||
|
|
||||||
|
$viewer = $this->requireViewer();
|
||||||
|
|
||||||
|
$can_edit_priority = PhabricatorPolicyFilter::hasCapability(
|
||||||
|
$viewer,
|
||||||
|
$this->getApplication(),
|
||||||
|
ManiphestCapabilityEditPriority::CAPABILITY);
|
||||||
|
|
||||||
|
$can_bulk_edit = PhabricatorPolicyFilter::hasCapability(
|
||||||
|
$viewer,
|
||||||
|
$this->getApplication(),
|
||||||
|
ManiphestCapabilityBulkEdit::CAPABILITY);
|
||||||
|
|
||||||
|
return id(new ManiphestTaskResultListView())
|
||||||
|
->setUser($viewer)
|
||||||
|
->setTasks($tasks)
|
||||||
|
->setSavedQuery($saved)
|
||||||
|
->setCanEditPriority($can_edit_priority)
|
||||||
|
->setCanBatchEdit($can_bulk_edit)
|
||||||
|
->setShowBatchControls($this->showBatchControls);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
279
src/applications/maniphest/view/ManiphestTaskResultListView.php
Normal file
279
src/applications/maniphest/view/ManiphestTaskResultListView.php
Normal file
|
@ -0,0 +1,279 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
final class ManiphestTaskResultListView extends ManiphestView {
|
||||||
|
|
||||||
|
private $tasks;
|
||||||
|
private $savedQuery;
|
||||||
|
private $canEditPriority;
|
||||||
|
private $canBatchEdit;
|
||||||
|
private $showBatchControls;
|
||||||
|
|
||||||
|
public function setSavedQuery(PhabricatorSavedQuery $query) {
|
||||||
|
$this->savedQuery = $query;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setTasks(array $tasks) {
|
||||||
|
$this->tasks = $tasks;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setCanEditPriority($can_edit_priority) {
|
||||||
|
$this->canEditPriority = $can_edit_priority;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setCanBatchEdit($can_batch_edit) {
|
||||||
|
$this->canBatchEdit = $can_batch_edit;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setShowBatchControls($show_batch_controls) {
|
||||||
|
$this->showBatchControls = $show_batch_controls;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function render() {
|
||||||
|
$viewer = $this->getUser();
|
||||||
|
$tasks = $this->tasks;
|
||||||
|
$query = $this->savedQuery;
|
||||||
|
|
||||||
|
// If we didn't match anything, just pick up the default empty state.
|
||||||
|
if (!$tasks) {
|
||||||
|
return id(new PHUIObjectItemListView())
|
||||||
|
->setUser($viewer);
|
||||||
|
}
|
||||||
|
|
||||||
|
$group_parameter = nonempty($query->getParameter('group'), 'priority');
|
||||||
|
$order_parameter = nonempty($query->getParameter('order'), 'priority');
|
||||||
|
|
||||||
|
$handles = ManiphestTaskListView::loadTaskHandles($viewer, $tasks);
|
||||||
|
$groups = $this->groupTasks(
|
||||||
|
$tasks,
|
||||||
|
$group_parameter,
|
||||||
|
$handles);
|
||||||
|
|
||||||
|
$can_edit_priority = $this->canEditPriority;
|
||||||
|
|
||||||
|
$can_drag = ($order_parameter == 'priority') &&
|
||||||
|
($can_edit_priority) &&
|
||||||
|
($group_parameter == 'none' || $group_parameter == 'priority');
|
||||||
|
|
||||||
|
if (!$viewer->isLoggedIn()) {
|
||||||
|
// TODO: (T603) Eventually, we conceivably need to make each task
|
||||||
|
// draggable individually, since the user may be able to edit some but
|
||||||
|
// not others.
|
||||||
|
$can_drag = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
$result = array();
|
||||||
|
|
||||||
|
$lists = array();
|
||||||
|
foreach ($groups as $group => $list) {
|
||||||
|
$task_list = new ManiphestTaskListView();
|
||||||
|
$task_list->setShowBatchControls($this->showBatchControls);
|
||||||
|
if ($can_drag) {
|
||||||
|
$task_list->setShowSubpriorityControls(true);
|
||||||
|
}
|
||||||
|
$task_list->setUser($viewer);
|
||||||
|
$task_list->setTasks($list);
|
||||||
|
$task_list->setHandles($handles);
|
||||||
|
|
||||||
|
$header = javelin_tag(
|
||||||
|
'h1',
|
||||||
|
array(
|
||||||
|
'class' => 'maniphest-task-group-header',
|
||||||
|
'sigil' => 'task-group',
|
||||||
|
'meta' => array(
|
||||||
|
'priority' => head($list)->getPriority(),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
pht('%s (%s)', $group, new PhutilNumber(count($list))));
|
||||||
|
|
||||||
|
$lists[] = phutil_tag(
|
||||||
|
'div',
|
||||||
|
array(
|
||||||
|
'class' => 'maniphest-task-group'
|
||||||
|
),
|
||||||
|
array(
|
||||||
|
$header,
|
||||||
|
$task_list,
|
||||||
|
));
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($can_drag) {
|
||||||
|
Javelin::initBehavior(
|
||||||
|
'maniphest-subpriority-editor',
|
||||||
|
array(
|
||||||
|
'uri' => '/maniphest/subpriority/',
|
||||||
|
));
|
||||||
|
}
|
||||||
|
|
||||||
|
return phutil_tag(
|
||||||
|
'div',
|
||||||
|
array(
|
||||||
|
'class' => 'maniphest-list-container',
|
||||||
|
),
|
||||||
|
array(
|
||||||
|
$lists,
|
||||||
|
$this->showBatchControls ? $this->renderBatchEditor($query) : null,
|
||||||
|
));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private function groupTasks(array $tasks, $group, array $handles) {
|
||||||
|
assert_instances_of($tasks, 'ManiphestTask');
|
||||||
|
assert_instances_of($handles, 'PhabricatorObjectHandle');
|
||||||
|
|
||||||
|
$groups = $this->getTaskGrouping($tasks, $group);
|
||||||
|
|
||||||
|
$results = array();
|
||||||
|
foreach ($groups as $label_key => $tasks) {
|
||||||
|
$label = $this->getTaskLabelName($group, $label_key, $handles);
|
||||||
|
$results[$label][] = $tasks;
|
||||||
|
}
|
||||||
|
foreach ($results as $label => $task_groups) {
|
||||||
|
$results[$label] = array_mergev($task_groups);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $results;
|
||||||
|
}
|
||||||
|
|
||||||
|
private function getTaskGrouping(array $tasks, $group) {
|
||||||
|
switch ($group) {
|
||||||
|
case 'priority':
|
||||||
|
return mgroup($tasks, 'getPriority');
|
||||||
|
case 'status':
|
||||||
|
return mgroup($tasks, 'getStatus');
|
||||||
|
case 'assigned':
|
||||||
|
return mgroup($tasks, 'getOwnerPHID');
|
||||||
|
case 'project':
|
||||||
|
return mgroup($tasks, 'getGroupByProjectPHID');
|
||||||
|
default:
|
||||||
|
return array(pht('Tasks') => $tasks);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private function getTaskLabelName($group, $label_key, array $handles) {
|
||||||
|
switch ($group) {
|
||||||
|
case 'priority':
|
||||||
|
return ManiphestTaskPriority::getTaskPriorityName($label_key);
|
||||||
|
case 'status':
|
||||||
|
return ManiphestTaskStatus::getTaskStatusFullName($label_key);
|
||||||
|
case 'assigned':
|
||||||
|
if ($label_key) {
|
||||||
|
return $handles[$label_key]->getFullName();
|
||||||
|
} else {
|
||||||
|
return pht('(Not Assigned)');
|
||||||
|
}
|
||||||
|
case 'project':
|
||||||
|
if ($label_key) {
|
||||||
|
return $handles[$label_key]->getFullName();
|
||||||
|
} else {
|
||||||
|
return pht('(No Project)');
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
return pht('Tasks');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private function renderBatchEditor(PhabricatorSavedQuery $saved_query) {
|
||||||
|
$user = $this->getUser();
|
||||||
|
|
||||||
|
if (!$this->canBatchEdit) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!$user->isLoggedIn()) {
|
||||||
|
// Don't show the batch editor or excel export for logged-out users.
|
||||||
|
// Technically we //could// let them export, but ehh.
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
Javelin::initBehavior(
|
||||||
|
'maniphest-batch-selector',
|
||||||
|
array(
|
||||||
|
'selectAll' => 'batch-select-all',
|
||||||
|
'selectNone' => 'batch-select-none',
|
||||||
|
'submit' => 'batch-select-submit',
|
||||||
|
'status' => 'batch-select-status-cell',
|
||||||
|
'idContainer' => 'batch-select-id-container',
|
||||||
|
'formID' => 'batch-select-form',
|
||||||
|
));
|
||||||
|
|
||||||
|
$select_all = javelin_tag(
|
||||||
|
'a',
|
||||||
|
array(
|
||||||
|
'href' => '#',
|
||||||
|
'mustcapture' => true,
|
||||||
|
'class' => 'grey button',
|
||||||
|
'id' => 'batch-select-all',
|
||||||
|
),
|
||||||
|
pht('Select All'));
|
||||||
|
|
||||||
|
$select_none = javelin_tag(
|
||||||
|
'a',
|
||||||
|
array(
|
||||||
|
'href' => '#',
|
||||||
|
'mustcapture' => true,
|
||||||
|
'class' => 'grey button',
|
||||||
|
'id' => 'batch-select-none',
|
||||||
|
),
|
||||||
|
pht('Clear Selection'));
|
||||||
|
|
||||||
|
$submit = phutil_tag(
|
||||||
|
'button',
|
||||||
|
array(
|
||||||
|
'id' => 'batch-select-submit',
|
||||||
|
'disabled' => 'disabled',
|
||||||
|
'class' => 'disabled',
|
||||||
|
),
|
||||||
|
pht("Batch Edit Selected \xC2\xBB"));
|
||||||
|
|
||||||
|
$export = javelin_tag(
|
||||||
|
'a',
|
||||||
|
array(
|
||||||
|
'href' => '/maniphest/export/'.$saved_query->getQueryKey().'/',
|
||||||
|
'class' => 'grey button',
|
||||||
|
),
|
||||||
|
pht('Export to Excel'));
|
||||||
|
|
||||||
|
$hidden = phutil_tag(
|
||||||
|
'div',
|
||||||
|
array(
|
||||||
|
'id' => 'batch-select-id-container',
|
||||||
|
),
|
||||||
|
'');
|
||||||
|
|
||||||
|
$editor = hsprintf(
|
||||||
|
'<div class="maniphest-batch-editor">'.
|
||||||
|
'<div class="batch-editor-header">%s</div>'.
|
||||||
|
'<table class="maniphest-batch-editor-layout">'.
|
||||||
|
'<tr>'.
|
||||||
|
'<td>%s%s</td>'.
|
||||||
|
'<td>%s</td>'.
|
||||||
|
'<td id="batch-select-status-cell">%s</td>'.
|
||||||
|
'<td class="batch-select-submit-cell">%s%s</td>'.
|
||||||
|
'</tr>'.
|
||||||
|
'</table>'.
|
||||||
|
'</div>',
|
||||||
|
pht('Batch Task Editor'),
|
||||||
|
$select_all,
|
||||||
|
$select_none,
|
||||||
|
$export,
|
||||||
|
'',
|
||||||
|
$submit,
|
||||||
|
$hidden);
|
||||||
|
|
||||||
|
$editor = phabricator_form(
|
||||||
|
$user,
|
||||||
|
array(
|
||||||
|
'method' => 'POST',
|
||||||
|
'action' => '/maniphest/batch/',
|
||||||
|
'id' => 'batch-select-form',
|
||||||
|
),
|
||||||
|
$editor);
|
||||||
|
|
||||||
|
return $editor;
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in a new issue