Skip to content

Commit 5703f3c

Browse files
committed
[console] Normalize Rector changed file lists
1 parent 37b5ba1 commit 5703f3c

2 files changed

Lines changed: 106 additions & 2 deletions

File tree

src/Console/Logger/Processor/CommandOutputProcessor.php

Lines changed: 50 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,7 @@ private function decodeStructuredOutput(string $content): mixed
9898
}
9999

100100
try {
101-
return json_decode($trimmedContent, true);
101+
return $this->normalizeStructuredPayload(json_decode($trimmedContent, true));
102102
} catch (JsonException) {
103103
}
104104

@@ -140,7 +140,7 @@ private function decodeJsonDocumentStream(string $content): ?array
140140
}
141141

142142
try {
143-
$decodedDocuments[] = json_decode($document, true);
143+
$decodedDocuments[] = $this->normalizeStructuredPayload(json_decode($document, true));
144144
} catch (JsonException) {
145145
return null;
146146
}
@@ -219,4 +219,52 @@ private function consumeJsonDocument(string $content, int &$offset): ?string
219219

220220
return null;
221221
}
222+
223+
/**
224+
* Normalizes decoded structured payloads produced by wrapped tooling.
225+
*
226+
* @param mixed $payload the decoded payload
227+
*
228+
* @return mixed the normalized payload
229+
*/
230+
private function normalizeStructuredPayload(mixed $payload): mixed
231+
{
232+
if (! \is_array($payload)) {
233+
return $payload;
234+
}
235+
236+
if (! isset($payload['totals']) || ! \is_array($payload['totals'])) {
237+
return $payload;
238+
}
239+
240+
$changedFilesTotal = $payload['totals']['changed_files'] ?? null;
241+
242+
if (! \is_int($changedFilesTotal)) {
243+
return $payload;
244+
}
245+
246+
if (0 === $changedFilesTotal) {
247+
$payload['changed_files'] = [];
248+
249+
return $payload;
250+
}
251+
252+
if (! isset($payload['file_diffs']) || ! \is_array($payload['file_diffs'])) {
253+
return $payload;
254+
}
255+
256+
$changedFiles = [];
257+
258+
foreach ($payload['file_diffs'] as $fileDiff) {
259+
if (! \is_array($fileDiff) || ! isset($fileDiff['file']) || ! \is_string($fileDiff['file'])) {
260+
continue;
261+
}
262+
263+
$changedFiles[$fileDiff['file']] = $fileDiff['file'];
264+
}
265+
266+
$payload['changed_files'] = array_values($changedFiles);
267+
268+
return $payload;
269+
}
222270
}

tests/Console/Logger/Processor/CommandOutputProcessorTest.php

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,62 @@ public function processWillDecodeSingleJsonBufferedOutput(): void
7171
], $context['output']);
7272
}
7373

74+
/**
75+
* @return void
76+
*/
77+
#[Test]
78+
public function processWillNormalizeRectorChangedFilesWhenNoFilesActuallyChanged(): void
79+
{
80+
$processor = new CommandOutputProcessor();
81+
$output = new BufferedOutput();
82+
$output->write(
83+
"{\"totals\":{\"changed_files\":0,\"errors\":0},\"changed_files\":[\"src/Foo.php\",\"src/Bar.php\"]}\n"
84+
);
85+
86+
$context = $processor->process([
87+
'output' => $output,
88+
]);
89+
90+
self::assertSame([
91+
'totals' => [
92+
'changed_files' => 0,
93+
'errors' => 0,
94+
],
95+
'changed_files' => [],
96+
], $context['output']);
97+
}
98+
99+
/**
100+
* @return void
101+
*/
102+
#[Test]
103+
public function processWillNormalizeRectorChangedFilesUsingOnlyDiffEntries(): void
104+
{
105+
$processor = new CommandOutputProcessor();
106+
$output = new BufferedOutput();
107+
$output->write(
108+
"{\"totals\":{\"changed_files\":1,\"errors\":0},\"changed_files\":[\"src/Foo.php\",\"src/Bar.php\"],\"file_diffs\":[{\"file\":\"src/Bar.php\",\"diff\":\"@@\"}]}\n"
109+
);
110+
111+
$context = $processor->process([
112+
'output' => $output,
113+
]);
114+
115+
self::assertSame([
116+
'totals' => [
117+
'changed_files' => 1,
118+
'errors' => 0,
119+
],
120+
'changed_files' => ['src/Bar.php'],
121+
'file_diffs' => [
122+
[
123+
'file' => 'src/Bar.php',
124+
'diff' => '@@',
125+
],
126+
],
127+
], $context['output']);
128+
}
129+
74130
/**
75131
* @return void
76132
*/

0 commit comments

Comments
 (0)