|
#!/usr/bin/php |
|
<?php |
|
$gerritId = null; |
|
$showUsage = count($argv) < 2; |
|
$patchesDirectory = __DIR__ . '/../patches/'; |
|
|
|
if (!$showUsage) { |
|
$gerritId = (int)$argv[1]; |
|
} |
|
|
|
if ($showUsage || empty($gerritId)) { |
|
$usage = [ |
|
'NAME', |
|
"\t" . basename($argv[0]) . ' -- downloads a patch from Gerrit', |
|
'', |
|
'SYNOPSIS', |
|
"\t" . basename($argv[0] . ' <id>'), |
|
'', |
|
'DESCRIPTION', |
|
"\tThis will download the latest patchset from", |
|
"\thttps://review.typo3.org/c/Packages/TYPO3.CMS/+/id then", |
|
"\tsplit it for the various typo3/cms-* packages and update", |
|
"\tyour composer.json", |
|
]; |
|
echo implode("\n", $usage) . "\n\n"; |
|
exit(1); |
|
} |
|
|
|
$change = file_get_contents('https://review.typo3.org/changes/' . $gerritId); |
|
// Fix garbage at the beginning |
|
if (strpos($change, ")]}'") === 0) { |
|
$change = json_decode(trim(substr($change, 4)), true); |
|
} |
|
if (empty($change['subject'])) { |
|
echo "Change $gerritId was not found.\n"; |
|
exit(2); |
|
} |
|
|
|
$subject = preg_replace('/^\\[.*?\] /', '', $change['subject']); |
|
echo "Subject is '$subject'\n"; |
|
|
|
$patch = base64_decode(file_get_contents('https://review.typo3.org/changes/' . $gerritId . '/revisions/current/patch')); |
|
|
|
$patchMessage = null; |
|
$patches = []; |
|
do { |
|
$nextPatchPos = strpos($patch, 'diff --git', 1); |
|
if ($nextPatchPos === false) { |
|
$buffer = $patch; |
|
$patch = ''; |
|
} else { |
|
$buffer = substr($patch, 0, $nextPatchPos); |
|
$patch = substr($patch, $nextPatchPos); |
|
} |
|
|
|
if ($patchMessage === null) { |
|
$patchMessage = $buffer; |
|
continue; |
|
} |
|
|
|
if (!preg_match('#^diff --git a/typo3/sysext/([^/]+)/([^ ]+)#', $buffer, $matches)) { |
|
// TODO: continue as well if patching a Test file? |
|
continue; |
|
} |
|
$sysext = $matches[1]; |
|
$package = 'typo3/cms-' . str_replace('_', '-', $sysext); |
|
if (!isset($patches[$package])) { |
|
$patches[$package] = [$patchMessage]; |
|
} |
|
|
|
// Fix the patch |
|
$prefix = 'typo3/sysext/' . $matches[1]; |
|
$file = $matches[2]; |
|
$buffer = str_replace(' a/' . $prefix . '/' . $file, ' a/' . $file, $buffer); |
|
$buffer = str_replace(' b/' . $prefix . '/' . $file, ' b/' . $file, $buffer); |
|
|
|
$patches[$package][] = $buffer; |
|
} while (!empty($patch)); |
|
|
|
$composerChanges = []; |
|
foreach ($patches as $package => $chunks) { |
|
$content = implode('', $chunks); |
|
$patchFileName = str_replace('/', '-', $package) . '-' . $gerritId . '.patch'; |
|
file_put_contents($patchesDirectory . $patchFileName, $content); |
|
echo "Created patch '" . $patchesDirectory . $patchFileName . "'\n"; |
|
|
|
$composerChanges[$package] = [ |
|
$subject => 'patches/' . $patchFileName, |
|
]; |
|
} |
|
|
|
echo "\nPlease extend your composer.json with following block:\n\n"; |
|
echo json_encode(['extra' => ['patches' => $composerChanges]], JSON_UNESCAPED_SLASHES | JSON_PRETTY_PRINT); |
|
echo "\n\nthen run \"composer update --lock\".\n\n"; |
You should suggest
composer update --lock
instead since you don't want to update all packages.