diff --git a/src/applications/audit/application/PhabricatorApplicationAudit.php b/src/applications/audit/application/PhabricatorApplicationAudit.php index ee3502f87..a229f0d99 100644 --- a/src/applications/audit/application/PhabricatorApplicationAudit.php +++ b/src/applications/audit/application/PhabricatorApplicationAudit.php @@ -1,88 +1,92 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationAudit extends PhabricatorApplication { public function getShortDescription() { return 'Audit Code'; } public function getBaseURI() { return '/audit/'; } public function getAutospriteName() { return 'audit'; } public function getRoutes() { return array( '/audit/' => array( '' => 'PhabricatorAuditListController', 'view/(?P<filter>[^/]+)/(?:(?P<name>[^/]+)/)?' => 'PhabricatorAuditListController', 'addcomment/' => 'PhabricatorAuditAddCommentController', 'preview/(?P<id>\d+)/' => 'PhabricatorAuditPreviewController', ), ); } - public function getCoreApplicationOrder() { + public function getApplicationGroup() { + return self::GROUP_CORE; + } + + public function getApplicationOrder() { return 0.130; } public function loadStatus(PhabricatorUser $user) { $status = array(); $phids = PhabricatorAuditCommentEditor::loadAuditPHIDsForUser($user); $audits = id(new PhabricatorAuditQuery()) ->withAuditorPHIDs($phids) ->withStatus(PhabricatorAuditQuery::STATUS_OPEN) ->withAwaitingUser($user) ->execute(); $count = count($audits); $type = $count ? PhabricatorApplicationStatusView::TYPE_INFO : PhabricatorApplicationStatusView::TYPE_EMPTY; $status[] = id(new PhabricatorApplicationStatusView()) ->setType($type) ->setText(pht('%d Commit(s) Awaiting Audit', $count)) ->setCount($count); $commits = id(new PhabricatorAuditCommitQuery()) ->withAuthorPHIDs($phids) ->withStatus(PhabricatorAuditQuery::STATUS_OPEN) ->execute(); $count = count($commits); $type = $count ? PhabricatorApplicationStatusView::TYPE_NEEDS_ATTENTION : PhabricatorApplicationStatusView::TYPE_EMPTY; $status[] = id(new PhabricatorApplicationStatusView()) ->setType($type) ->setText(pht('%d Problem Commit(s)', $count)) ->setCount($count); return $status; } } diff --git a/src/applications/base/PhabricatorApplication.php b/src/applications/base/PhabricatorApplication.php index 1c5f23eef..657739ef5 100644 --- a/src/applications/base/PhabricatorApplication.php +++ b/src/applications/base/PhabricatorApplication.php @@ -1,181 +1,205 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ /** * @task info Application Information * @task ui UI Integration * @task uri URI Routing * @task fact Fact Integration * @task meta Application Management * @group apps */ abstract class PhabricatorApplication { + const GROUP_CORE = 'core'; + const GROUP_COMMUNICATION = 'communication'; + const GROUP_ORGANIZATION = 'organization'; + const GROUP_UTILITIES = 'util'; + const GROUP_ADMIN = 'admin'; + const GROUP_DEVELOPER = 'developer'; + const GROUP_MISC = 'misc'; + + public static function getApplicationGroups() { + return array( + self::GROUP_CORE => pht('Core Applications'), + self::GROUP_COMMUNICATION => pht('Communication'), + self::GROUP_ORGANIZATION => pht('Organization'), + self::GROUP_UTILITIES => pht('Utilities'), + self::GROUP_ADMIN => pht('Administration'), + self::GROUP_DEVELOPER => pht('Developer Tools'), + self::GROUP_MISC => pht('Miscellaneous Applications'), + ); + } + /* -( Application Information )-------------------------------------------- */ public function getName() { return substr(get_class($this), strlen('PhabricatorApplication')); } public function getShortDescription() { return $this->getName().' Application'; } public function isEnabled() { return true; } public function getPHID() { return 'PHID-APPS-'.get_class($this); } public function getTypeaheadURI() { return $this->getBaseURI(); } public function getBaseURI() { return null; } public function getIconURI() { return null; } public function getAutospriteName() { return 'default'; } public function shouldAppearInLaunchView() { return true; } - public function getCoreApplicationOrder() { - return null; + public function getApplicationOrder() { + return PHP_INT_MAX; + } + + public function getApplicationGroup() { + return self::GROUP_MISC; } public function getTitleGlyph() { return null; } public function getHelpURI() { // TODO: When these applications get created, link to their docs: // // - Drydock // - OAuth Server return null; } public function getEventListeners() { return array(); } /* -( URI Routing )-------------------------------------------------------- */ public function getRoutes() { return array(); } /* -( Fact Integration )--------------------------------------------------- */ public function getFactObjectsForAnalysis() { return array(); } /* -( UI Integration )----------------------------------------------------- */ /** * Render status elements (like "3 Waiting Reviews") for application list * views. These provide a way to alert users to new or pending action items * in applications. * * @param PhabricatorUser Viewing user. * @return list<PhabricatorApplicationStatusView> Application status elements. * @task ui */ public function loadStatus(PhabricatorUser $user) { return array(); } /** * You can provide an optional piece of flavor text for the application. This * is currently rendered in application launch views if the application has no * status elements. * * @return string|null Flavor text. * @task ui */ public function getFlavorText() { return null; } /** * Build items for the main menu. * * @param PhabricatorUser The viewing user. * @param AphrontController The current controller. May be null for special * pages like 404, exception handlers, etc. * @return list<PhabricatorMainMenuIconView> List of menu items. * @task ui */ public function buildMainMenuItems( PhabricatorUser $user, PhabricatorController $controller = null) { return array(); } /* -( Application Management )--------------------------------------------- */ public static function getAllInstalledApplications() { static $applications; if (empty($applications)) { $classes = id(new PhutilSymbolLoader()) ->setAncestorClass(__CLASS__) ->setConcreteOnly(true) ->selectAndLoadSymbols(); $apps = array(); foreach ($classes as $class) { $app = newv($class['name'], array()); if (!$app->isEnabled()) { continue; } $apps[] = $app; } $applications = $apps; } return $applications; } } diff --git a/src/applications/conduit/application/PhabricatorApplicationConduit.php b/src/applications/conduit/application/PhabricatorApplicationConduit.php index e89f25cdd..3c393fdcd 100644 --- a/src/applications/conduit/application/PhabricatorApplicationConduit.php +++ b/src/applications/conduit/application/PhabricatorApplicationConduit.php @@ -1,55 +1,63 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationConduit extends PhabricatorApplication { public function getBaseURI() { return '/conduit/'; } public function getAutospriteName() { return 'conduit'; } public function getHelpURI() { return PhabricatorEnv::getDoclink( 'article/Conduit_Technical_Documentation.html'); } public function getShortDescription() { return 'Conduit API Console'; } public function getTitleGlyph() { return "\xE2\x87\xB5"; } + public function getApplicationGroup() { + return self::GROUP_DEVELOPER; + } + + public function getApplicationOrder() { + return 0.100; + } + public function getRoutes() { return array( '/conduit/' => array( '' => 'PhabricatorConduitListController', 'method/(?P<method>[^/]+)/' => 'PhabricatorConduitConsoleController', 'log/' => 'PhabricatorConduitLogController', 'log/view/(?P<view>[^/]+)/' => 'PhabricatorConduitLogController', 'token/' => 'PhabricatorConduitTokenController', ), '/api/(?P<method>[^/]+)' => 'PhabricatorConduitAPIController', ); } } diff --git a/src/applications/countdown/application/PhabricatorApplicationCountdown.php b/src/applications/countdown/application/PhabricatorApplicationCountdown.php index 255a02e20..f7e986808 100644 --- a/src/applications/countdown/application/PhabricatorApplicationCountdown.php +++ b/src/applications/countdown/application/PhabricatorApplicationCountdown.php @@ -1,56 +1,60 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationCountdown extends PhabricatorApplication { public function getBaseURI() { return '/countdown/'; } public function getAutospriteName() { return 'countdown'; } public function getShortDescription() { return 'Countdown Timers'; } public function getTitleGlyph() { return "\xE2\x9A\xB2"; } public function getFlavorText() { return pht('Utilize the full capabilities of your ALU.'); } + public function getApplicationGroup() { + return self::GROUP_UTILITIES; + } + public function getRoutes() { return array( '/countdown/' => array( '' => 'PhabricatorCountdownListController', '(?P<id>\d+)/' => 'PhabricatorCountdownViewController', 'edit/(?:(?P<id>\d+)/)?' => 'PhabricatorCountdownEditController', 'delete/(?P<id>\d+)/' => 'PhabricatorCountdownDeleteController' ), ); } } diff --git a/src/applications/daemon/application/PhabricatorApplicationDaemons.php b/src/applications/daemon/application/PhabricatorApplicationDaemons.php index c2209a4ab..841afe146 100644 --- a/src/applications/daemon/application/PhabricatorApplicationDaemons.php +++ b/src/applications/daemon/application/PhabricatorApplicationDaemons.php @@ -1,59 +1,63 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationDaemons extends PhabricatorApplication { public function getName() { return 'Daemon Console'; } public function getShortDescription() { return 'Manage Daemons'; } public function getBaseURI() { return '/daemon/'; } public function getTitleGlyph() { return "\xE2\x98\xAF"; } public function getAutospriteName() { return 'daemons'; } + public function getApplicationGroup() { + return self::GROUP_ADMIN; + } + public function getRoutes() { return array( '/daemon/' => array( 'task/(?P<id>\d+)/' => 'PhabricatorWorkerTaskDetailController', 'task/(?P<id>\d+)/(?P<action>[^/]+)/' => 'PhabricatorWorkerTaskUpdateController', 'log/' => array( '(?P<running>running/)?' => 'PhabricatorDaemonLogListController', 'combined/' => 'PhabricatorDaemonCombinedLogController', '(?P<id>\d+)/' => 'PhabricatorDaemonLogViewController', ), 'timeline/' => 'PhabricatorDaemonTimelineConsoleController', 'timeline/(?P<id>\d+)/' => 'PhabricatorDaemonTimelineEventController', '' => 'PhabricatorDaemonConsoleController', ), ); } } diff --git a/src/applications/differential/application/PhabricatorApplicationDifferential.php b/src/applications/differential/application/PhabricatorApplicationDifferential.php index 79c6b98a1..b327153aa 100644 --- a/src/applications/differential/application/PhabricatorApplicationDifferential.php +++ b/src/applications/differential/application/PhabricatorApplicationDifferential.php @@ -1,106 +1,110 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationDifferential extends PhabricatorApplication { public function getBaseURI() { return '/differential/'; } public function getShortDescription() { return 'Review Code'; } public function getAutospriteName() { return 'differential'; } public function getFactObjectsForAnalysis() { return array( new DifferentialRevision(), ); } public function getRoutes() { return array( '/D(?P<id>\d+)' => 'DifferentialRevisionViewController', '/differential/' => array( '' => 'DifferentialRevisionListController', 'filter/(?P<filter>\w+)/(?:(?P<username>[\w\.-_]+)/)?' => 'DifferentialRevisionListController', 'stats/(?P<filter>\w+)/' => 'DifferentialRevisionStatsController', 'diff/' => array( '(?P<id>\d+)/' => 'DifferentialDiffViewController', 'create/' => 'DifferentialDiffCreateController', ), 'changeset/' => 'DifferentialChangesetViewController', 'revision/edit/(?:(?P<id>\d+)/)?' => 'DifferentialRevisionEditController', 'comment/' => array( 'preview/(?P<id>\d+)/' => 'DifferentialCommentPreviewController', 'save/' => 'DifferentialCommentSaveController', 'inline/' => array( 'preview/(?P<id>\d+)/' => 'DifferentialInlineCommentPreviewController', 'edit/(?P<id>\d+)/' => 'DifferentialInlineCommentEditController', ), ), 'subscribe/(?P<action>add|rem)/(?P<id>\d+)/' => 'DifferentialSubscribeController', ), ); } - public function getCoreApplicationOrder() { + public function getApplicationGroup() { + return self::GROUP_CORE; + } + + public function getApplicationOrder() { return 0.100; } public function loadStatus(PhabricatorUser $user) { $revisions = id(new DifferentialRevisionQuery()) ->withResponsibleUsers(array($user->getPHID())) ->withStatus(DifferentialRevisionQuery::STATUS_OPEN) ->execute(); list($active, $waiting) = DifferentialRevisionQuery::splitResponsible( $revisions, $user->getPHID()); $status = array(); $active = count($active); $type = $active ? PhabricatorApplicationStatusView::TYPE_NEEDS_ATTENTION : PhabricatorApplicationStatusView::TYPE_EMPTY; $status[] = id(new PhabricatorApplicationStatusView()) ->setType($type) ->setText(pht('%d Review(s) Need Attention', $active)) ->setCount($active); $waiting = count($waiting); $type = $waiting ? PhabricatorApplicationStatusView::TYPE_INFO : PhabricatorApplicationStatusView::TYPE_EMPTY; $status[] = id(new PhabricatorApplicationStatusView()) ->setType($type) ->setText(pht('%d Review(s) Waiting on Others', $waiting)); return $status; } } diff --git a/src/applications/diffusion/application/PhabricatorApplicationDiffusion.php b/src/applications/diffusion/application/PhabricatorApplicationDiffusion.php index 0051166bf..d5ae8c24e 100644 --- a/src/applications/diffusion/application/PhabricatorApplicationDiffusion.php +++ b/src/applications/diffusion/application/PhabricatorApplicationDiffusion.php @@ -1,90 +1,94 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationDiffusion extends PhabricatorApplication { public function getShortDescription() { return 'Repository Browser'; } public function getBaseURI() { return '/diffusion/'; } public function getAutospriteName() { return 'diffusion'; } public function getHelpURI() { return PhabricatorEnv::getDoclink('article/Diffusion_User_Guide.html'); } public function getFactObjectsForAnalysis() { return array( new PhabricatorRepositoryCommit(), ); } public function getRoutes() { return array( '/r(?P<callsign>[A-Z]+)(?P<commit>[a-z0-9]+)' => 'DiffusionCommitController', '/diffusion/' => array( '' => 'DiffusionHomeController', '(?P<callsign>[A-Z]+)/' => array( '' => 'DiffusionRepositoryController', 'repository/(?P<dblob>.*)' => 'DiffusionRepositoryController', 'change/(?P<dblob>.*)' => 'DiffusionChangeController', 'history/(?P<dblob>.*)' => 'DiffusionHistoryController', 'browse/(?P<dblob>.*)' => 'DiffusionBrowseController', 'lastmodified/(?P<dblob>.*)' => 'DiffusionLastModifiedController', 'diff/' => 'DiffusionDiffController', 'tags/(?P<dblob>.*)' => 'DiffusionTagListController', 'branches/(?P<dblob>.*)' => 'DiffusionBranchTableController', 'commit/(?P<commit>[a-z0-9]+)/branches/' => 'DiffusionCommitBranchesController', 'commit/(?P<commit>[a-z0-9]+)/tags/' => 'DiffusionCommitTagsController', 'commit/(?P<commit>[a-z0-9]+)/edit/' => 'DiffusionCommitEditController', ), 'inline/' => array( 'edit/(?P<phid>[^/]+)/' => 'DiffusionInlineCommentController', 'preview/(?P<phid>[^/]+)/' => 'DiffusionInlineCommentPreviewController', ), 'services/' => array( 'path/' => array( 'complete/' => 'DiffusionPathCompleteController', 'validate/' => 'DiffusionPathValidateController', ), ), 'symbol/(?P<name>[^/]+)/' => 'DiffusionSymbolController', 'external/' => 'DiffusionExternalController', ), ); } - public function getCoreApplicationOrder() { + public function getApplicationGroup() { + return self::GROUP_CORE; + } + + public function getApplicationOrder() { return 0.120; } } diff --git a/src/applications/diviner/application/PhabricatorApplicationDiviner.php b/src/applications/diviner/application/PhabricatorApplicationDiviner.php index a8c786cc1..a15ad514a 100644 --- a/src/applications/diviner/application/PhabricatorApplicationDiviner.php +++ b/src/applications/diviner/application/PhabricatorApplicationDiviner.php @@ -1,69 +1,73 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationDiviner extends PhabricatorApplication { public function getBaseURI() { return '/diviner/'; } public function getAutospriteName() { return 'diviner'; } public function getShortDescription() { return 'Documentation'; } public function getTitleGlyph() { return "\xE2\x97\x89"; } public function getRoutes() { return array( '/diviner/' => 'DivinerListController', ); } + public function getApplicationGroup() { + return self::GROUP_COMMUNICATION; + } + public function buildMainMenuItems( PhabricatorUser $user, PhabricatorController $controller = null) { $items = array(); $application = null; if ($controller) { $application = $controller->getCurrentApplication(); } if ($application && $application->getHelpURI()) { $class = 'main-menu-item-icon-help'; $item = new PhabricatorMainMenuIconView(); $item->setName(pht('%s Help', $application->getName())); $item->addClass('autosprite main-menu-item-icon '.$class); $item->setHref($application->getHelpURI()); $item->setSortOrder(0.1); $items[] = $item; } return $items; } } diff --git a/src/applications/fact/application/PhabricatorApplicationFact.php b/src/applications/fact/application/PhabricatorApplicationFact.php index d39c2580a..4f2fb42ea 100644 --- a/src/applications/fact/application/PhabricatorApplicationFact.php +++ b/src/applications/fact/application/PhabricatorApplicationFact.php @@ -1,42 +1,46 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationFact extends PhabricatorApplication { public function getShortDescription() { return 'Analyze Data'; } public function getBaseURI() { return '/fact/'; } public function getAutospriteName() { return 'fact'; } + public function getApplicationGroup() { + return self::GROUP_UTILITIES; + } + public function getRoutes() { return array( '/fact/' => array( '' => 'PhabricatorFactHomeController', 'chart/' => 'PhabricatorFactChartController', ), ); } } diff --git a/src/applications/files/application/PhabricatorApplicationFiles.php b/src/applications/files/application/PhabricatorApplicationFiles.php index 7ab3ae6a5..77e3fdbff 100644 --- a/src/applications/files/application/PhabricatorApplicationFiles.php +++ b/src/applications/files/application/PhabricatorApplicationFiles.php @@ -1,60 +1,64 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationFiles extends PhabricatorApplication { public function getBaseURI() { return '/file/'; } public function getShortDescription() { return 'Store and Share Files'; } public function getAutospriteName() { return 'files'; } public function getTitleGlyph() { return "\xE2\x87\xAA"; } public function getFlavorText() { return pht('Blob store for Pokemon pictures.'); } + public function getApplicationGroup() { + return self::GROUP_UTILITIES; + } + public function getRoutes() { return array( '/F(?P<id>\d+)' => 'PhabricatorFileShortcutController', '/file/' => array( '' => 'PhabricatorFileListController', 'filter/(?P<filter>\w+)/' => 'PhabricatorFileListController', 'upload/' => 'PhabricatorFileUploadController', 'dropupload/' => 'PhabricatorFileDropUploadController', 'delete/(?P<id>\d+)/' => 'PhabricatorFileDeleteController', 'info/(?P<phid>[^/]+)/' => 'PhabricatorFileInfoController', 'data/(?P<key>[^/]+)/(?P<phid>[^/]+)/.*' => 'PhabricatorFileDataController', 'proxy/' => 'PhabricatorFileProxyController', 'xform/(?P<transform>[^/]+)/(?P<phid>[^/]+)/' => 'PhabricatorFileTransformController', ), ); } } diff --git a/src/applications/flag/application/PhabricatorApplicationFlags.php b/src/applications/flag/application/PhabricatorApplicationFlags.php index e6721ec52..63471a62f 100644 --- a/src/applications/flag/application/PhabricatorApplicationFlags.php +++ b/src/applications/flag/application/PhabricatorApplicationFlags.php @@ -1,70 +1,74 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationFlags extends PhabricatorApplication { public function getShortDescription() { return 'Reminders'; } public function getBaseURI() { return '/flag/'; } public function getAutospriteName() { return 'flags'; } public function getEventListeners() { return array( new PhabricatorFlagsUIEventListener(), ); } + public function getApplicationGroup() { + return self::GROUP_ORGANIZATION; + } + public function loadStatus(PhabricatorUser $user) { $status = array(); $flags = id(new PhabricatorFlagQuery()) ->withOwnerPHIDs(array($user->getPHID())) ->execute(); $count = count($flags); $type = $count ? PhabricatorApplicationStatusView::TYPE_INFO : PhabricatorApplicationStatusView::TYPE_EMPTY; $status[] = id(new PhabricatorApplicationStatusView()) ->setType($type) ->setText(pht('%d Flagged Object(s)', $count)) ->setCount($count); return $status; } public function getRoutes() { return array( '/flag/' => array( '' => 'PhabricatorFlagListController', 'view/(?P<view>[^/]+)/' => 'PhabricatorFlagListController', 'edit/(?P<phid>[^/]+)/' => 'PhabricatorFlagEditController', 'delete/(?P<id>\d+)/' => 'PhabricatorFlagDeleteController', ), ); } } diff --git a/src/applications/herald/application/PhabricatorApplicationHerald.php b/src/applications/herald/application/PhabricatorApplicationHerald.php index 943ae9ca0..41dea836f 100644 --- a/src/applications/herald/application/PhabricatorApplicationHerald.php +++ b/src/applications/herald/application/PhabricatorApplicationHerald.php @@ -1,64 +1,68 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationHerald extends PhabricatorApplication { public function getBaseURI() { return '/herald/'; } public function getAutospriteName() { return 'herald'; } public function getShortDescription() { return 'Create Notification Rules'; } public function getTitleGlyph() { return "\xE2\x98\xBF"; } public function getHelpURI() { return PhabricatorEnv::getDoclink('article/Herald_User_Guide.html'); } public function getFlavorText() { return pht('Watch for danger!'); } + public function getApplicationGroup() { + return self::GROUP_ORGANIZATION; + } + public function getRoutes() { return array( '/herald/' => array( '' => 'HeraldHomeController', 'view/(?P<content_type>[^/]+)/(?:(?P<rule_type>[^/]+)/)?' => 'HeraldHomeController', 'new/(?:(?P<type>[^/]+)/(?:(?P<rule_type>[^/]+)/)?)?' => 'HeraldNewController', 'rule/(?:(?P<id>\d+)/)?' => 'HeraldRuleController', 'history/(?:(?P<id>\d+)/)?' => 'HeraldRuleEditHistoryController', 'delete/(?P<id>\d+)/' => 'HeraldDeleteController', 'test/' => 'HeraldTestConsoleController', 'transcript/' => 'HeraldTranscriptListController', 'transcript/(?P<id>\d+)/(?:(?P<filter>\w+)/)?' => 'HeraldTranscriptController', ), ); } } diff --git a/src/applications/macro/application/PhabricatorApplicationMacro.php b/src/applications/macro/application/PhabricatorApplicationMacro.php index 74f7506a3..343ac047d 100644 --- a/src/applications/macro/application/PhabricatorApplicationMacro.php +++ b/src/applications/macro/application/PhabricatorApplicationMacro.php @@ -1,47 +1,51 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationMacro extends PhabricatorApplication { public function getBaseURI() { return '/macro/'; } public function getShortDescription() { return 'Image Macros and Memes'; } public function getAutospriteName() { return 'macro'; } public function getTitleGlyph() { return "\xE2\x9A\x98"; } + public function getApplicationGroup() { + return self::GROUP_UTILITIES; + } + public function getRoutes() { return array( '/macro/' => array( '' => 'PhabricatorMacroListController', 'edit/(?:(?P<id>\d+)/)?' => 'PhabricatorMacroEditController', 'delete/(?P<id>\d+)/' => 'PhabricatorMacroDeleteController', ), ); } } diff --git a/src/applications/mailinglists/application/PhabricatorApplicationMailingLists.php b/src/applications/mailinglists/application/PhabricatorApplicationMailingLists.php index 17dda9563..129e5fdea 100644 --- a/src/applications/mailinglists/application/PhabricatorApplicationMailingLists.php +++ b/src/applications/mailinglists/application/PhabricatorApplicationMailingLists.php @@ -1,50 +1,54 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationMailingLists extends PhabricatorApplication { public function getName() { return 'Mailing Lists'; } public function getBaseURI() { return '/mailinglists/'; } public function getShortDescription() { return 'Manage External Lists'; } public function getAutospriteName() { return 'mail'; } + public function getApplicationGroup() { + return self::GROUP_ADMIN; + } + public function getRoutes() { return array( '/mailinglists/' => array( '' => 'PhabricatorMailingListsListController', 'edit/(?:(?P<id>\d+)/)?' => 'PhabricatorMailingListsEditController', ), ); } public function getTitleGlyph() { return '@'; } } diff --git a/src/applications/maniphest/application/PhabricatorApplicationManiphest.php b/src/applications/maniphest/application/PhabricatorApplicationManiphest.php index 983125340..c225044ce 100644 --- a/src/applications/maniphest/application/PhabricatorApplicationManiphest.php +++ b/src/applications/maniphest/application/PhabricatorApplicationManiphest.php @@ -1,116 +1,120 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationManiphest extends PhabricatorApplication { public function getShortDescription() { return 'Tasks and Bugs'; } public function getBaseURI() { return '/maniphest/'; } public function isEnabled() { return PhabricatorEnv::getEnvConfig('maniphest.enabled'); } public function getAutospriteName() { return 'maniphest'; } - public function getCoreApplicationOrder() { + public function getApplicationGroup() { + return self::GROUP_CORE; + } + + public function getApplicationOrder() { return 0.110; } public function getFactObjectsForAnalysis() { return array( new ManiphestTask(), ); } public function getRoutes() { return array( '/T(?P<id>\d+)' => 'ManiphestTaskDetailController', '/maniphest/' => array( '' => 'ManiphestTaskListController', 'view/(?P<view>\w+)/' => 'ManiphestTaskListController', 'report/(?:(?P<view>\w+)/)?' => 'ManiphestReportController', 'batch/' => 'ManiphestBatchEditController', 'task/' => array( 'create/' => 'ManiphestTaskEditController', 'edit/(?P<id>\d+)/' => 'ManiphestTaskEditController', 'descriptionchange/(?:(?P<id>\d+)/)?' => 'ManiphestTaskDescriptionChangeController', 'descriptionpreview/' => 'ManiphestTaskDescriptionPreviewController', ), 'transaction/' => array( 'save/' => 'ManiphestTransactionSaveController', 'preview/(?P<id>\d+)/' => 'ManiphestTransactionPreviewController', ), 'export/(?P<key>[^/]+)/' => 'ManiphestExportController', 'subpriority/' => 'ManiphestSubpriorityController', 'custom/' => array( '' => 'ManiphestSavedQueryListController', 'edit/(?:(?P<id>\d+)/)?' => 'ManiphestSavedQueryEditController', 'delete/(?P<id>\d+)/' => 'ManiphestSavedQueryDeleteController', ), ), ); } public function loadStatus(PhabricatorUser $user) { $status = array(); $query = id(new ManiphestTaskQuery()) ->withStatus(ManiphestTaskQuery::STATUS_OPEN) ->withPriority(ManiphestTaskPriority::PRIORITY_UNBREAK_NOW) ->setLimit(1) ->setCalculateRows(true); $query->execute(); $count = $query->getRowCount(); $type = $count ? PhabricatorApplicationStatusView::TYPE_NEEDS_ATTENTION : PhabricatorApplicationStatusView::TYPE_EMPTY; $status[] = id(new PhabricatorApplicationStatusView()) ->setType($type) ->setText(pht('%d Unbreak Now Task(s)!', $count)) ->setCount($count); $query = id(new ManiphestTaskQuery()) ->withStatus(ManiphestTaskQuery::STATUS_OPEN) ->withOwners(array($user->getPHID())) ->setLimit(1) ->setCalculateRows(true); $query->execute(); $count = $query->getRowCount(); $type = $count ? PhabricatorApplicationStatusView::TYPE_INFO : PhabricatorApplicationStatusView::TYPE_EMPTY; $status[] = id(new PhabricatorApplicationStatusView()) ->setType($type) ->setText(pht('%d Assigned Task(s)', $count)); return $status; } } diff --git a/src/applications/meta/controller/PhabricatorApplicationsListController.php b/src/applications/meta/controller/PhabricatorApplicationsListController.php index 2e1dbb6ff..01fdd8814 100644 --- a/src/applications/meta/controller/PhabricatorApplicationsListController.php +++ b/src/applications/meta/controller/PhabricatorApplicationsListController.php @@ -1,64 +1,75 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationsListController extends PhabricatorController { public function processRequest() { $request = $this->getRequest(); $user = $request->getUser(); $applications = PhabricatorApplication::getAllInstalledApplications(); - $applications = msort($applications, 'getName'); foreach ($applications as $key => $application) { if (!$application->shouldAppearInLaunchView()) { unset($applications[$key]); } } - $status = array(); - foreach ($applications as $key => $application) { - $status[$key] = $application->loadStatus($user); - } + $groups = PhabricatorApplication::getApplicationGroups(); - $views = array(); - foreach ($applications as $key => $application) { - $views[] = id(new PhabricatorApplicationLaunchView()) - ->setApplication($application) - ->setApplicationStatus(idx($status, $key, array())) - ->setUser($user); - } + $applications = msort($applications, 'getApplicationOrder'); + $applications = mgroup($applications, 'getApplicationGroup'); + $applications = array_select_keys($applications, array_keys($groups)); - $view = phutil_render_tag( - 'div', - array( - 'class' => 'phabricator-application-list', - ), - id(new AphrontNullView())->appendChild($views)->render()); + $view = array(); + foreach ($applications as $group => $application_list) { + $status = array(); + foreach ($application_list as $key => $application) { + $status[$key] = $application->loadStatus($user); + } + + $views = array(); + foreach ($application_list as $key => $application) { + $views[] = id(new PhabricatorApplicationLaunchView()) + ->setApplication($application) + ->setApplicationStatus(idx($status, $key, array())) + ->setUser($user); + } + + $view[] = id(new PhabricatorHeaderView()) + ->setHeader($groups[$group]); + + $view[] = phutil_render_tag( + 'div', + array( + 'class' => 'phabricator-application-list', + ), + id(new AphrontNullView())->appendChild($views)->render()); + } return $this->buildApplicationPage( $view, array( 'title' => 'Applications', 'device' => true, )); } } diff --git a/src/applications/metamta/application/PhabricatorApplicationMetaMTA.php b/src/applications/metamta/application/PhabricatorApplicationMetaMTA.php index f45640144..130a5f89e 100644 --- a/src/applications/metamta/application/PhabricatorApplicationMetaMTA.php +++ b/src/applications/metamta/application/PhabricatorApplicationMetaMTA.php @@ -1,54 +1,58 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationMetaMTA extends PhabricatorApplication { public function getBaseURI() { return '/mail/'; } public function getShortDescription() { return 'View Mail Logs'; } public function getAutospriteName() { return 'mail'; } public function getFlavorText() { return pht('Yo dawg, we heard you like MTAs.'); } + public function getApplicationGroup() { + return self::GROUP_ADMIN; + } + public function getRoutes() { return array( $this->getBaseURI() => array( '' => 'PhabricatorMetaMTAListController', 'send/' => 'PhabricatorMetaMTASendController', 'view/(?P<id>\d+)/' => 'PhabricatorMetaMTAViewController', 'receive/' => 'PhabricatorMetaMTAReceiveController', 'received/' => 'PhabricatorMetaMTAReceivedListController', 'sendgrid/' => 'PhabricatorMetaMTASendGridReceiveController', ), ); } public function getTitleGlyph() { return '@'; } } diff --git a/src/applications/owners/application/PhabricatorApplicationOwners.php b/src/applications/owners/application/PhabricatorApplicationOwners.php index 5659c862a..bf4a40ce7 100644 --- a/src/applications/owners/application/PhabricatorApplicationOwners.php +++ b/src/applications/owners/application/PhabricatorApplicationOwners.php @@ -1,58 +1,62 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationOwners extends PhabricatorApplication { public function getBaseURI() { return '/owners/'; } public function getAutospriteName() { return 'owners'; } public function getShortDescription() { return 'Group Source Code'; } public function getTitleGlyph() { return "\xE2\x98\x81"; } public function getHelpURI() { return PhabricatorEnv::getDoclink('article/Owners_Tool_User_Guide.html'); } public function getFlavorText() { return pht('Adopt today!'); } + public function getApplicationGroup() { + return self::GROUP_ORGANIZATION; + } + public function getRoutes() { return array( '/owners/' => array( '' => 'PhabricatorOwnersListController', 'view/(?P<view>[^/]+)/' => 'PhabricatorOwnersListController', 'edit/(?P<id>\d+)/' => 'PhabricatorOwnersEditController', 'new/' => 'PhabricatorOwnersEditController', 'package/(?P<id>\d+)/' => 'PhabricatorOwnersDetailController', 'delete/(?P<id>\d+)/' => 'PhabricatorOwnersDeleteController', ), ); } } diff --git a/src/applications/paste/application/PhabricatorApplicationPaste.php b/src/applications/paste/application/PhabricatorApplicationPaste.php index 0ca94dd5c..655d78608 100644 --- a/src/applications/paste/application/PhabricatorApplicationPaste.php +++ b/src/applications/paste/application/PhabricatorApplicationPaste.php @@ -1,44 +1,48 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationPaste extends PhabricatorApplication { public function getBaseURI() { return '/paste/'; } public function getAutospriteName() { return 'paste'; } public function getTitleGlyph() { return "\xE2\x9C\x8E"; } + public function getApplicationGroup() { + return self::GROUP_UTILITIES; + } + public function getRoutes() { return array( '/P(?P<id>\d+)' => 'PhabricatorPasteViewController', '/paste/' => array( '' => 'PhabricatorPasteEditController', 'edit/(?P<id>\d+)/' => 'PhabricatorPasteEditController', 'filter/(?P<filter>\w+)/' => 'PhabricatorPasteListController', ), ); } } diff --git a/src/applications/people/application/PhabricatorApplicationPeople.php b/src/applications/people/application/PhabricatorApplicationPeople.php index 40eda3ec2..91facadc3 100644 --- a/src/applications/people/application/PhabricatorApplicationPeople.php +++ b/src/applications/people/application/PhabricatorApplicationPeople.php @@ -1,86 +1,90 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationPeople extends PhabricatorApplication { public function getShortDescription() { return 'User Accounts'; } public function getBaseURI() { return '/people/'; } public function getTitleGlyph() { return "\xE2\x99\x9F"; } public function getAutospriteName() { return 'people'; } public function getFlavorText() { return pht('Sort of a social utility.'); } + public function getApplicationGroup() { + return self::GROUP_ADMIN; + } + public function getRoutes() { return array( '/people/' => array( '' => 'PhabricatorPeopleListController', 'logs/' => 'PhabricatorPeopleLogsController', 'edit/(?:(?P<id>\d+)/(?:(?P<view>\w+)/)?)?' => 'PhabricatorPeopleEditController', 'ldap/' => 'PhabricatorPeopleLdapController', ), '/p/(?P<username>[\w._-]+)/(?:(?P<page>\w+)/)?' => 'PhabricatorPeopleProfileController', '/emailverify/(?P<code>[^/]+)/' => 'PhabricatorEmailVerificationController', ); } public function buildMainMenuItems( PhabricatorUser $user, PhabricatorController $controller = null) { $items = array(); if (($controller instanceof PhabricatorPeopleProfileController) && ($controller->getProfileUser()) && ($controller->getProfileUser()->getPHID() == $user->getPHID())) { $class = 'main-menu-item-icon-profile-selected'; } else { $class = 'main-menu-item-icon-profile-not-selected'; } if ($user->isLoggedIn()) { $image = $user->loadProfileImageURI(); $item = new PhabricatorMainMenuIconView(); $item->setName($user->getUsername()); $item->addClass('main-menu-item-icon-profile '.$class); $item->addStyle('background-image: url('.$image.')'); $item->setHref('/p/'.$user->getUsername().'/'); $item->setSortOrder(0.0); $items[] = $item; } return $items; } } diff --git a/src/applications/phame/application/PhabricatorApplicationPhame.php b/src/applications/phame/application/PhabricatorApplicationPhame.php index e05e95148..5038c1cd9 100644 --- a/src/applications/phame/application/PhabricatorApplicationPhame.php +++ b/src/applications/phame/application/PhabricatorApplicationPhame.php @@ -1,74 +1,78 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationPhame extends PhabricatorApplication { public function getBaseURI() { return '/phame/'; } public function getAutospriteName() { return 'phame'; } public function getShortDescription() { return 'Blog'; } public function getTitleGlyph() { return "\xe2\x9c\xa9"; } public function getHelpURI() { return PhabricatorEnv::getDoclink('article/Phame_User_Guide.html'); } + public function getApplicationGroup() { + return self::GROUP_COMMUNICATION; + } + public function getRoutes() { return array( '/phame/' => array( '' => 'PhameAllPostListController', 'post/' => array( '' => 'PhameUserPostListController', 'delete/(?P<phid>[^/]+)/' => 'PhamePostDeleteController', 'edit/(?P<phid>[^/]+)/' => 'PhamePostEditController', 'new/' => 'PhamePostEditController', 'preview/' => 'PhamePostPreviewController', 'view/(?P<phid>[^/]+)/' => 'PhamePostViewController', ), 'draft/' => array( '' => 'PhameDraftListController', 'new/' => 'PhamePostEditController', ), 'blog/' => array( '' => 'PhameUserBlogListController', 'all/' => 'PhameAllBlogListController', 'new/' => 'PhameBlogEditController', 'delete/(?P<phid>[^/]+)/' => 'PhameBlogDeleteController', 'edit/(?P<phid>[^/]+)/' => 'PhameBlogEditController', 'view/(?P<phid>[^/]+)/' => 'PhameBlogViewController', ), 'posts/' => array( '' => 'PhameUserPostListController', '(?P<bloggername>\w+)/' => 'PhameBloggerPostListController', '(?P<bloggername>\w+)/(?P<phametitle>.+/)' => 'PhamePostViewController', ), ), ); } } diff --git a/src/applications/phid/application/PhabricatorApplicationPHID.php b/src/applications/phid/application/PhabricatorApplicationPHID.php index 8c41c701d..5da3a8dd5 100644 --- a/src/applications/phid/application/PhabricatorApplicationPHID.php +++ b/src/applications/phid/application/PhabricatorApplicationPHID.php @@ -1,49 +1,53 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationPHID extends PhabricatorApplication { public function getName() { return 'PHID Manager'; } public function getBaseURI() { return '/phid/'; } public function getAutospriteName() { return 'phid'; } public function getShortDescription() { return 'Lookup PHIDs'; } public function getTitleGlyph() { return "#"; } + public function getApplicationGroup() { + return self::GROUP_DEVELOPER; + } + public function getRoutes() { return array( '/phid/' => array( '' => 'PhabricatorPHIDLookupController', ), ); } } diff --git a/src/applications/phriction/application/PhabricatorApplicationPhriction.php b/src/applications/phriction/application/PhabricatorApplicationPhriction.php index 2a9b42380..7bfe8febd 100644 --- a/src/applications/phriction/application/PhabricatorApplicationPhriction.php +++ b/src/applications/phriction/application/PhabricatorApplicationPhriction.php @@ -1,65 +1,69 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationPhriction extends PhabricatorApplication { public function getShortDescription() { return 'Wiki'; } public function getBaseURI() { return '/w/'; } public function getAutospriteName() { return 'phriction'; } public function getHelpURI() { return PhabricatorEnv::getDoclink('article/Phriction_User_Guide.html'); } public function getRoutes() { return array( // Match "/w/" with slug "/". '/w(?P<slug>/)' => 'PhrictionDocumentController', // Match "/w/x/y/z/" with slug "x/y/z/". '/w/(?P<slug>.+/)' => 'PhrictionDocumentController', '/phriction/' => array( '' => 'PhrictionListController', 'list/(?P<view>[^/]+)/' => 'PhrictionListController', 'history(?P<slug>/)' => 'PhrictionHistoryController', 'history/(?P<slug>.+/)' => 'PhrictionHistoryController', 'edit/(?:(?P<id>\d+)/)?' => 'PhrictionEditController', 'delete/(?P<id>\d+)/' => 'PhrictionDeleteController', 'preview/' => 'PhrictionDocumentPreviewController', 'diff/(?P<id>\d+)/' => 'PhrictionDiffController', ), ); } - public function getCoreApplicationOrder() { + public function getApplicationGroup() { + return self::GROUP_COMMUNICATION; + } + + public function getApplicationOrder() { return 0.140; } } diff --git a/src/applications/ponder/application/PhabricatorApplicationPonder.php b/src/applications/ponder/application/PhabricatorApplicationPonder.php index d04d2748b..16e64059a 100644 --- a/src/applications/ponder/application/PhabricatorApplicationPonder.php +++ b/src/applications/ponder/application/PhabricatorApplicationPonder.php @@ -1,63 +1,67 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationPonder extends PhabricatorApplication { public function getBaseURI() { return '/ponder/'; } public function getShortDescription() { return 'Find Answers'; } public function getAutospriteName() { return 'ponder'; } public function getFactObjectsForAnalysis() { return array( new PonderQuestion(), ); } public function loadStatus(PhabricatorUser $user) { // replace with "x new unanswered questions" or some such $status = array(); return $status; } + public function getApplicationGroup() { + return self::GROUP_COMMUNICATION; + } + public function getroutes() { return array( '/Q(?P<id>\d+)' => 'PonderQuestionViewController', '/ponder/' => array( '(?P<page>feed/)?' => 'PonderFeedController', '(?P<page>questions)/' => 'PonderFeedController', '(?P<page>answers)/' => 'PonderFeedController', 'answer/add/' => 'PonderAnswerSaveController', 'answer/preview/' => 'PonderAnswerPreviewController', 'question/ask/' => 'PonderQuestionAskController', 'question/preview/' => 'PonderQuestionPreviewController', 'comment/add/' => 'PonderCommentSaveController', '(?P<kind>question)/vote/' => 'PonderVoteSaveController', '(?P<kind>answer)/vote/' => 'PonderVoteSaveController' )); } } diff --git a/src/applications/project/application/PhabricatorApplicationProject.php b/src/applications/project/application/PhabricatorApplicationProject.php index bba25821d..49594817d 100644 --- a/src/applications/project/application/PhabricatorApplicationProject.php +++ b/src/applications/project/application/PhabricatorApplicationProject.php @@ -1,57 +1,61 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationProject extends PhabricatorApplication { public function getName() { return 'Projects'; } public function getShortDescription() { return 'Organize Work'; } public function getBaseURI() { return '/project/'; } public function getAutospriteName() { return 'projects'; } public function getFlavorText() { return pht('Group stuff into big piles.'); } + public function getApplicationGroup() { + return self::GROUP_ORGANIZATION; + } + public function getRoutes() { return array( '/project/' => array( '' => 'PhabricatorProjectListController', 'filter/(?P<filter>[^/]+)/' => 'PhabricatorProjectListController', 'edit/(?P<id>\d+)/' => 'PhabricatorProjectProfileEditController', 'members/(?P<id>\d+)/' => 'PhabricatorProjectMembersEditController', 'view/(?P<id>\d+)/(?:(?P<page>\w+)/)?' => 'PhabricatorProjectProfileController', 'create/' => 'PhabricatorProjectCreateController', 'update/(?P<id>\d+)/(?P<action>[^/]+)/' => 'PhabricatorProjectUpdateController', ), ); } } diff --git a/src/applications/repository/application/PhabricatorApplicationRepositories.php b/src/applications/repository/application/PhabricatorApplicationRepositories.php index 8d8b2fecf..c55760e54 100644 --- a/src/applications/repository/application/PhabricatorApplicationRepositories.php +++ b/src/applications/repository/application/PhabricatorApplicationRepositories.php @@ -1,51 +1,55 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationRepositories extends PhabricatorApplication { public function getBaseURI() { return '/repository/'; } public function getAutospriteName() { return 'repositories'; } public function getShortDescription() { return 'Track Repositories'; } public function getTitleGlyph() { return "rX"; } + public function getApplicationGroup() { + return self::GROUP_ADMIN; + } + public function getRoutes() { return array( '/repository/' => array( '' => 'PhabricatorRepositoryListController', 'create/' => 'PhabricatorRepositoryCreateController', 'edit/(?P<id>\d+)/(?:(?P<view>\w+)?/)?' => 'PhabricatorRepositoryEditController', 'delete/(?P<id>\d+)/' => 'PhabricatorRepositoryDeleteController', 'project/(?P<id>\d+)/' => 'PhabricatorRepositoryArcanistProjectEditController', ), ); } } diff --git a/src/applications/settings/application/PhabricatorApplicationSettings.php b/src/applications/settings/application/PhabricatorApplicationSettings.php index 22dc2a2f0..275845e6d 100644 --- a/src/applications/settings/application/PhabricatorApplicationSettings.php +++ b/src/applications/settings/application/PhabricatorApplicationSettings.php @@ -1,66 +1,70 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationSettings extends PhabricatorApplication { public function getBaseURI() { return '/settings/'; } public function getShortDescription() { return 'User Preferences'; } public function getAutospriteName() { return 'settings'; } public function getRoutes() { return array( '/settings/' => array( '(?:panel/(?P<key>[^/]+)/)?' => 'PhabricatorSettingsMainController', 'adjust/' => 'PhabricatorSettingsAdjustController', ), ); } + public function getApplicationGroup() { + return self::GROUP_UTILITIES; + } + public function buildMainMenuItems( PhabricatorUser $user, PhabricatorController $controller = null) { $items = array(); if ($controller instanceof PhabricatorSettingsMainController) { $class = 'main-menu-item-icon-settings-selected'; } else { $class = 'main-menu-item-icon-settings'; } if ($user->isLoggedIn()) { $item = new PhabricatorMainMenuIconView(); $item->setName(pht('Settings')); $item->addClass('autosprite main-menu-item-icon '.$class); $item->setHref('/settings/'); $item->setSortOrder(0.90); $items[] = $item; } return $items; } } diff --git a/src/applications/slowvote/application/PhabricatorApplicationSlowvote.php b/src/applications/slowvote/application/PhabricatorApplicationSlowvote.php index 7d55e82a6..7424b156a 100644 --- a/src/applications/slowvote/application/PhabricatorApplicationSlowvote.php +++ b/src/applications/slowvote/application/PhabricatorApplicationSlowvote.php @@ -1,55 +1,59 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationSlowvote extends PhabricatorApplication { public function getBaseURI() { return '/vote/'; } public function getAutospriteName() { return 'slowvote'; } public function getShortDescription() { return 'Conduct Polls'; } public function getTitleGlyph() { return "\xE2\x9C\x94"; } public function getHelpURI() { return PhabricatorEnv::getDoclink('article/Slowvote_User_Guide.html'); } public function getFlavorText() { return pht('Design by committee.'); } + public function getApplicationGroup() { + return self::GROUP_UTILITIES; + } + public function getRoutes() { return array( '/V(?P<id>\d+)' => 'PhabricatorSlowvotePollController', '/vote/' => array( '(?:view/(?P<view>\w+)/)?' => 'PhabricatorSlowvoteListController', 'create/' => 'PhabricatorSlowvoteCreateController', ), ); } } diff --git a/src/applications/uiexample/application/PhabricatorApplicationUIExamples.php b/src/applications/uiexample/application/PhabricatorApplicationUIExamples.php index 7b89a8904..a0c899f4a 100644 --- a/src/applications/uiexample/application/PhabricatorApplicationUIExamples.php +++ b/src/applications/uiexample/application/PhabricatorApplicationUIExamples.php @@ -1,50 +1,58 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationUIExamples extends PhabricatorApplication { public function getBaseURI() { return '/uiexample/'; } public function getShortDescription() { return 'Developer UI Examples'; } public function getAutospriteName() { return 'uiexample'; } public function getTitleGlyph() { return "\xE2\x8F\x9A"; } public function getFlavorText() { return pht('A gallery of modern art.'); } + public function getApplicationGroup() { + return self::GROUP_DEVELOPER; + } + + public function getApplicationOrder() { + return 0.110; + } + public function getRoutes() { return array( '/uiexample/' => array( '' => 'PhabricatorUIExampleRenderController', 'view/(?P<class>[^/]+)/' => 'PhabricatorUIExampleRenderController', ), ); } } diff --git a/src/applications/xhpastview/application/PhabricatorApplicationPHPAST.php b/src/applications/xhpastview/application/PhabricatorApplicationPHPAST.php index 16b0e763d..4e8bd1c92 100644 --- a/src/applications/xhpastview/application/PhabricatorApplicationPHPAST.php +++ b/src/applications/xhpastview/application/PhabricatorApplicationPHPAST.php @@ -1,55 +1,59 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class PhabricatorApplicationPHPAST extends PhabricatorApplication { public function getBaseURI() { return '/xhpast/'; } public function getAutospriteName() { return 'phpast'; } public function getShortDescription() { return 'Visual PHP Parser'; } public function getTitleGlyph() { return "\xE2\x96\xA0"; } + public function getApplicationGroup() { + return self::GROUP_DEVELOPER; + } + public function getRoutes() { return array( '/xhpast/' => array( '' => 'PhabricatorXHPASTViewRunController', 'view/(?P<id>\d+)/' => 'PhabricatorXHPASTViewFrameController', 'frameset/(?P<id>\d+)/' => 'PhabricatorXHPASTViewFramesetController', 'input/(?P<id>\d+)/' => 'PhabricatorXHPASTViewInputController', 'tree/(?P<id>\d+)/' => 'PhabricatorXHPASTViewTreeController', 'stream/(?P<id>\d+)/' => 'PhabricatorXHPASTViewStreamController', ), ); } } diff --git a/src/view/layout/AphrontSideNavView.php b/src/view/layout/AphrontSideNavView.php index 6e032a1bd..f7f16ffed 100644 --- a/src/view/layout/AphrontSideNavView.php +++ b/src/view/layout/AphrontSideNavView.php @@ -1,265 +1,270 @@ <?php /* * Copyright 2012 Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ final class AphrontSideNavView extends AphrontView { private $items = array(); private $flexNav; private $isFlexible; private $showApplicationMenu; private $user; private $currentApplication; private $active; public function setUser(PhabricatorUser $user) { $this->user = $user; return $this; } public function setShowApplicationMenu($show_application_menu) { $this->showApplicationMenu = $show_application_menu; return $this; } public function setCurrentApplication(PhabricatorApplication $current) { $this->currentApplication = $current; return $this; } public function addNavItem($item) { $this->items[] = $item; return $this; } public function setFlexNav($flex) { $this->flexNav = $flex; return $this; } public function setFlexible($flexible) { $this->isFlexible = $flexible; return $this; } public function setActive($active) { $this->active = $active; return $this; } public function render() { $view = new AphrontNullView(); $view->appendChild($this->items); if ($this->flexNav) { $user = $this->user; require_celerity_resource('phabricator-nav-view-css'); $nav_classes = array(); $nav_classes[] = 'phabricator-nav'; $app_id = celerity_generate_unique_node_id(); $nav_id = null; $drag_id = null; $content_id = celerity_generate_unique_node_id(); $local_id = null; $local_menu = null; $main_id = celerity_generate_unique_node_id(); $apps = $this->renderApplications(); $app_menu = phutil_render_tag( 'div', array( 'class' => 'phabricator-nav-col phabricator-nav-app', 'id' => $app_id, ), $apps->render()); if ($this->isFlexible) { $drag_id = celerity_generate_unique_node_id(); $flex_bar = phutil_render_tag( 'div', array( 'class' => 'phabricator-nav-drag', 'id' => $drag_id, ), ''); } else { $flex_bar = null; } $nav_menu = null; if ($this->items) { $local_id = celerity_generate_unique_node_id(); $nav_classes[] = 'has-local-nav'; $local_menu = phutil_render_tag( 'div', array( 'class' => 'phabricator-nav-col phabricator-nav-local', 'id' => $local_id, ), $view->render()); } Javelin::initBehavior( 'phabricator-nav', array( 'mainID' => $main_id, 'appID' => $app_id, 'localID' => $local_id, 'dragID' => $drag_id, 'contentID' => $content_id, )); if ($this->active && $local_id) { Javelin::initBehavior( 'phabricator-active-nav', array( 'localID' => $local_id, )); } $header_part = '<div class="phabricator-nav-head">'. '<div class="phabricator-nav-head-tablet">'. '<a href="#" class="nav-button nav-button-w nav-button-menu" '. 'id="tablet-menu1"></a>'. '<a href="#" class="nav-button nav-button-e nav-button-content '. 'nav-button-selected" id="tablet-menu2"></a>'. '</div>'. '<div class="phabricator-nav-head-phone">'. '<a href="#" class="nav-button nav-button-w nav-button-apps" '. 'id="phone-menu1"></button>'. '<a href="#" class="nav-button nav-button-menu" '. 'id="phone-menu2"></button>'. '<a href="#" class="nav-button nav-button-e nav-button-content '. 'nav-button-selected" id="phone-menu3"></button>'. '</div>'. '</div>'; return $header_part.phutil_render_tag( 'div', array( 'class' => implode(' ', $nav_classes), 'id' => $main_id, ), $app_menu. $local_menu. $flex_bar. phutil_render_tag( 'div', array( 'class' => 'phabricator-nav-content', 'id' => $content_id, ), $this->renderChildren())); } else { require_celerity_resource('aphront-side-nav-view-css'); return '<table class="aphront-side-nav-view">'. '<tr>'. '<th class="aphront-side-nav-navigation">'. $view->render(). '</th>'. '<td class="aphront-side-nav-content">'. $this->renderChildren(). '</td>'. '</tr>'. '</table>'; } } private function renderApplications() { $core = array(); $current = $this->currentApplication; $meta = null; + $group_core = PhabricatorApplication::GROUP_CORE; + $applications = PhabricatorApplication::getAllInstalledApplications(); foreach ($applications as $application) { if ($application instanceof PhabricatorApplicationApplications) { $meta = $application; continue; } - if ($application->getCoreApplicationOrder() !== null) { + if ($application->getApplicationGroup() != $group_core) { + continue; + } + if ($application->getApplicationOrder() !== null) { $core[] = $application; } } - $core = msort($core, 'getCoreApplicationOrder'); + $core = msort($core, 'getApplicationOrder'); if ($meta) { $core[] = $meta; } $core = mpull($core, null, 'getPHID'); if ($current && empty($core[$current->getPHID()])) { array_unshift($core, $current); } Javelin::initBehavior('phabricator-tooltips', array()); require_celerity_resource('aphront-tooltip-css'); $apps = array(); foreach ($core as $phid => $application) { $classes = array(); $classes[] = 'phabricator-nav-app-item'; if ($current && $phid == $current->getPHID()) { $classes[] = 'phabricator-nav-app-item-selected'; } $iclasses = array(); $iclasses[] = 'phabricator-nav-app-item-icon'; $style = null; if ($application->getIconURI()) { $style = 'background-image: url('.$application->getIconURI().'); '. 'background-size: 30px auto;'; } else { $iclasses[] = 'autosprite'; $iclasses[] = 'app-'.$application->getAutospriteName(); } $icon = phutil_render_tag( 'span', array( 'class' => implode(' ', $iclasses), 'style' => $style, ), ''); $apps[] = javelin_render_tag( 'a', array( 'class' => implode(' ', $classes), 'href' => $application->getBaseURI(), 'sigil' => 'has-tooltip', 'meta' => array( 'tip' => $application->getName(), 'align' => 'E', ), ), $icon. phutil_escape_html($application->getName())); } return id(new AphrontNullView())->appendChild($apps); } }