Changeset View
Changeset View
Standalone View
Standalone View
src/applications/differential/query/DifferentialRevisionQuery.php
| Show First 20 Lines • Show All 525 Lines • ▼ Show 20 Lines | private function loadData() { | ||||
| // NOTE: If the query includes "responsiblePHIDs", we execute it as a | // NOTE: If the query includes "responsiblePHIDs", we execute it as a | ||||
| // UNION of revisions they own and revisions they're reviewing. This has | // UNION of revisions they own and revisions they're reviewing. This has | ||||
| // much better performance than doing it with JOIN/WHERE. | // much better performance than doing it with JOIN/WHERE. | ||||
| if ($this->responsibles) { | if ($this->responsibles) { | ||||
| $basic_authors = $this->authors; | $basic_authors = $this->authors; | ||||
| $basic_reviewers = $this->reviewers; | $basic_reviewers = $this->reviewers; | ||||
| $authority_phids = $this->responsibles; | |||||
| $authority_projects = id(new PhabricatorProjectQuery()) | $authority_projects = id(new PhabricatorProjectQuery()) | ||||
| ->setViewer($this->getViewer()) | ->setViewer($this->getViewer()) | ||||
| ->withMemberPHIDs($this->responsibles) | ->withMemberPHIDs($this->responsibles) | ||||
| ->execute(); | ->execute(); | ||||
| $authority_phids = mpull($authority_projects, 'getPHID'); | foreach ($authority_projects as $project) { | ||||
| $authority_phids[] = $project->getPHID(); | |||||
| } | |||||
| // NOTE: We're querying by explicit owners to make this a little faster, | |||||
| // since we've already expanded project membership so we don't need to | |||||
| // have the PackageQuery do it again. | |||||
| $authority_packages = id(new PhabricatorOwnersPackageQuery()) | |||||
| ->setViewer($this->getViewer()) | |||||
| ->withOwnerPHIDs($authority_phids) | |||||
| ->execute(); | |||||
| foreach ($authority_packages as $package) { | |||||
| $authority_phids[] = $package->getPHID(); | |||||
| } | |||||
| try { | try { | ||||
| // Build the query where the responsible users are authors. | // Build the query where the responsible users are authors. | ||||
| $this->authors = array_merge($basic_authors, $this->responsibles); | $this->authors = array_merge($basic_authors, $this->responsibles); | ||||
| $this->reviewers = $basic_reviewers; | $this->reviewers = $basic_reviewers; | ||||
| $selects[] = $this->buildSelectStatement($conn_r); | $selects[] = $this->buildSelectStatement($conn_r); | ||||
| // Build the query where the responsible users are reviewers, or | // Build the query where the responsible users are reviewers, or | ||||
| // projects they are members of are reviewers. | // projects they are members of are reviewers. | ||||
| $this->authors = $basic_authors; | $this->authors = $basic_authors; | ||||
| $this->reviewers = array_merge( | $this->reviewers = array_merge( | ||||
| $basic_reviewers, | $basic_reviewers, | ||||
| $this->responsibles, | |||||
| $authority_phids); | $authority_phids); | ||||
| $selects[] = $this->buildSelectStatement($conn_r); | $selects[] = $this->buildSelectStatement($conn_r); | ||||
| // Put everything back like it was. | // Put everything back like it was. | ||||
| $this->authors = $basic_authors; | $this->authors = $basic_authors; | ||||
| $this->reviewers = $basic_reviewers; | $this->reviewers = $basic_reviewers; | ||||
| } catch (Exception $ex) { | } catch (Exception $ex) { | ||||
| $this->authors = $basic_authors; | $this->authors = $basic_authors; | ||||
| ▲ Show 20 Lines • Show All 540 Lines • ▼ Show 20 Lines | /* -( Internals )---------------------------------------------------------- */ | ||||
| private function loadReviewerAuthority( | private function loadReviewerAuthority( | ||||
| array $revisions, | array $revisions, | ||||
| array $edges, | array $edges, | ||||
| $allow_self) { | $allow_self) { | ||||
| $revision_map = mpull($revisions, null, 'getPHID'); | $revision_map = mpull($revisions, null, 'getPHID'); | ||||
| $viewer_phid = $this->getViewer()->getPHID(); | $viewer_phid = $this->getViewer()->getPHID(); | ||||
| // Find all the project reviewers which the user may have authority over. | // Find all the project/package reviewers which the user may have authority | ||||
| // over. | |||||
| $project_phids = array(); | $project_phids = array(); | ||||
| $package_phids = array(); | |||||
| $project_type = PhabricatorProjectProjectPHIDType::TYPECONST; | $project_type = PhabricatorProjectProjectPHIDType::TYPECONST; | ||||
| $package_type = PhabricatorOwnersPackagePHIDType::TYPECONST; | |||||
| $edge_type = DifferentialRevisionHasReviewerEdgeType::EDGECONST; | $edge_type = DifferentialRevisionHasReviewerEdgeType::EDGECONST; | ||||
| foreach ($edges as $src => $types) { | foreach ($edges as $src => $types) { | ||||
| if (!$allow_self) { | if (!$allow_self) { | ||||
| if ($revision_map[$src]->getAuthorPHID() == $viewer_phid) { | if ($revision_map[$src]->getAuthorPHID() == $viewer_phid) { | ||||
| // If self-review isn't permitted, the user will never have | // If self-review isn't permitted, the user will never have | ||||
| // authority over projects on revisions they authored because you | // authority over projects on revisions they authored because you | ||||
| // can't accept your own revisions, so we don't need to load any | // can't accept your own revisions, so we don't need to load any | ||||
| // data about these reviewers. | // data about these reviewers. | ||||
| continue; | continue; | ||||
| } | } | ||||
| } | } | ||||
| $edge_data = idx($types, $edge_type, array()); | $edge_data = idx($types, $edge_type, array()); | ||||
| foreach ($edge_data as $dst => $data) { | foreach ($edge_data as $dst => $data) { | ||||
| if (phid_get_type($dst) == $project_type) { | $phid_type = phid_get_type($dst); | ||||
| if ($phid_type == $project_type) { | |||||
| $project_phids[] = $dst; | $project_phids[] = $dst; | ||||
| } | } | ||||
| if ($phid_type == $package_type) { | |||||
| $package_phids[] = $dst; | |||||
| } | } | ||||
| } | } | ||||
| } | |||||
| // The viewer has authority over themselves. | |||||
| $user_authority = array_fuse(array($viewer_phid)); | |||||
| // Now, figure out which of these projects the viewer is actually a | // And over any projects they are a member of. | ||||
| // member of. | |||||
| $project_authority = array(); | $project_authority = array(); | ||||
| if ($project_phids) { | if ($project_phids) { | ||||
| $project_authority = id(new PhabricatorProjectQuery()) | $project_authority = id(new PhabricatorProjectQuery()) | ||||
| ->setViewer($this->getViewer()) | ->setViewer($this->getViewer()) | ||||
| ->withPHIDs($project_phids) | ->withPHIDs($project_phids) | ||||
| ->withMemberPHIDs(array($viewer_phid)) | ->withMemberPHIDs(array($viewer_phid)) | ||||
| ->execute(); | ->execute(); | ||||
| $project_authority = mpull($project_authority, 'getPHID'); | $project_authority = mpull($project_authority, 'getPHID'); | ||||
| $project_authority = array_fuse($project_authority); | |||||
| } | } | ||||
| // Finally, the viewer has authority over themselves. | // And over any packages they own. | ||||
| return array( | $package_authority = array(); | ||||
| $viewer_phid => true, | if ($package_phids) { | ||||
| ) + array_fuse($project_authority); | $package_authority = id(new PhabricatorOwnersPackageQuery()) | ||||
| ->setViewer($this->getViewer()) | |||||
| ->withPHIDs($package_phids) | |||||
| ->withAuthorityPHIDs(array($viewer_phid)) | |||||
| ->execute(); | |||||
| $package_authority = mpull($package_authority, 'getPHID'); | |||||
| $package_authority = array_fuse($package_authority); | |||||
| } | |||||
| return $user_authority + $project_authority + $package_authority; | |||||
| } | } | ||||
| public function getQueryApplicationClass() { | public function getQueryApplicationClass() { | ||||
| return 'PhabricatorDifferentialApplication'; | return 'PhabricatorDifferentialApplication'; | ||||
| } | } | ||||
| protected function getPrimaryTableAlias() { | protected function getPrimaryTableAlias() { | ||||
| return 'r'; | return 'r'; | ||||
| } | } | ||||
| } | } | ||||