@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.

Improve Conduit performance of special edge-based custom Revision fields

Summary:
Ref T11404. Depends on D16351. Currently, both `differential.query` and `differential.revision.search` issue `2N` queries to fetch:

- dependencies for each revision; and
- projects for each revision.

Fix this:

- Take these custom fields out of Conduit so they don't load this data by default.
- For `differential.query`, put this data back in by hard coding it.
- For `differential.revision.search`, just leave it out. You can already optionally get projects efficiently, and this endpoint is a work in progress. I would tentatively be inclined to expose graph data as a "graph" extension once we need it.

This makes both methods execute in `O(1)` time (which is still 20-30 queries, but at least it's not 320 queries anymore).

Test Plan:
- Ran `differential.query`, observed no change in results but 199 fewer internal queries.
- Ran `differential.revision.search`, observed data gone from results and 200 fewer internal queries.

Reviewers: yelirekim, chad

Reviewed By: chad

Maniphest Tasks: T11404

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

+35 -6
+27
src/applications/differential/conduit/DifferentialConduitAPIMethod.php
··· 178 178 179 179 $results = array(); 180 180 foreach ($field_lists as $revision_phid => $field_list) { 181 + $results[$revision_phid] = array(); 181 182 foreach ($field_list->getFields() as $field) { 182 183 $field_key = $field->getFieldKeyForConduit(); 183 184 $value = $field->getConduitDictionaryValue(); 184 185 $results[$revision_phid][$field_key] = $value; 186 + } 187 + } 188 + 189 + // For compatibility, fill in these "custom fields" by querying for them 190 + // efficiently. See T11404 for discussion. 191 + 192 + $legacy_edge_map = array( 193 + 'phabricator:projects' => 194 + PhabricatorProjectObjectHasProjectEdgeType::EDGECONST, 195 + 'phabricator:depends-on' => 196 + DifferentialRevisionDependsOnRevisionEdgeType::EDGECONST, 197 + ); 198 + 199 + $query = id(new PhabricatorEdgeQuery()) 200 + ->withSourcePHIDs(array_keys($results)) 201 + ->withEdgeTypes($legacy_edge_map); 202 + 203 + $query->execute(); 204 + 205 + foreach ($results as $revision_phid => $dict) { 206 + foreach ($legacy_edge_map as $edge_key => $edge_type) { 207 + $phid_list = $query->getDestinationPHIDs( 208 + array($revision_phid), 209 + array($edge_type)); 210 + 211 + $results[$revision_phid][$edge_key] = $phid_list; 185 212 } 186 213 } 187 214
+4 -5
src/applications/differential/customfield/DifferentialParentRevisionsField.php
··· 7 7 return 'differential:depends-on'; 8 8 } 9 9 10 - public function getFieldKeyForConduit() { 11 - return 'phabricator:depends-on'; 12 - } 13 - 14 10 public function getFieldName() { 15 11 return pht('Parent Revisions'); 16 12 } ··· 33 29 } 34 30 35 31 public function shouldAppearInConduitDictionary() { 36 - return true; 32 + // To improve performance, we exclude this field from Conduit results. 33 + // See T11404 for discussion. In modern "differential.revision.search", 34 + // this information is available efficiently as an attachment. 35 + return false; 37 36 } 38 37 39 38 public function getConduitDictionaryValue() {
+4 -1
src/applications/differential/customfield/DifferentialProjectsField.php
··· 91 91 } 92 92 93 93 public function shouldAppearInConduitDictionary() { 94 - return true; 94 + // To improve performance, we exclude this field from Conduit results. 95 + // See T11404 for discussion. In modern "differential.revision.search", 96 + // this information is available efficiently as an attachment. 97 + return false; 95 98 } 96 99 97 100 public function getApplicationTransactionMetadata() {