mirror of
https://we.phorge.it/source/phorge.git
synced 2024-11-09 16:32:39 +01:00
Add options to include patches inline or attached for Diffusion commit emails
Summary: See D818 for an older attempt at this. Support code has matured to the point where the patch is pretty straightforward. @tido, this was a long-standing request from Aditya back in the day. Test Plan: Used `reparse.php --herald` to send myself a bunch of emails with various patch configurations. Confirmed that limits are respected, reasonable errors arise when they're violated, etc. (Timeout is a little funky but that's out of scope here, I think.) Reviewers: btrahan Reviewed By: btrahan CC: tido, aran Maniphest Tasks: T456 Differential Revision: https://secure.phabricator.com/D2967
This commit is contained in:
parent
2b690372de
commit
9574b91e55
2 changed files with 119 additions and 2 deletions
|
@ -396,6 +396,26 @@ return array(
|
|||
// affects Diffusion.
|
||||
'metamta.diffusion.reply-handler' => 'PhabricatorAuditReplyHandler',
|
||||
|
||||
// Set this to true if you want patches to be attached to commit notifications
|
||||
// from Diffusion. This won't work with SendGrid.
|
||||
'metamta.diffusion.attach-patches' => false,
|
||||
|
||||
// To include patches in Diffusion email bodies, set this to a positive
|
||||
// integer. Patches will be inlined if they are at most that many lines.
|
||||
// By default, patches are not inlined.
|
||||
'metamta.diffusion.inline-patches' => 0,
|
||||
|
||||
// If you've enabled attached patches or inline patches for commit emails, you
|
||||
// can establish a hard byte limit on their size. You should generally set
|
||||
// reasonable byte and time limits (defaults are 1MB and 60 seconds) to avoid
|
||||
// sending ridiculously enormous email for changes like "importing an external
|
||||
// library" or "accidentally committed this full-length movie as text".
|
||||
'metamta.diffusion.byte-limit' => 1024 * 1024,
|
||||
|
||||
// If you've enabled attached patches or inline patches for commit emails, you
|
||||
// can establish a hard time limit on generating them.
|
||||
'metamta.diffusion.time-limit' => 60,
|
||||
|
||||
// Prefix prepended to mail sent by Package.
|
||||
'metamta.package.subject-prefix' => '[Package]',
|
||||
|
||||
|
|
|
@ -130,6 +130,9 @@ final class PhabricatorRepositoryCommitHeraldWorker
|
|||
" ".$reply_instructions."\n";
|
||||
}
|
||||
|
||||
$template = new PhabricatorMetaMTAMail();
|
||||
|
||||
$inline_patch_text = $this->buildPatch($template, $repository, $commit);
|
||||
|
||||
$body = <<<EOBODY
|
||||
DESCRIPTION
|
||||
|
@ -149,7 +152,7 @@ MANAGE HERALD COMMIT RULES
|
|||
|
||||
WHY DID I GET THIS EMAIL?
|
||||
{$why_uri}
|
||||
|
||||
{$inline_patch_text}
|
||||
EOBODY;
|
||||
|
||||
$prefix = PhabricatorEnv::getEnvConfig('metamta.diffusion.subject-prefix');
|
||||
|
@ -159,7 +162,6 @@ EOBODY;
|
|||
$commit);
|
||||
list($thread_id, $thread_topic) = $threading;
|
||||
|
||||
$template = new PhabricatorMetaMTAMail();
|
||||
$template->setRelatedPHID($commit->getPHID());
|
||||
$template->setSubject("{$commit_name}: {$name}");
|
||||
$template->setSubjectPrefix($prefix);
|
||||
|
@ -314,4 +316,99 @@ EOBODY;
|
|||
$publisher->publish();
|
||||
}
|
||||
|
||||
private function buildPatch(
|
||||
PhabricatorMetaMTAMail $template,
|
||||
PhabricatorRepository $repository,
|
||||
PhabricatorRepositoryCommit $commit) {
|
||||
|
||||
$attach_key = 'metamta.diffusion.attach-patches';
|
||||
$inline_key = 'metamta.diffusion.inline-patches';
|
||||
|
||||
$attach_patches = PhabricatorEnv::getEnvConfig($attach_key);
|
||||
$inline_patches = PhabricatorEnv::getEnvConfig($inline_key);
|
||||
|
||||
if (!$attach_patches && !$inline_patches) {
|
||||
return;
|
||||
}
|
||||
|
||||
$encoding = $repository->getDetail('encoding', 'utf-8');
|
||||
|
||||
$result = null;
|
||||
$patch_error = null;
|
||||
|
||||
try {
|
||||
$raw_patch = $this->loadRawPatchText($repository, $commit);
|
||||
if ($attach_patches) {
|
||||
$commit_name = $repository->formatCommitName(
|
||||
$commit->getCommitIdentifier());
|
||||
|
||||
$template->addAttachment(
|
||||
new PhabricatorMetaMTAAttachment(
|
||||
$raw_patch,
|
||||
$commit_name.'.patch',
|
||||
'text/x-patch; charset='.$encoding));
|
||||
}
|
||||
} catch (Exception $ex) {
|
||||
phlog($ex);
|
||||
$patch_error = 'Unable to generate: '.$ex->getMessage();
|
||||
}
|
||||
|
||||
if ($patch_error) {
|
||||
$result = $patch_error;
|
||||
} else if ($inline_patches) {
|
||||
$len = substr_count($raw_patch, "\n");
|
||||
if ($len <= $inline_patches) {
|
||||
// We send email as utf8, so we need to convert the text to utf8 if
|
||||
// we can.
|
||||
if (strtolower($encoding) != 'utf-8' &&
|
||||
function_exists('mb_convert_encoding')) {
|
||||
$raw_patch = mb_convert_encoding($raw_patch, 'utf-8', $encoding);
|
||||
}
|
||||
$result = phutil_utf8ize($raw_patch);
|
||||
}
|
||||
}
|
||||
|
||||
if ($result) {
|
||||
$result = "\nPATCH\n\n{$result}\n";
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
private function loadRawPatchText(
|
||||
PhabricatorRepository $repository,
|
||||
PhabricatorRepositoryCommit $commit) {
|
||||
|
||||
$drequest = DiffusionRequest::newFromDictionary(
|
||||
array(
|
||||
'repository' => $repository,
|
||||
'commit' => $commit->getCommitIdentifier(),
|
||||
));
|
||||
|
||||
$raw_query = DiffusionRawDiffQuery::newFromDiffusionRequest($drequest);
|
||||
$raw_query->setLinesOfContext(3);
|
||||
|
||||
$time_key = 'metamta.diffusion.time-limit';
|
||||
$byte_key = 'metamta.diffusion.byte-limit';
|
||||
$time_limit = PhabricatorEnv::getEnvConfig($time_key);
|
||||
$byte_limit = PhabricatorEnv::getEnvConfig($byte_key);
|
||||
|
||||
if ($time_limit) {
|
||||
$raw_query->setTimeout($time_limit);
|
||||
}
|
||||
|
||||
$raw_diff = $raw_query->loadRawDiff();
|
||||
|
||||
$size = strlen($raw_diff);
|
||||
if ($byte_limit && $size > $byte_limit) {
|
||||
$pretty_size = phabricator_format_bytes($size);
|
||||
$pretty_limit = phabricator_format_bytes($byte_limit);
|
||||
throw new Exception(
|
||||
"Patch size of {$pretty_size} exceeds configured byte size limit of ".
|
||||
"{$pretty_limit}.");
|
||||
}
|
||||
|
||||
return $raw_diff;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue