@recaptime-dev's working patches + fork for Phorge, a community fork of Phabricator. (Upstream dev and stable branches are at upstream/main and upstream/stable respectively.) hq.recaptime.dev/wiki/Phorge
phorge phabricator
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Migrate project profiles onto projects, and remove ProjectProfile object

Summary:
Ref T4379. Long ago, the "Project" vs "ProjectProfile" split was intended to allow a bunch of special fields on projects without burdening the simple use cases, but CustomField handles that far better and far more generally, and doing this makes using ApplicationTransactions a pain to get right, so get rid of it.

The only remaining field is `profileImagePHID`, which we can just move to the main Project object. This is custom enough that I think it's reasonable not to express it as a custom field.

Test Plan: Created a project, set profile, edited project, viewed in typeahead, ran migration, verified database results.

Reviewers: btrahan

Reviewed By: btrahan

CC: aran

Maniphest Tasks: T4379

Differential Revision: https://secure.phabricator.com/D8183

+48 -105
+2
resources/sql/autopatches/20140210.projcfield.2.piccol.sql
··· 1 + ALTER TABLE {$NAMESPACE}_project.project 2 + ADD profileImagePHID VARCHAR(64) COLLATE utf8_bin;
+4
resources/sql/autopatches/20140210.projcfield.3.picmig.sql
··· 1 + UPDATE {$NAMESPACE}_project.project proj, 2 + {$NAMESPACE}_project.project_profile profile 3 + SET proj.profileImagePHID = profile.profileImagePHID 4 + WHERE proj.phid = profile.projectPHID;
-2
src/__phutil_library_map__.php
··· 1849 1849 'PhabricatorProjectNameCollisionException' => 'applications/project/exception/PhabricatorProjectNameCollisionException.php', 1850 1850 'PhabricatorProjectPHIDTypeColumn' => 'applications/project/phid/PhabricatorProjectPHIDTypeColumn.php', 1851 1851 'PhabricatorProjectPHIDTypeProject' => 'applications/project/phid/PhabricatorProjectPHIDTypeProject.php', 1852 - 'PhabricatorProjectProfile' => 'applications/project/storage/PhabricatorProjectProfile.php', 1853 1852 'PhabricatorProjectProfileController' => 'applications/project/controller/PhabricatorProjectProfileController.php', 1854 1853 'PhabricatorProjectProfileEditController' => 'applications/project/controller/PhabricatorProjectProfileEditController.php', 1855 1854 'PhabricatorProjectProfilePictureController' => 'applications/project/controller/PhabricatorProjectProfilePictureController.php', ··· 4599 4598 'PhabricatorProjectNameCollisionException' => 'Exception', 4600 4599 'PhabricatorProjectPHIDTypeColumn' => 'PhabricatorPHIDType', 4601 4600 'PhabricatorProjectPHIDTypeProject' => 'PhabricatorPHIDType', 4602 - 'PhabricatorProjectProfile' => 'PhabricatorProjectDAO', 4603 4601 'PhabricatorProjectProfileController' => 'PhabricatorProjectController', 4604 4602 'PhabricatorProjectProfileEditController' => 'PhabricatorProjectController', 4605 4603 'PhabricatorProjectProfilePictureController' => 'PhabricatorProjectController',
-1
src/applications/project/controller/PhabricatorProjectArchiveController.php
··· 21 21 PhabricatorPolicyCapability::CAN_VIEW, 22 22 PhabricatorPolicyCapability::CAN_EDIT, 23 23 )) 24 - ->needProfiles(true) 25 24 ->executeOne(); 26 25 if (!$project) { 27 26 return new Aphront404Response();
-4
src/applications/project/controller/PhabricatorProjectCreateController.php
··· 13 13 ProjectCapabilityCreateProjects::CAPABILITY); 14 14 15 15 $project = PhabricatorProject::initializeNewProject($user); 16 - $profile = new PhabricatorProjectProfile(); 17 16 18 17 $e_name = true; 19 18 $errors = array(); ··· 42 41 43 42 if (!$errors) { 44 43 $project->save(); 45 - $profile->setProjectPHID($project->getPHID()); 46 - $profile->setBlurb(''); 47 - $profile->save(); 48 44 49 45 if ($request->isAjax()) { 50 46 return id(new AphrontAjaxResponse())
+6 -13
src/applications/project/controller/PhabricatorProjectProfileController.php
··· 23 23 ->setViewer($user) 24 24 ->withIDs(array($this->id)) 25 25 ->needMembers(true) 26 - ->needProfiles(true) 26 + ->needImages(true) 27 27 ->executeOne(); 28 28 if (!$project) { 29 29 return new Aphront404Response(); 30 30 } 31 31 32 - $profile = $project->getProfile(); 33 - $picture = $profile->getProfileImageURI(); 32 + $picture = $project->getProfileImageURI(); 34 33 35 34 require_celerity_resource('phabricator-profile-css'); 36 35 37 - $tasks = $this->renderTasksPage($project, $profile); 36 + $tasks = $this->renderTasksPage($project); 38 37 39 38 $query = new PhabricatorFeedQuery(); 40 39 $query->setFilterPHIDs( ··· 62 61 $header->setStatus('policy-noone', '', pht('Archived')); 63 62 } 64 63 65 - 66 64 $actions = $this->buildActionListView($project); 67 - $properties = $this->buildPropertyListView($project, $profile, $actions); 65 + $properties = $this->buildPropertyListView($project, $actions); 68 66 69 67 $crumbs = $this->buildApplicationCrumbs(); 70 68 $crumbs->addTextCrumb($project->getName()) ··· 86 84 )); 87 85 } 88 86 89 - private function renderFeedPage( 90 - PhabricatorProject $project, 91 - PhabricatorProjectProfile $profile) { 87 + private function renderFeedPage(PhabricatorProject $project) { 92 88 93 89 $query = new PhabricatorFeedQuery(); 94 90 $query->setFilterPHIDs(array($project->getPHID())); ··· 117 113 } 118 114 119 115 120 - private function renderTasksPage( 121 - PhabricatorProject $project, 122 - PhabricatorProjectProfile $profile) { 116 + private function renderTasksPage(PhabricatorProject $project) { 123 117 124 118 $user = $this->getRequest()->getUser(); 125 119 ··· 244 238 245 239 private function buildPropertyListView( 246 240 PhabricatorProject $project, 247 - PhabricatorProjectProfile $profile, 248 241 PhabricatorActionListView $actions) { 249 242 $request = $this->getRequest(); 250 243 $viewer = $request->getUser();
+4 -6
src/applications/project/controller/PhabricatorProjectProfilePictureController.php
··· 16 16 $project = id(new PhabricatorProjectQuery()) 17 17 ->setViewer($viewer) 18 18 ->withIDs(array($this->id)) 19 - ->needProfiles(true) 20 19 ->requireCapabilities( 21 20 array( 22 21 PhabricatorPolicyCapability::CAN_VIEW, ··· 75 74 } 76 75 77 76 if (!$errors) { 78 - $profile = $project->getProfile(); 79 77 if ($is_default) { 80 - $profile->setProfileImagePHID(null); 78 + $project->setProfileImagePHID(null); 81 79 } else { 82 - $profile->setProfileImagePHID($xformed->getPHID()); 80 + $project->setProfileImagePHID($xformed->getPHID()); 83 81 $xformed->attachToObject($viewer, $project->getPHID()); 84 82 } 85 - $profile->save(); 83 + $project->save(); 86 84 return id(new AphrontRedirectResponse())->setURI($project_uri); 87 85 } 88 86 } ··· 99 97 100 98 $images = array(); 101 99 102 - $current = $project->getProfile()->getProfileImagePHID(); 100 + $current = $project->getProfileImagePHID(); 103 101 $has_current = false; 104 102 if ($current) { 105 103 $files = id(new PhabricatorFileQuery())
-5
src/applications/project/lipsum/PhabricatorProjectTestDataGenerator.php
··· 37 37 ->setContentSource(PhabricatorContentSource::newConsoleSource()) 38 38 ->applyTransactions($project, $this->xactions); 39 39 40 - $profile = id(new PhabricatorProjectProfile()) 41 - ->setBlurb($this->generateDescription()) 42 - ->setProjectPHID($project->getPHID()) 43 - ->save(); 44 - 45 40 return $project->save(); 46 41 } 47 42
+15 -37
src/applications/project/query/PhabricatorProjectQuery.php
··· 17 17 const STATUS_ARCHIVED = 'status-archived'; 18 18 19 19 private $needMembers; 20 - private $needProfiles; 20 + private $needImages; 21 21 22 22 public function withIDs(array $ids) { 23 23 $this->ids = $ids; ··· 54 54 return $this; 55 55 } 56 56 57 - public function needProfiles($need_profiles) { 58 - $this->needProfiles = $need_profiles; 57 + public function needImages($need_images) { 58 + $this->needImages = $need_images; 59 59 return $this; 60 60 } 61 61 ··· 126 126 } 127 127 128 128 protected function didFilterPage(array $projects) { 129 - if ($this->needProfiles) { 130 - $profiles = id(new PhabricatorProjectProfile())->loadAllWhere( 131 - 'projectPHID IN (%Ls)', 132 - mpull($projects, 'getPHID')); 133 - $profiles = mpull($profiles, null, 'getProjectPHID'); 134 - 129 + if ($this->needImages) { 135 130 $default = null; 136 131 137 - if ($profiles) { 138 - $file_phids = mpull($profiles, 'getProfileImagePHID'); 139 - $files = id(new PhabricatorFileQuery()) 140 - ->setParentQuery($this) 141 - ->setViewer($this->getViewer()) 142 - ->withPHIDs($file_phids) 143 - ->execute(); 144 - $files = mpull($files, null, 'getPHID'); 145 - foreach ($profiles as $profile) { 146 - $file = idx($files, $profile->getProfileImagePHID()); 147 - if (!$file) { 148 - if (!$default) { 149 - $default = PhabricatorFile::loadBuiltin( 150 - $this->getViewer(), 151 - 'project.png'); 152 - } 153 - $file = $default; 154 - } 155 - $profile->attachProfileImageFile($file); 156 - } 157 - } 158 - 132 + $file_phids = mpull($projects, 'getProfileImagePHID'); 133 + $files = id(new PhabricatorFileQuery()) 134 + ->setParentQuery($this) 135 + ->setViewer($this->getViewer()) 136 + ->withPHIDs($file_phids) 137 + ->execute(); 138 + $files = mpull($files, null, 'getPHID'); 159 139 foreach ($projects as $project) { 160 - $profile = idx($profiles, $project->getPHID()); 161 - if (!$profile) { 140 + $file = idx($files, $project->getProfileImagePHID()); 141 + if (!$file) { 162 142 if (!$default) { 163 143 $default = PhabricatorFile::loadBuiltin( 164 144 $this->getViewer(), 165 145 'project.png'); 166 146 } 167 - $profile = id(new PhabricatorProjectProfile()) 168 - ->setProjectPHID($project->getPHID()) 169 - ->attachProfileImageFile($default); 147 + $file = $default; 170 148 } 171 - $project->attachProfile($profile); 149 + $project->attachProfileImageFile($file); 172 150 } 173 151 } 174 152
+15 -10
src/applications/project/storage/PhabricatorProject.php
··· 12 12 protected $authorPHID; 13 13 protected $subprojectPHIDs = array(); 14 14 protected $phrictionSlug; 15 + protected $profileImagePHID; 15 16 16 17 protected $viewPolicy; 17 18 protected $editPolicy; ··· 19 20 20 21 private $memberPHIDs = self::ATTACHABLE; 21 22 private $sparseMembers = self::ATTACHABLE; 22 - private $profile = self::ATTACHABLE; 23 23 private $customFields = self::ATTACHABLE; 24 + private $profileImageFile = self::ATTACHABLE; 24 25 25 26 public static function initializeNewProject(PhabricatorUser $actor) { 26 27 return id(new PhabricatorProject()) ··· 113 114 PhabricatorProjectPHIDTypeProject::TYPECONST); 114 115 } 115 116 116 - public function getProfile() { 117 - return $this->assertAttached($this->profile); 118 - } 119 - 120 - public function attachProfile(PhabricatorProjectProfile $profile) { 121 - $this->profile = $profile; 122 - return $this; 123 - } 124 - 125 117 public function attachMemberPHIDs(array $phids) { 126 118 $this->memberPHIDs = $phids; 127 119 return $this; ··· 151 143 152 144 public function isArchived() { 153 145 return ($this->getStatus() == PhabricatorProjectStatus::STATUS_ARCHIVED); 146 + } 147 + 148 + public function getProfileImageURI() { 149 + return $this->getProfileImageFile()->getBestURI(); 150 + } 151 + 152 + public function attachProfileImageFile(PhabricatorFile $file) { 153 + $this->profileImageFile = $file; 154 + return $this; 155 + } 156 + 157 + public function getProfileImageFile() { 158 + return $this->assertAttached($this->profileImageFile); 154 159 } 155 160 156 161
-24
src/applications/project/storage/PhabricatorProjectProfile.php
··· 1 - <?php 2 - 3 - final class PhabricatorProjectProfile extends PhabricatorProjectDAO { 4 - 5 - protected $projectPHID; 6 - protected $blurb; 7 - protected $profileImagePHID; 8 - 9 - private $profileImageFile = self::ATTACHABLE; 10 - 11 - public function getProfileImageURI() { 12 - return $this->getProfileImageFile()->getBestURI(); 13 - } 14 - 15 - public function attachProfileImageFile(PhabricatorFile $file) { 16 - $this->profileImageFile = $file; 17 - return $this; 18 - } 19 - 20 - public function getProfileImageFile() { 21 - return $this->assertAttached($this->profileImageFile); 22 - } 23 - 24 - }
+2 -3
src/applications/typeahead/controller/PhabricatorTypeaheadCommonDatasourceController.php
··· 286 286 $projs = id(new PhabricatorProjectQuery()) 287 287 ->setViewer($viewer) 288 288 ->withStatus(PhabricatorProjectQuery::STATUS_OPEN) 289 - ->needProfiles(true) 289 + ->needImages(true) 290 290 ->execute(); 291 291 foreach ($projs as $proj) { 292 292 $proj_result = id(new PhabricatorTypeaheadResult()) ··· 295 295 ->setURI('/project/view/'.$proj->getID().'/') 296 296 ->setPHID($proj->getPHID()); 297 297 298 - $prof = $proj->getProfile(); 299 - $proj_result->setImageURI($prof->getProfileImageURI()); 298 + $proj_result->setImageURI($proj->getProfileImageURI()); 300 299 301 300 $results[] = $proj_result; 302 301 }