Page MenuHomePhabricator

D10153.id24427.diff
No OneTemporary

D10153.id24427.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,85 @@
+<?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 Aphront400Response();
+ }
+
+ $project_id = $project->getID();
+ $board_uri = $this->getApplicationURI("board/{$project_id}/");
+
+ if ($request->isFormPost()) {
+ $import_phid = $request->getArr('importProjectPHID');
+ $import_phid = reset($import_phid);
+
+ $import_columns = id(new PhabricatorProjectColumnQuery())
+ ->setViewer($viewer)
+ ->withProjectPHIDs(array($import_phid))
+ ->execute();
+ if (!$import_columns) {
+ return new Aphront400Response();
+ }
+
+ $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);
+ }
+
+ $proj_selector = id(new AphrontFormTokenizerControl())
+ ->setName('importProjectPHID')
+ ->setUser($viewer)
+ ->setDatasource(id(new PhabricatorProjectDatasource())
+ ->setParameters(array('mustHaveColumns' => true))
+ ->setLimit(1));
+ return $this->newDialog()
+ ->setTitle(pht('Import Columns'))
+ ->setWidth(AphrontDialogView::WIDTH_FORM)
+ ->appendParagraph(pht('Choose a project to import columns from:'))
+ ->appendChild($proj_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,27 @@
$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);
+ switch ($request->getStr('initialize-type')) {
+ case 'backlog-only':
+ $unguarded = AphrontWriteGuard::beginScopedUnguardedWrites();
+ $column = PhabricatorProjectColumn::initializeNewColumn($viewer)
+ ->setSequence(0)
+ ->setProjectPHID($project->getPHID())
+ ->save();
+ $column->attachProject($project);
+ $columns[0] = $column;
+ unset($unguarded);
+ break;
+ case 'import':
+ return id(new AphrontRedirectResponse())
+ ->setURI(
+ $this->getApplicationURI('board/'.$project->getID().'/import/'));
+ break;
+ default:
+ return $this->initializeWorkboardDialog($project);
+ break;
+ }
}
ksort($columns);
@@ -406,5 +417,31 @@
return $manage_button;
}
+ private function initializeWorkboardDialog(PhabricatorProject $project) {
+
+ $instructions = pht('This workboard has not been setup yet.');
+ $new_selector = id(new AphrontFormRadioButtonControl())
+ ->setName('initialize-type')
+ ->setValue('backlog-only')
+ ->addButton(
+ 'backlog-only',
+ pht('New Empty Board'),
+ pht('Create a new board with just a backlog column.'))
+ ->addButton(
+ 'import',
+ pht('Import Columns'),
+ pht('Import board columns from another project.'));
+
+ $dialog = id(new AphrontDialogView())
+ ->setUser($this->getRequest()->getUser())
+ ->setTitle(pht('New Workboard'))
+ ->addSubmitButton('Continue')
+ ->addCancelButton($this->getApplicationURI('view/'.$project->getID().'/'))
+ ->appendParagraph($instructions)
+ ->appendChild($new_selector);
+
+ return id(new AphrontDialogResponse())
+ ->setDialog($dialog);
+ }
}
diff --git a/src/applications/project/typeahead/PhabricatorProjectDatasource.php b/src/applications/project/typeahead/PhabricatorProjectDatasource.php
--- a/src/applications/project/typeahead/PhabricatorProjectDatasource.php
+++ b/src/applications/project/typeahead/PhabricatorProjectDatasource.php
@@ -29,9 +29,24 @@
->needSlugs(true)
->withDatasourceQuery($raw_query)
->execute();
+ $projs = mpull($projs, null, 'getPHID');
+
+ $must_have_cols = $this->getParameter('mustHaveColumns', false);
+ if ($must_have_cols) {
+ $columns = id(new PhabricatorProjectColumnQuery())
+ ->setViewer($viewer)
+ ->withProjectPHIDs(array_keys($projs))
+ ->execute();
+ $has_cols = mgroup($columns, 'getProjectPHID');
+ } else {
+ $has_cols = array_fill_keys(array_keys($projs), true);
+ }
$results = array();
foreach ($projs as $proj) {
+ if (!isset($has_cols[$proj->getPHID()])) {
+ continue;
+ }
$closed = null;
if ($proj->isArchived()) {
$closed = pht('Archived');

File Metadata

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

Event Timeline