Index: src/__phutil_library_map__.php =================================================================== --- src/__phutil_library_map__.php +++ src/__phutil_library_map__.php @@ -676,6 +676,7 @@ 'DrydockResourceCloseController' => 'applications/drydock/controller/DrydockResourceCloseController.php', 'DrydockResourceListController' => 'applications/drydock/controller/DrydockResourceListController.php', 'DrydockResourceQuery' => 'applications/drydock/query/DrydockResourceQuery.php', + 'DrydockResourceSearchEngine' => 'applications/drydock/query/DrydockResourceSearchEngine.php', 'DrydockResourceStatus' => 'applications/drydock/constants/DrydockResourceStatus.php', 'DrydockResourceViewController' => 'applications/drydock/controller/DrydockResourceViewController.php', 'DrydockSFTPFilesystemInterface' => 'applications/drydock/interface/filesystem/DrydockSFTPFilesystemInterface.php', @@ -3091,8 +3092,13 @@ 1 => 'PhabricatorPolicyInterface', ), 'DrydockResourceCloseController' => 'DrydockController', - 'DrydockResourceListController' => 'DrydockController', + 'DrydockResourceListController' => + array( + 0 => 'DrydockController', + 1 => 'PhabricatorApplicationSearchResultsControllerInterface', + ), 'DrydockResourceQuery' => 'PhabricatorCursorPagedPolicyAwareQuery', + 'DrydockResourceSearchEngine' => 'PhabricatorApplicationSearchEngine', 'DrydockResourceStatus' => 'DrydockConstants', 'DrydockResourceViewController' => 'DrydockController', 'DrydockSFTPFilesystemInterface' => 'DrydockFilesystemInterface', Index: src/applications/drydock/application/PhabricatorApplicationDrydock.php =================================================================== --- src/applications/drydock/application/PhabricatorApplicationDrydock.php +++ src/applications/drydock/application/PhabricatorApplicationDrydock.php @@ -41,7 +41,7 @@ 'edit/(?P[1-9]\d*)/' => 'DrydockBlueprintEditController', ), 'resource/' => array( - '' => 'DrydockResourceListController', + '(?:query/(?P[^/]+)/)?' => 'DrydockResourceListController', '(?P[1-9]\d*)/' => 'DrydockResourceViewController', '(?P[1-9]\d*)/close/' => 'DrydockResourceCloseController', ), Index: src/applications/drydock/constants/DrydockResourceStatus.php =================================================================== --- src/applications/drydock/constants/DrydockResourceStatus.php +++ src/applications/drydock/constants/DrydockResourceStatus.php @@ -9,15 +9,25 @@ const STATUS_DESTROYED = 4; public static function getNameForStatus($status) { - static $map = array( - self::STATUS_PENDING => 'Pending', - self::STATUS_OPEN => 'Open', - self::STATUS_CLOSED => 'Closed', - self::STATUS_BROKEN => 'Broken', - self::STATUS_DESTROYED => 'Destroyed', + $map = array( + self::STATUS_PENDING => pht('Pending'), + self::STATUS_OPEN => pht('Open'), + self::STATUS_CLOSED => pht('Closed'), + self::STATUS_BROKEN => pht('Broken'), + self::STATUS_DESTROYED => pht('Destroyed'), ); return idx($map, $status, 'Unknown'); } + public static function getAllStatuses() { + return array( + self::STATUS_PENDING, + self::STATUS_OPEN, + self::STATUS_CLOSED, + self::STATUS_BROKEN, + self::STATUS_DESTROYED, + ); + } + } Index: src/applications/drydock/controller/DrydockController.php =================================================================== --- src/applications/drydock/controller/DrydockController.php +++ src/applications/drydock/controller/DrydockController.php @@ -14,8 +14,9 @@ ->setViewer($this->getRequest()->getUser()) ->addNavigationItems($nav->getMenu(), pht('Leases')); - $nav->addLabel(pht('Resources')); - $nav->addFilter('resource', 'Resources'); + id(new DrydockResourceSearchEngine()) + ->setViewer($this->getRequest()->getUser()) + ->addNavigationItems($nav->getMenu(), pht('Resources')); $nav->addLabel(pht('Logs')); $nav->addFilter('log', 'Logs'); Index: src/applications/drydock/controller/DrydockResourceListController.php =================================================================== --- src/applications/drydock/controller/DrydockResourceListController.php +++ src/applications/drydock/controller/DrydockResourceListController.php @@ -1,43 +1,34 @@ getRequest(); - $user = $request->getUser(); - - $title = pht('Resources'); + private $queryKey; - $resource_header = id(new PHUIHeaderView()) - ->setHeader($title); - - $pager = new AphrontPagerView(); - $pager->setURI(new PhutilURI('/drydock/resource/'), 'offset'); - $resources = id(new DrydockResourceQuery()) - ->setViewer($user) - ->executeWithOffsetPager($pager); + public function shouldAllowPublic() { + return true; + } - $resource_list = $this->buildResourceListView($resources); + public function willProcessRequest(array $data) { + $this->queryKey = idx($data, 'queryKey'); + } - $crumbs = $this->buildApplicationCrumbs(); - $crumbs->addTextCrumb($title, $request->getRequestURI()); + public function processRequest() { + $request = $this->getRequest(); + $controller = id(new PhabricatorApplicationSearchController($request)) + ->setQueryKey($this->queryKey) + ->setSearchEngine(new DrydockResourceSearchEngine()) + ->setNavigation($this->buildSideNav()); - $nav = $this->buildSideNav('resource'); - $nav->setCrumbs($crumbs); - $nav->appendChild( - array( - $resource_header, - $resource_list, - $pager, - )); + return $this->delegateToController($controller); + } - return $this->buildApplicationPage( - $nav, - array( - 'title' => $title, - 'device' => true, - )); + public function renderResultsList( + array $resources, + PhabricatorSavedQuery $query) { + assert_instances_of($resources, 'DrydockResource'); + return $this->buildResourceListView($resources); } } Index: src/applications/drydock/query/DrydockResourceSearchEngine.php =================================================================== --- /dev/null +++ src/applications/drydock/query/DrydockResourceSearchEngine.php @@ -0,0 +1,80 @@ +setParameter( + 'statuses', + $this->readListFromRequest($request, 'statuses')); + + return $saved; + } + + public function buildQueryFromSavedQuery(PhabricatorSavedQuery $saved) { + $query = id(new DrydockResourceQuery()); + + $statuses = $saved->getParameter('statuses', array()); + if ($statuses) { + $query->withStatuses($statuses); + } + + return $query; + } + + public function buildSearchForm( + AphrontFormView $form, + PhabricatorSavedQuery $saved) { + + $statuses = $saved->getParameter('statuses', array()); + + $status_control = id(new AphrontFormCheckboxControl()) + ->setLabel(pht('Status')); + foreach (DrydockResourceStatus::getAllStatuses() as $status) { + $status_control->addCheckbox( + 'statuses[]', + $status, + DrydockResourceStatus::getNameForStatus($status), + in_array($status, $statuses)); + } + + $form + ->appendChild($status_control); + + } + + protected function getURI($path) { + return '/drydock/resource/'.$path; + } + + public function getBuiltinQueryNames() { + $names = array( + 'active' => pht('Active Resources'), + 'all' => pht('All Resources'), + ); + + return $names; + } + + public function buildSavedQueryFromBuiltin($query_key) { + $query = $this->newSavedQuery(); + $query->setQueryKey($query_key); + + switch ($query_key) { + case 'active': + return $query->setParameter( + 'statuses', + array( + DrydockResourceStatus::STATUS_PENDING, + DrydockResourceStatus::STATUS_OPEN, + )); + case 'all': + return $query; + } + + return parent::buildSavedQueryFromBuiltin($query_key); + } + +}