@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<?php
2
3/**
4 * @extends PhabricatorCursorPagedPolicyAwareQuery<DifferentialDiff>
5 */
6final class DifferentialDiffQuery
7 extends PhabricatorCursorPagedPolicyAwareQuery {
8
9 private $ids;
10 private $phids;
11 private $revisionIDs;
12 private $revisionPHIDs;
13 private $commitPHIDs;
14 private $hasRevision;
15
16 private $needChangesets = false;
17 private $needProperties;
18
19 public function withIDs(array $ids) {
20 $this->ids = $ids;
21 return $this;
22 }
23
24 public function withPHIDs(array $phids) {
25 $this->phids = $phids;
26 return $this;
27 }
28
29 public function withRevisionIDs(array $revision_ids) {
30 $this->revisionIDs = $revision_ids;
31 return $this;
32 }
33
34 public function withRevisionPHIDs(array $revision_phids) {
35 $this->revisionPHIDs = $revision_phids;
36 return $this;
37 }
38
39 public function withCommitPHIDs(array $phids) {
40 $this->commitPHIDs = $phids;
41 return $this;
42 }
43
44 public function withHasRevision($has_revision) {
45 $this->hasRevision = $has_revision;
46 return $this;
47 }
48
49 public function needChangesets($bool) {
50 $this->needChangesets = $bool;
51 return $this;
52 }
53
54 public function needProperties($need_properties) {
55 $this->needProperties = $need_properties;
56 return $this;
57 }
58
59 public function newResultObject() {
60 return new DifferentialDiff();
61 }
62
63 protected function willFilterPage(array $diffs) {
64 $revision_ids = array_filter(mpull($diffs, 'getRevisionID'));
65
66 $revisions = array();
67 if ($revision_ids) {
68 $revisions = id(new DifferentialRevisionQuery())
69 ->setViewer($this->getViewer())
70 ->withIDs($revision_ids)
71 ->execute();
72 }
73
74 foreach ($diffs as $key => $diff) {
75 if (!$diff->getRevisionID()) {
76 continue;
77 }
78
79 $revision = idx($revisions, $diff->getRevisionID());
80 if ($revision) {
81 $diff->attachRevision($revision);
82 continue;
83 }
84
85 unset($diffs[$key]);
86 }
87
88
89 if ($diffs && $this->needChangesets) {
90 $diffs = $this->loadChangesets($diffs);
91 }
92
93 return $diffs;
94 }
95
96 protected function didFilterPage(array $diffs) {
97 if ($this->needProperties) {
98 $properties = id(new DifferentialDiffProperty())->loadAllWhere(
99 'diffID IN (%Ld)',
100 mpull($diffs, 'getID'));
101
102 $properties = mgroup($properties, 'getDiffID');
103 foreach ($diffs as $diff) {
104 $map = idx($properties, $diff->getID(), array());
105 $map = mpull($map, 'getData', 'getName');
106 $diff->attachDiffProperties($map);
107 }
108 }
109
110 return $diffs;
111 }
112
113 private function loadChangesets(array $diffs) {
114 id(new DifferentialChangesetQuery())
115 ->setViewer($this->getViewer())
116 ->setParentQuery($this)
117 ->withDiffs($diffs)
118 ->needAttachToDiffs(true)
119 ->needHunks(true)
120 ->execute();
121
122 return $diffs;
123 }
124
125 protected function buildWhereClauseParts(AphrontDatabaseConnection $conn) {
126 $where = parent::buildWhereClauseParts($conn);
127
128 if ($this->ids !== null) {
129 $where[] = qsprintf(
130 $conn,
131 'id IN (%Ld)',
132 $this->ids);
133 }
134
135 if ($this->phids !== null) {
136 $where[] = qsprintf(
137 $conn,
138 'phid IN (%Ls)',
139 $this->phids);
140 }
141
142 if ($this->revisionIDs !== null) {
143 $where[] = qsprintf(
144 $conn,
145 'revisionID IN (%Ld)',
146 $this->revisionIDs);
147 }
148
149 if ($this->commitPHIDs !== null) {
150 $where[] = qsprintf(
151 $conn,
152 'commitPHID IN (%Ls)',
153 $this->commitPHIDs);
154 }
155
156 if ($this->hasRevision !== null) {
157 if ($this->hasRevision) {
158 $where[] = qsprintf(
159 $conn,
160 'revisionID IS NOT NULL');
161 } else {
162 $where[] = qsprintf(
163 $conn,
164 'revisionID IS NULL');
165 }
166 }
167
168 if ($this->revisionPHIDs !== null) {
169 $viewer = $this->getViewer();
170
171 $revisions = id(new DifferentialRevisionQuery())
172 ->setViewer($viewer)
173 ->setParentQuery($this)
174 ->withPHIDs($this->revisionPHIDs)
175 ->execute();
176 $revision_ids = mpull($revisions, 'getID');
177 if (!$revision_ids) {
178 throw new PhabricatorEmptyQueryException();
179 }
180
181 $where[] = qsprintf(
182 $conn,
183 'revisionID IN (%Ls)',
184 $revision_ids);
185 }
186
187 return $where;
188 }
189
190 public function getQueryApplicationClass() {
191 return PhabricatorDifferentialApplication::class;
192 }
193
194}