Page MenuHomePhabricator

D10153.id24423.diff
No OneTemporary

D10153.id24423.diff

diff --git a/src/__phutil_library_map__.php b/src/__phutil_library_map__.php
--- a/src/__phutil_library_map__.php
+++ b/src/__phutil_library_map__.php
@@ -1926,6 +1926,7 @@
'PhabricatorProjectBoardController' => 'applications/project/controller/PhabricatorProjectBoardController.php',
'PhabricatorProjectBoardDeleteController' => 'applications/project/controller/PhabricatorProjectBoardDeleteController.php',
'PhabricatorProjectBoardEditController' => 'applications/project/controller/PhabricatorProjectBoardEditController.php',
+ 'PhabricatorProjectBoardImportController' => 'applications/project/controller/PhabricatorProjectBoardImportController.php',
'PhabricatorProjectBoardReorderController' => 'applications/project/controller/PhabricatorProjectBoardReorderController.php',
'PhabricatorProjectBoardViewController' => 'applications/project/controller/PhabricatorProjectBoardViewController.php',
'PhabricatorProjectColumn' => 'applications/project/storage/PhabricatorProjectColumn.php',
@@ -2620,6 +2621,7 @@
'PonderVoteSaveController' => 'applications/ponder/controller/PonderVoteSaveController.php',
'ProjectBoardTaskCard' => 'applications/project/view/ProjectBoardTaskCard.php',
'ProjectConduitAPIMethod' => 'applications/project/conduit/ProjectConduitAPIMethod.php',
+ 'ProjectCreateConduitAPIMethod' => 'applications/project/conduit/ProjectCreateConduitAPIMethod.php',
'ProjectCreateProjectsCapability' => 'applications/project/capability/ProjectCreateProjectsCapability.php',
'ProjectQueryConduitAPIMethod' => 'applications/project/conduit/ProjectQueryConduitAPIMethod.php',
'ProjectRemarkupRule' => 'applications/project/remarkup/ProjectRemarkupRule.php',
@@ -4752,6 +4754,7 @@
'PhabricatorProjectBoardController' => 'PhabricatorProjectController',
'PhabricatorProjectBoardDeleteController' => 'PhabricatorProjectBoardController',
'PhabricatorProjectBoardEditController' => 'PhabricatorProjectBoardController',
+ 'PhabricatorProjectBoardImportController' => 'PhabricatorProjectBoardController',
'PhabricatorProjectBoardReorderController' => 'PhabricatorProjectBoardController',
'PhabricatorProjectBoardViewController' => 'PhabricatorProjectBoardController',
'PhabricatorProjectColumn' => array(
@@ -5561,6 +5564,7 @@
'PonderVoteEditor' => 'PhabricatorEditor',
'PonderVoteSaveController' => 'PonderController',
'ProjectConduitAPIMethod' => 'ConduitAPIMethod',
+ 'ProjectCreateConduitAPIMethod' => 'ProjectConduitAPIMethod',
'ProjectCreateProjectsCapability' => 'PhabricatorPolicyCapability',
'ProjectQueryConduitAPIMethod' => 'ProjectConduitAPIMethod',
'ProjectRemarkupRule' => 'PhabricatorObjectRemarkupRule',
diff --git a/src/applications/project/application/PhabricatorProjectApplication.php b/src/applications/project/application/PhabricatorProjectApplication.php
--- a/src/applications/project/application/PhabricatorProjectApplication.php
+++ b/src/applications/project/application/PhabricatorProjectApplication.php
@@ -71,6 +71,8 @@
=> 'PhabricatorProjectBoardDeleteController',
'column/(?:(?P<id>\d+)/)?'
=> 'PhabricatorProjectColumnDetailController',
+ 'import/'
+ => 'PhabricatorProjectBoardImportController',
'reorder/'
=> 'PhabricatorProjectBoardReorderController',
),
diff --git a/src/applications/project/controller/PhabricatorProjectBoardImportController.php b/src/applications/project/controller/PhabricatorProjectBoardImportController.php
new file mode 100644
--- /dev/null
+++ b/src/applications/project/controller/PhabricatorProjectBoardImportController.php
@@ -0,0 +1,118 @@
+<?php
+
+final class PhabricatorProjectBoardImportController
+ extends PhabricatorProjectBoardController {
+
+ private $projectID;
+
+ public function willProcessRequest(array $data) {
+ $this->projectID = $data['projectID'];
+ }
+
+ public function processRequest() {
+ $request = $this->getRequest();
+ $viewer = $request->getUser();
+
+ $project = id(new PhabricatorProjectQuery())
+ ->setViewer($viewer)
+ ->requireCapabilities(
+ array(
+ PhabricatorPolicyCapability::CAN_VIEW,
+ PhabricatorPolicyCapability::CAN_EDIT,
+ ))
+ ->withIDs(array($this->projectID))
+ ->executeOne();
+ if (!$project) {
+ return new Aphront404Response();
+ }
+
+ $this->setProject($project);
+
+ $columns = id(new PhabricatorProjectColumnQuery())
+ ->setViewer($viewer)
+ ->withProjectPHIDs(array($project->getPHID()))
+ ->execute();
+ if ($columns) {
+ return new Aphront404Response();
+ }
+
+ $project_id = $project->getID();
+ $board_uri = $this->getApplicationURI("board/{$project_id}/");
+
+ if ($request->isFormPost()) {
+ $import_phid = $request->getStr('importProjectPHID');
+
+ $import_columns = id(new PhabricatorProjectColumnQuery())
+ ->setViewer($viewer)
+ ->withProjectPHIDs(array($import_phid))
+ ->execute();
+ // not sure how this can happen exactly, but it is bad so 404
+ if (!$import_columns) {
+ return new Aphront404Response();
+ }
+
+ $table = id(new PhabricatorProjectColumn())
+ ->openTransaction();
+ foreach ($import_columns as $import_column) {
+ if ($import_column->isHidden()) {
+ continue;
+ }
+ $new_column = PhabricatorProjectColumn::initializeNewColumn($viewer)
+ ->setSequence($import_column->getSequence())
+ ->setProjectPHID($project->getPHID())
+ ->setName($import_column->getName())
+ ->save();
+ }
+ $table->saveTransaction();
+
+ return id(new AphrontRedirectResponse())->setURI($board_uri);
+ }
+
+ $viewer_projects = id(new PhabricatorProjectQuery())
+ ->setViewer($viewer)
+ ->requireCapabilities(
+ array(
+ PhabricatorPolicyCapability::CAN_VIEW,
+ PhabricatorPolicyCapability::CAN_EDIT,
+ ))
+ ->withMemberPHIDs(array($viewer->getPHID()))
+ ->execute();
+
+ if (empty($viewer_projects)) {
+ $body = pht(
+ 'You are not a member of any projects that have initialized '.
+ 'workboards. Join such a project and try again.');
+ return $this->newDialog()
+ ->setTitle(pht('Can Not Import Project Columns'))
+ ->appendChild($body)
+ ->setWidth(AphrontDialogView::WIDTH_FORM)
+ ->addCancelButton($board_uri);
+ }
+ $viewer_projects = mpull($viewer_projects, null, 'getPHID');
+
+ $columns = id(new PhabricatorProjectColumnQuery())
+ ->setViewer($viewer)
+ ->withProjectPHIDs(array_keys($viewer_projects))
+ ->execute();
+ $columns = mgroup($columns, 'getProjectPHID');
+ $importable_projects = array_intersect_key($viewer_projects, $columns);
+ $project_selector = id(new AphrontFormRadioButtonControl())
+ ->setLabel(pht('Import from one of the following projects:'))
+ ->setName('importProjectPHID')
+ ->setValue(reset($importable_projects)->getPHID());
+ foreach ($importable_projects as $importable_project) {
+ $project_selector->addButton(
+ $importable_project->getPHID(),
+ $importable_project->getName(),
+ null);
+ }
+
+ return $this->newDialog()
+ ->setTitle(pht('Import Project Columns'))
+ ->setWidth(AphrontDialogView::WIDTH_FORM)
+ ->appendChild($project_selector)
+ ->addCancelButton($board_uri)
+ ->addSubmitButton(pht('Import'));
+ }
+
+}
diff --git a/src/applications/project/controller/PhabricatorProjectBoardViewController.php b/src/applications/project/controller/PhabricatorProjectBoardViewController.php
--- a/src/applications/project/controller/PhabricatorProjectBoardViewController.php
+++ b/src/applications/project/controller/PhabricatorProjectBoardViewController.php
@@ -54,16 +54,20 @@
$columns = $column_query->execute();
$columns = mpull($columns, null, 'getSequence');
- // If there's no default column, create one now.
if (empty($columns[0])) {
- $unguarded = AphrontWriteGuard::beginScopedUnguardedWrites();
- $column = PhabricatorProjectColumn::initializeNewColumn($viewer)
- ->setSequence(0)
- ->setProjectPHID($project->getPHID())
- ->save();
- $column->attachProject($project);
- $columns[0] = $column;
- unset($unguarded);
+ // If there's no default column and the user wants us to, create one now.
+ if ($request->getExists('initialize')) {
+ $unguarded = AphrontWriteGuard::beginScopedUnguardedWrites();
+ $column = PhabricatorProjectColumn::initializeNewColumn($viewer)
+ ->setSequence(0)
+ ->setProjectPHID($project->getPHID())
+ ->save();
+ $column->attachProject($project);
+ $columns[0] = $column;
+ unset($unguarded);
+ } else {
+ return $this->initializeWorkboardDialog();
+ }
}
ksort($columns);
@@ -406,5 +410,37 @@
return $manage_button;
}
+ private function initializeWorkboardDialog() {
+ $default_column_link = phutil_tag(
+ 'a',
+ array(
+ 'href' =>
+ $this->getApplicationURI('/board/'.$this->id.'/?initialize=true')
+ ),
+ pht('add a default backlog column'));
+ $import_panels_link = phutil_tag(
+ 'a',
+ array(
+ 'href' => $this->getApplicationURI('/board/'.$this->id.'/import/')
+ ),
+ pht('import columns from another project'));
+
+ $instructions = phutil_tag(
+ 'p',
+ array(),
+ pht(
+ 'You can %s or %s to get started.',
+ $default_column_link,
+ $import_panels_link));
+ $dialog = id(new AphrontDialogView())
+ ->setUser($this->getRequest()->getUser())
+ ->setTitle(pht('This workboard needs initial setup.'))
+ ->addHiddenInput('initialize', true)
+ ->addSubmitButton('Add Default Backlog Column')
+ ->appendChild($instructions);
+
+ return id(new AphrontDialogResponse())
+ ->setDialog($dialog);
+ }
}

File Metadata

Mime Type
text/plain
Expires
Fri, Apr 18, 12:30 AM (3 w, 12 h ago)
Storage Engine
blob
Storage Format
Encrypted (AES-256-CBC)
Storage Handle
7728681
Default Alt Text
D10153.id24423.diff (9 KB)

Event Timeline