Find this useful? Enter your email to receive occasional updates for securing PHP code.
Signing you up...
Thank you for signing up!
PHP Decode
<?php final class PhabricatorMetaMTAMail extends PhabricatorMetaMTADAO implements Phabric..
Decoded Output download
<?php
final class PhabricatorMetaMTAMail extends PhabricatorMetaMTADAO implements PhabricatorPolicyInterface, PhabricatorDestructibleInterface { const RETRY_DELAY = 5; protected $actorPHID; protected $parameters = array(); protected $status; protected $message; protected $relatedPHID; private $recipientExpansionMap; private $routingMap; public function __construct() { $this->status = PhabricatorMailOutboundStatus::STATUS_QUEUE; $this->parameters = array("sensitive" => true, "mustEncrypt" => false); parent::__construct(); } protected function getConfiguration() { return array(self::CONFIG_AUX_PHID => true, self::CONFIG_SERIALIZATION => array("parameters" => self::SERIALIZATION_JSON), self::CONFIG_COLUMN_SCHEMA => array("actorPHID" => "phid?", "status" => "text32", "relatedPHID" => "phid?", "message" => "text?"), self::CONFIG_KEY_SCHEMA => array("status" => array("columns" => array("status")), "key_actorPHID" => array("columns" => array("actorPHID")), "relatedPHID" => array("columns" => array("relatedPHID")), "key_created" => array("columns" => array("dateCreated")))) + parent::getConfiguration(); } public function generatePHID() { return PhabricatorPHID::generateNewPHID(PhabricatorMetaMTAMailPHIDType::TYPECONST); } protected function setParam($param, $value) { $this->parameters[$param] = $value; return $this; } protected function getParam($param, $default = null) { if (!is_array($this->parameters)) { $this->parameters = array(); } return idx($this->parameters, $param, $default); } public function setMailTags(array $tags) { $this->setParam("mailtags", array_unique($tags)); return $this; } public function getMailTags() { return $this->getParam("mailtags", array()); } public function setParentMessageID($id) { $this->setParam("parent-message-id", $id); return $this; } public function getParentMessageID() { return $this->getParam("parent-message-id"); } public function getSubject() { return $this->getParam("subject"); } public function addTos(array $phids) { $phids = array_unique($phids); $this->setParam("to", $phids); return $this; } public function addRawTos(array $raw_email) { foreach ($raw_email as $key => $email) { $object = new PhutilEmailAddress($email); $raw_email[$key] = $object->getAddress(); } $this->setParam("raw-to", $raw_email); return $this; } public function addCCs(array $phids) { $phids = array_unique($phids); $this->setParam("cc", $phids); return $this; } public function setExcludeMailRecipientPHIDs(array $exclude) { $this->setParam("exclude", $exclude); return $this; } private function getExcludeMailRecipientPHIDs() { return $this->getParam("exclude", array()); } public function setMutedPHIDs(array $muted) { $this->setParam("muted", $muted); return $this; } private function getMutedPHIDs() { return $this->getParam("muted", array()); } public function setForceHeraldMailRecipientPHIDs(array $force) { $this->setParam("herald-force-recipients", $force); return $this; } private function getForceHeraldMailRecipientPHIDs() { return $this->getParam("herald-force-recipients", array()); } public function addPHIDHeaders($name, array $phids) { $phids = array_unique($phids); foreach ($phids as $phid) { $this->addHeader($name, "<" . $phid . ">"); } return $this; } public function addHeader($name, $value) { $this->parameters["headers"][] = array($name, $value); return $this; } public function getHeaders() { return $this->getParam("headers", array()); } public function addAttachment(PhabricatorMailAttachment $attachment) { $this->parameters["attachments"][] = $attachment->toDictionary(); return $this; } public function getAttachments() { $dicts = $this->getParam("attachments", array()); $result = array(); foreach ($dicts as $dict) { $result[] = PhabricatorMailAttachment::newFromDictionary($dict); } return $result; } public function getAttachmentFilePHIDs() { $file_phids = array(); $dictionaries = $this->getParam("attachments"); if ($dictionaries) { foreach ($dictionaries as $dictionary) { $file_phid = idx($dictionary, "filePHID"); if ($file_phid) { $file_phids[] = $file_phid; } } } return $file_phids; } public function loadAttachedFiles(PhabricatorUser $viewer) { $file_phids = $this->getAttachmentFilePHIDs(); if (!$file_phids) { return array(); } return id(new PhabricatorFileQuery())->setViewer($viewer)->withPHIDs($file_phids)->execute(); } public function setAttachments(array $attachments) { assert_instances_of($attachments, "PhabricatorMailAttachment"); $this->setParam("attachments", mpull($attachments, "toDictionary")); return $this; } public function setFrom($from) { $this->setParam("from", $from); $this->setActorPHID($from); return $this; } public function getFrom() { return $this->getParam("from"); } public function setRawFrom($raw_email, $raw_name) { $this->setParam("raw-from", array($raw_email, $raw_name)); return $this; } public function getRawFrom() { return $this->getParam("raw-from"); } public function setReplyTo($reply_to) { $this->setParam("reply-to", $reply_to); return $this; } public function getReplyTo() { return $this->getParam("reply-to"); } public function setSubject($subject) { $this->setParam("subject", $subject); return $this; } public function setSubjectPrefix($prefix) { $this->setParam("subject-prefix", $prefix); return $this; } public function getSubjectPrefix() { return $this->getParam("subject-prefix"); } public function setVarySubjectPrefix($prefix) { $this->setParam("vary-subject-prefix", $prefix); return $this; } public function getVarySubjectPrefix() { return $this->getParam("vary-subject-prefix"); } public function setBody($body) { $this->setParam("body", $body); return $this; } public function setSensitiveContent($bool) { $this->setParam("sensitive", $bool); return $this; } public function hasSensitiveContent() { return $this->getParam("sensitive", true); } public function setMustEncrypt($bool) { return $this->setParam("mustEncrypt", $bool); } public function getMustEncrypt() { return $this->getParam("mustEncrypt", false); } public function setMustEncryptURI($uri) { return $this->setParam("mustEncrypt.uri", $uri); } public function getMustEncryptURI() { return $this->getParam("mustEncrypt.uri"); } public function setMustEncryptSubject($subject) { return $this->setParam("mustEncrypt.subject", $subject); } public function getMustEncryptSubject() { return $this->getParam("mustEncrypt.subject"); } public function setMustEncryptReasons(array $reasons) { return $this->setParam("mustEncryptReasons", $reasons); } public function getMustEncryptReasons() { return $this->getParam("mustEncryptReasons", array()); } public function setMailStamps(array $stamps) { return $this->setParam("stamps", $stamps); } public function getMailStamps() { return $this->getParam("stamps", array()); } public function setMailStampMetadata($metadata) { return $this->setParam("stampMetadata", $metadata); } public function getMailStampMetadata() { return $this->getParam("stampMetadata", array()); } public function getMailerKey() { return $this->getParam("mailer.key"); } public function setTryMailers(array $mailers) { return $this->setParam("mailers.try", $mailers); } public function setHTMLBody($html) { $this->setParam("html-body", $html); return $this; } public function getBody() { return $this->getParam("body"); } public function getHTMLBody() { return $this->getParam("html-body"); } public function setIsErrorEmail($is_error) { $this->setParam("is-error", $is_error); return $this; } public function getIsErrorEmail() { return $this->getParam("is-error", false); } public function getToPHIDs() { return $this->getParam("to", array()); } public function getRawToAddresses() { return $this->getParam("raw-to", array()); } public function getCcPHIDs() { return $this->getParam("cc", array()); } public function setMessageType($message_type) { return $this->setParam("message.type", $message_type); } public function getMessageType() { return $this->getParam("message.type", PhabricatorMailEmailMessage::MESSAGETYPE); } public function setForceDelivery($force) { $this->setParam("force", $force); return $this; } public function getForceDelivery() { return $this->getParam("force", false); } public function setIsBulk($is_bulk) { $this->setParam("is-bulk", $is_bulk); return $this; } public function getIsBulk() { return $this->getParam("is-bulk"); } public function setThreadID($thread_id, $is_first_message = false) { $this->setParam("thread-id", $thread_id); $this->setParam("is-first-message", $is_first_message); return $this; } public function getThreadID() { return $this->getParam("thread-id"); } public function getIsFirstMessage() { return (bool) $this->getParam("is-first-message"); } public function saveAndSend() { return $this->save(); } public function save() { if ($this->getID()) { return parent::save(); } $this->openTransaction(); $result = parent::save(); $editor = new PhabricatorEdgeEditor(); $edge_type = PhabricatorMetaMTAMailHasRecipientEdgeType::EDGECONST; $recipient_phids = array_merge($this->getToPHIDs(), $this->getCcPHIDs()); $expanded_phids = $this->expandRecipients($recipient_phids); $all_phids = array_unique(array_merge($recipient_phids, $expanded_phids)); foreach ($all_phids as $curr_phid) { $editor->addEdge($this->getPHID(), $edge_type, $curr_phid); } $editor->save(); $this->saveTransaction(); $mailer_task = PhabricatorWorker::scheduleTask("PhabricatorMetaMTAWorker", $this->getID(), array("priority" => PhabricatorWorker::PRIORITY_ALERTS)); return $result; } public function sendNow() { if ($this->getStatus() != PhabricatorMailOutboundStatus::STATUS_QUEUE) { throw new Exception(pht("Trying to send an already-sent mail!")); } $mailers = self::newMailers(array("outbound" => true, "media" => array($this->getMessageType()))); $try_mailers = $this->getParam("mailers.try"); if ($try_mailers) { $mailers = mpull($mailers, null, "getKey"); $mailers = array_select_keys($mailers, $try_mailers); } return $this->sendWithMailers($mailers); } public static function newMailers(array $constraints) { PhutilTypeSpec::checkMap($constraints, array("types" => "optional list<string>", "inbound" => "optional bool", "outbound" => "optional bool", "media" => "optional list<string>")); $mailers = array(); $config = PhabricatorEnv::getEnvConfig("cluster.mailers"); $adapters = PhabricatorMailAdapter::getAllAdapters(); $next_priority = -1; foreach ($config as $spec) { $type = $spec["type"]; if (!isset($adapters[$type])) { throw new Exception(pht("Unknown mailer ("%s")!", $type)); } $key = $spec["key"]; $mailer = id(clone $adapters[$type])->setKey($key); $priority = idx($spec, "priority"); if (!$priority) { $priority = $next_priority; $next_priority--; } $mailer->setPriority($priority); $defaults = $mailer->newDefaultOptions(); $options = idx($spec, "options", array()) + $defaults; $mailer->setOptions($options); $mailer->setSupportsInbound(idx($spec, "inbound", true)); $mailer->setSupportsOutbound(idx($spec, "outbound", true)); $media = idx($spec, "media"); if ($media !== null) { $mailer->setMedia($media); } $mailers[] = $mailer; } if (isset($constraints["types"])) { $types = $constraints["types"]; $types = array_fuse($types); foreach ($mailers as $key => $mailer) { $mailer_type = $mailer->getAdapterType(); if (!isset($types[$mailer_type])) { unset($mailers[$key]); } } } if (!empty($constraints["inbound"])) { foreach ($mailers as $key => $mailer) { if (!$mailer->getSupportsInbound()) { unset($mailers[$key]); } } } if (!empty($constraints["outbound"])) { foreach ($mailers as $key => $mailer) { if (!$mailer->getSupportsOutbound()) { unset($mailers[$key]); } } } if (!empty($constraints["media"])) { foreach ($mailers as $key => $mailer) { $supports_any = false; foreach ($constraints["media"] as $medium) { if ($mailer->supportsMessageType($medium)) { $supports_any = true; break; } } if (!$supports_any) { unset($mailers[$key]); } } } $sorted = array(); $groups = mgroup($mailers, "getPriority"); krsort($groups); foreach ($groups as $group) { shuffle($group); foreach ($group as $mailer) { $sorted[] = $mailer; } } return $sorted; } public function sendWithMailers(array $mailers) { if (!$mailers) { $any_mailers = self::newMailers(array()); if ($any_mailers) { $void_message = pht("No configured mailers support sending outbound mail."); } else { $void_message = pht("No mailers are configured."); } return $this->setStatus(PhabricatorMailOutboundStatus::STATUS_VOID)->setMessage($void_message)->save(); } $actors = $this->loadAllActors(); $target_phid = head($this->getToPHIDs()); if (!$target_phid) { $target_phid = head($this->getCcPHIDs()); } $preferences = $this->loadPreferences($target_phid); $viewer = PhabricatorUser::getOmnipotentUser(); $files = $this->loadAttachedFiles($viewer); foreach ($files as $file) { $file->attachToObject($this->getPHID()); } $type_map = PhabricatorMailExternalMessage::getAllMessageTypes(); $type = idx($type_map, $this->getMessageType()); if (!$type) { throw new Exception(pht("Unable to send message with unknown message type "%s".", $type)); } $exceptions = array(); foreach ($mailers as $mailer) { try { $message = $type->newMailMessageEngine()->setMailer($mailer)->setMail($this)->setActors($actors)->setPreferences($preferences)->newMessage($mailer); } catch (Exception $ex) { $exceptions[] = $ex; continue; } if (!$message) { return $this->setStatus(PhabricatorMailOutboundStatus::STATUS_VOID)->save(); } try { $mailer->sendMessage($message); } catch (PhabricatorMetaMTAPermanentFailureException $ex) { $this->setStatus(PhabricatorMailOutboundStatus::STATUS_FAIL)->setMessage($ex->getMessage())->save(); throw $ex; } catch (Exception $ex) { $exceptions[] = $ex; continue; } $mailer_key = $mailer->getKey(); if ($mailer_key !== null) { $this->setParam("mailer.key", $mailer_key); } $actor_list = array(); foreach ($actors as $actor) { $actor_list[$actor->getPHID()] = array("deliverable" => $actor->isDeliverable(), "reasons" => $actor->getDeliverabilityReasons()); } $this->setParam("actors.sent", $actor_list); $this->setParam("routing.sent", $this->getParam("routing")); $this->setParam("routingmap.sent", $this->getRoutingRuleMap()); return $this->setStatus(PhabricatorMailOutboundStatus::STATUS_SENT)->save(); } $messages = array(); foreach ($exceptions as $ex) { $messages[] = $ex->getMessage(); } $messages = implode("
", $messages); $this->setMessage($messages)->save(); if (count($exceptions) === 1) { throw head($exceptions); } throw new PhutilAggregateException(pht("Encountered multiple exceptions while transmitting mail."), $exceptions); } public static function shouldMailEachRecipient() { return PhabricatorEnv::getEnvConfig("metamta.one-mail-per-recipient"); } public function buildRecipientList() { $actors = $this->loadAllActors(); $actors = $this->filterDeliverableActors($actors); return mpull($actors, "getPHID"); } public function loadAllActors() { $actor_phids = $this->getExpandedRecipientPHIDs(); return $this->loadActors($actor_phids); } public function getExpandedRecipientPHIDs() { $actor_phids = $this->getAllActorPHIDs(); return $this->expandRecipients($actor_phids); } private function getAllActorPHIDs() { return array_merge(array($this->getParam("from")), $this->getToPHIDs(), $this->getCcPHIDs()); } public function expandRecipients(array $phids) { if ($this->recipientExpansionMap === null) { $all_phids = $this->getAllActorPHIDs(); $this->recipientExpansionMap = id(new PhabricatorMetaMTAMemberQuery())->setViewer(PhabricatorUser::getOmnipotentUser())->withPHIDs($all_phids)->execute(); } $results = array(); foreach ($phids as $phid) { foreach ($this->recipientExpansionMap[$phid] as $recipient_phid) { $results[$recipient_phid] = $recipient_phid; } } return array_keys($results); } private function filterDeliverableActors(array $actors) { assert_instances_of($actors, "PhabricatorMetaMTAActor"); $deliverable_actors = array(); foreach ($actors as $phid => $actor) { if ($actor->isDeliverable()) { $deliverable_actors[$phid] = $actor; } } return $deliverable_actors; } private function loadActors(array $actor_phids) { $actor_phids = array_filter($actor_phids); $viewer = PhabricatorUser::getOmnipotentUser(); $actors = id(new PhabricatorMetaMTAActorQuery())->setViewer($viewer)->withPHIDs($actor_phids)->execute(); if (!$actors) { return array(); } if ($this->getForceDelivery()) { foreach ($actors as $actor) { $actor->setDeliverable(PhabricatorMetaMTAActor::REASON_FORCE); } return $actors; } foreach ($this->getExcludeMailRecipientPHIDs() as $phid) { $actor = idx($actors, $phid); if (!$actor) { continue; } $actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_RESPONSE); } $deliverable = array(); foreach ($actors as $phid => $actor) { if ($actor->isDeliverable()) { $deliverable[] = $phid; } } foreach ($this->getMutedPHIDs() as $muted_phid) { $muted_actor = idx($actors, $muted_phid); if (!$muted_actor) { continue; } $muted_actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_MUTED); } $from_phid = $this->getParam("from"); $from_actor = idx($actors, $from_phid); if ($from_actor) { $from_user = id(new PhabricatorPeopleQuery())->setViewer($viewer)->withPHIDs(array($from_phid))->needUserSettings(true)->execute(); $from_user = head($from_user); if ($from_user) { $pref_key = PhabricatorEmailSelfActionsSetting::SETTINGKEY; $exclude_self = $from_user->getUserSetting($pref_key); if ($exclude_self) { $from_actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_SELF); } } } $all_prefs = id(new PhabricatorUserPreferencesQuery())->setViewer(PhabricatorUser::getOmnipotentUser())->withUserPHIDs($actor_phids)->needSyntheticPreferences(true)->execute(); $all_prefs = mpull($all_prefs, null, "getUserPHID"); $value_email = PhabricatorEmailTagsSetting::VALUE_EMAIL; $tags = $this->getParam("mailtags"); if ($tags) { foreach ($all_prefs as $phid => $prefs) { $user_mailtags = $prefs->getSettingValue(PhabricatorEmailTagsSetting::SETTINGKEY); $send = false; foreach ($tags as $tag) { if ((int) idx($user_mailtags, $tag, $value_email) == $value_email) { $send = true; break; } } if (!$send) { $actors[$phid]->setUndeliverable(PhabricatorMetaMTAActor::REASON_MAILTAGS); } } } foreach ($deliverable as $phid) { switch ($this->getRoutingRule($phid)) { case PhabricatorMailRoutingRule::ROUTE_AS_NOTIFICATION: $actors[$phid]->setUndeliverable(PhabricatorMetaMTAActor::REASON_ROUTE_AS_NOTIFICATION); break; case PhabricatorMailRoutingRule::ROUTE_AS_MAIL: $actors[$phid]->setDeliverable(PhabricatorMetaMTAActor::REASON_ROUTE_AS_MAIL); break; default: break; } } $force_recipients = $this->getForceHeraldMailRecipientPHIDs(); $force_recipients = array_fuse($force_recipients); if ($force_recipients) { foreach ($deliverable as $phid) { if (isset($force_recipients[$phid])) { $actors[$phid]->setDeliverable(PhabricatorMetaMTAActor::REASON_FORCE_HERALD); } } } foreach ($all_prefs as $phid => $prefs) { $exclude = $prefs->getSettingValue(PhabricatorEmailNotificationsSetting::SETTINGKEY); if ($exclude) { $actors[$phid]->setUndeliverable(PhabricatorMetaMTAActor::REASON_MAIL_DISABLED); } } foreach ($actors as $phid => $actor) { if ($actor->getIsVerified()) { continue; } $actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_UNVERIFIED); } return $actors; } public function getDeliveredHeaders() { return $this->getParam("headers.sent"); } public function setDeliveredHeaders(array $headers) { $headers = $this->flattenHeaders($headers); return $this->setParam("headers.sent", $headers); } public function getUnfilteredHeaders() { $unfiltered = $this->getParam("headers.unfiltered"); if ($unfiltered === null) { return $this->getDeliveredHeaders(); } return $unfiltered; } public function setUnfilteredHeaders(array $headers) { $headers = $this->flattenHeaders($headers); return $this->setParam("headers.unfiltered", $headers); } private function flattenHeaders(array $headers) { assert_instances_of($headers, "PhabricatorMailHeader"); $list = array(); foreach ($list as $header) { $list[] = array($header->getName(), $header->getValue()); } return $list; } public function getDeliveredActors() { return $this->getParam("actors.sent"); } public function getDeliveredRoutingRules() { return $this->getParam("routing.sent"); } public function getDeliveredRoutingMap() { return $this->getParam("routingmap.sent"); } public function getDeliveredBody() { return $this->getParam("body.sent"); } public function setDeliveredBody($body) { return $this->setParam("body.sent", $body); } public function getURI() { return "/mail/detail/" . $this->getID() . "/"; } public function addRoutingRule($routing_rule, $phids, $reason_phid) { $routing = $this->getParam("routing", array()); $routing[] = array("routingRule" => $routing_rule, "phids" => $phids, "reasonPHID" => $reason_phid); $this->setParam("routing", $routing); $this->routingMap = null; return $this; } private function getRoutingRule($phid) { $map = $this->getRoutingRuleMap(); $info = idx($map, $phid, idx($map, "default")); if ($info) { return idx($info, "rule"); } return null; } private function getRoutingRuleMap() { if ($this->routingMap === null) { $map = array(); $routing = $this->getParam("routing", array()); foreach ($routing as $route) { $phids = $route["phids"]; if ($phids === null) { $phids = array("default"); } foreach ($phids as $phid) { $new_rule = $route["routingRule"]; $current_rule = idx($map, $phid); if ($current_rule === null) { $is_stronger = true; } else { $is_stronger = PhabricatorMailRoutingRule::isStrongerThan($new_rule, $current_rule); } if ($is_stronger) { $map[$phid] = array("rule" => $new_rule, "reason" => $route["reasonPHID"]); } } } $this->routingMap = $map; } return $this->routingMap; } private function loadPreferences($target_phid) { $viewer = PhabricatorUser::getOmnipotentUser(); if (self::shouldMailEachRecipient()) { $preferences = id(new PhabricatorUserPreferencesQuery())->setViewer($viewer)->withUserPHIDs(array($target_phid))->needSyntheticPreferences(true)->executeOne(); if ($preferences) { return $preferences; } } return PhabricatorUserPreferences::loadGlobalPreferences($viewer); } public function shouldRenderMailStampsInBody($viewer) { $preferences = $this->loadPreferences($viewer->getPHID()); $value = $preferences->getSettingValue(PhabricatorEmailStampsSetting::SETTINGKEY); return $value == PhabricatorEmailStampsSetting::VALUE_BODY_STAMPS; } public function getCapabilities() { return array(PhabricatorPolicyCapability::CAN_VIEW); } public function getPolicy($capability) { return PhabricatorPolicies::POLICY_NOONE; } public function hasAutomaticCapability($capability, PhabricatorUser $viewer) { $actor_phids = $this->getExpandedRecipientPHIDs(); return in_array($viewer->getPHID(), $actor_phids); } public function describeAutomaticCapability($capability) { return pht("The mail sender and message recipients can always see the mail."); } public function destroyObjectPermanently(PhabricatorDestructionEngine $engine) { $files = $this->loadAttachedFiles($engine->getViewer()); foreach ($files as $file) { $engine->destroyObject($file); } $this->delete(); } } ?>
Did this file decode correctly?
Original Code
<?php
final class PhabricatorMetaMTAMail extends PhabricatorMetaMTADAO implements PhabricatorPolicyInterface, PhabricatorDestructibleInterface { const RETRY_DELAY = 5; protected $actorPHID; protected $parameters = array(); protected $status; protected $message; protected $relatedPHID; private $recipientExpansionMap; private $routingMap; public function __construct() { $this->status = PhabricatorMailOutboundStatus::STATUS_QUEUE; $this->parameters = array("\x73\145\x6e\163\x69\x74\x69\166\145" => true, "\x6d\x75\163\164\105\x6e\143\x72\x79\x70\164" => false); parent::__construct(); } protected function getConfiguration() { return array(self::CONFIG_AUX_PHID => true, self::CONFIG_SERIALIZATION => array("\x70\x61\162\x61\155\145\164\x65\162\x73" => self::SERIALIZATION_JSON), self::CONFIG_COLUMN_SCHEMA => array("\x61\x63\x74\x6f\162\120\110\111\104" => "\160\x68\x69\144\x3f", "\163\x74\x61\x74\165\163" => "\x74\145\x78\164\x33\62", "\162\x65\154\141\x74\145\144\x50\x48\111\104" => "\160\x68\x69\144\77", "\155\x65\x73\x73\x61\x67\x65" => "\x74\x65\x78\x74\77"), self::CONFIG_KEY_SCHEMA => array("\163\x74\x61\x74\165\163" => array("\x63\x6f\x6c\x75\x6d\156\x73" => array("\x73\x74\141\164\x75\163")), "\153\145\171\137\141\x63\164\x6f\162\x50\x48\111\104" => array("\143\157\154\165\x6d\156\163" => array("\x61\143\164\157\162\x50\x48\111\104")), "\162\145\x6c\x61\164\x65\x64\x50\110\111\x44" => array("\143\157\154\165\155\x6e\163" => array("\162\145\x6c\141\164\145\144\120\x48\x49\104")), "\153\145\x79\x5f\x63\x72\x65\141\164\x65\x64" => array("\143\x6f\x6c\x75\x6d\x6e\x73" => array("\x64\141\164\145\103\162\x65\141\164\x65\x64")))) + parent::getConfiguration(); } public function generatePHID() { return PhabricatorPHID::generateNewPHID(PhabricatorMetaMTAMailPHIDType::TYPECONST); } protected function setParam($param, $value) { $this->parameters[$param] = $value; return $this; } protected function getParam($param, $default = null) { if (!is_array($this->parameters)) { $this->parameters = array(); } return idx($this->parameters, $param, $default); } public function setMailTags(array $tags) { $this->setParam("\155\x61\x69\154\164\x61\147\x73", array_unique($tags)); return $this; } public function getMailTags() { return $this->getParam("\x6d\141\151\154\164\x61\x67\x73", array()); } public function setParentMessageID($id) { $this->setParam("\160\x61\x72\145\x6e\x74\55\155\145\163\x73\141\147\145\55\151\144", $id); return $this; } public function getParentMessageID() { return $this->getParam("\160\141\162\x65\x6e\x74\x2d\155\x65\x73\163\x61\147\x65\x2d\151\x64"); } public function getSubject() { return $this->getParam("\163\x75\142\x6a\145\143\164"); } public function addTos(array $phids) { $phids = array_unique($phids); $this->setParam("\x74\x6f", $phids); return $this; } public function addRawTos(array $raw_email) { foreach ($raw_email as $key => $email) { $object = new PhutilEmailAddress($email); $raw_email[$key] = $object->getAddress(); } $this->setParam("\162\x61\x77\x2d\x74\157", $raw_email); return $this; } public function addCCs(array $phids) { $phids = array_unique($phids); $this->setParam("\143\143", $phids); return $this; } public function setExcludeMailRecipientPHIDs(array $exclude) { $this->setParam("\x65\170\x63\154\x75\x64\x65", $exclude); return $this; } private function getExcludeMailRecipientPHIDs() { return $this->getParam("\x65\x78\x63\154\165\x64\145", array()); } public function setMutedPHIDs(array $muted) { $this->setParam("\155\165\164\x65\144", $muted); return $this; } private function getMutedPHIDs() { return $this->getParam("\x6d\165\164\x65\144", array()); } public function setForceHeraldMailRecipientPHIDs(array $force) { $this->setParam("\x68\145\162\141\154\x64\55\146\x6f\x72\143\145\x2d\162\x65\143\x69\x70\151\x65\156\x74\x73", $force); return $this; } private function getForceHeraldMailRecipientPHIDs() { return $this->getParam("\150\145\x72\x61\154\x64\55\146\x6f\x72\x63\145\55\x72\x65\143\x69\x70\x69\145\x6e\164\163", array()); } public function addPHIDHeaders($name, array $phids) { $phids = array_unique($phids); foreach ($phids as $phid) { $this->addHeader($name, "\x3c" . $phid . "\76"); } return $this; } public function addHeader($name, $value) { $this->parameters["\150\x65\141\144\145\x72\x73"][] = array($name, $value); return $this; } public function getHeaders() { return $this->getParam("\x68\x65\141\144\145\162\163", array()); } public function addAttachment(PhabricatorMailAttachment $attachment) { $this->parameters["\141\164\x74\x61\x63\x68\x6d\x65\x6e\164\163"][] = $attachment->toDictionary(); return $this; } public function getAttachments() { $dicts = $this->getParam("\141\x74\164\141\x63\x68\155\145\156\x74\x73", array()); $result = array(); foreach ($dicts as $dict) { $result[] = PhabricatorMailAttachment::newFromDictionary($dict); } return $result; } public function getAttachmentFilePHIDs() { $file_phids = array(); $dictionaries = $this->getParam("\x61\x74\164\x61\143\x68\155\145\x6e\164\163"); if ($dictionaries) { foreach ($dictionaries as $dictionary) { $file_phid = idx($dictionary, "\x66\151\154\145\x50\x48\x49\104"); if ($file_phid) { $file_phids[] = $file_phid; } } } return $file_phids; } public function loadAttachedFiles(PhabricatorUser $viewer) { $file_phids = $this->getAttachmentFilePHIDs(); if (!$file_phids) { return array(); } return id(new PhabricatorFileQuery())->setViewer($viewer)->withPHIDs($file_phids)->execute(); } public function setAttachments(array $attachments) { assert_instances_of($attachments, "\x50\x68\x61\142\162\x69\x63\x61\164\x6f\x72\x4d\x61\x69\x6c\101\164\x74\x61\143\150\x6d\145\x6e\x74"); $this->setParam("\141\x74\x74\x61\x63\x68\155\x65\156\x74\163", mpull($attachments, "\x74\157\x44\151\x63\x74\x69\157\156\141\x72\171")); return $this; } public function setFrom($from) { $this->setParam("\x66\162\x6f\x6d", $from); $this->setActorPHID($from); return $this; } public function getFrom() { return $this->getParam("\x66\162\157\155"); } public function setRawFrom($raw_email, $raw_name) { $this->setParam("\x72\141\x77\x2d\146\x72\157\x6d", array($raw_email, $raw_name)); return $this; } public function getRawFrom() { return $this->getParam("\162\141\x77\55\x66\162\x6f\155"); } public function setReplyTo($reply_to) { $this->setParam("\x72\x65\x70\x6c\x79\55\164\157", $reply_to); return $this; } public function getReplyTo() { return $this->getParam("\162\x65\x70\154\171\55\x74\157"); } public function setSubject($subject) { $this->setParam("\163\165\x62\x6a\x65\143\x74", $subject); return $this; } public function setSubjectPrefix($prefix) { $this->setParam("\163\x75\142\x6a\145\x63\164\x2d\160\162\x65\146\x69\170", $prefix); return $this; } public function getSubjectPrefix() { return $this->getParam("\163\x75\142\x6a\145\143\x74\55\160\162\145\146\x69\x78"); } public function setVarySubjectPrefix($prefix) { $this->setParam("\166\x61\x72\171\x2d\163\165\142\x6a\x65\x63\164\x2d\x70\162\145\146\x69\x78", $prefix); return $this; } public function getVarySubjectPrefix() { return $this->getParam("\166\x61\162\x79\55\163\165\142\152\x65\143\x74\x2d\160\x72\x65\146\x69\x78"); } public function setBody($body) { $this->setParam("\x62\157\144\171", $body); return $this; } public function setSensitiveContent($bool) { $this->setParam("\x73\x65\x6e\163\x69\164\151\x76\x65", $bool); return $this; } public function hasSensitiveContent() { return $this->getParam("\163\x65\156\163\x69\x74\x69\x76\145", true); } public function setMustEncrypt($bool) { return $this->setParam("\x6d\165\x73\x74\x45\x6e\x63\x72\171\x70\164", $bool); } public function getMustEncrypt() { return $this->getParam("\x6d\x75\163\x74\x45\x6e\143\162\x79\x70\x74", false); } public function setMustEncryptURI($uri) { return $this->setParam("\x6d\165\163\x74\105\x6e\143\x72\x79\160\164\x2e\165\x72\x69", $uri); } public function getMustEncryptURI() { return $this->getParam("\155\x75\163\x74\x45\156\143\x72\x79\x70\164\x2e\x75\x72\x69"); } public function setMustEncryptSubject($subject) { return $this->setParam("\x6d\x75\163\164\x45\156\x63\162\171\160\x74\56\x73\165\x62\152\145\143\x74", $subject); } public function getMustEncryptSubject() { return $this->getParam("\155\165\x73\164\x45\156\143\162\171\x70\x74\56\x73\165\142\x6a\x65\x63\164"); } public function setMustEncryptReasons(array $reasons) { return $this->setParam("\155\165\163\164\x45\156\x63\x72\x79\x70\x74\122\x65\141\x73\157\156\x73", $reasons); } public function getMustEncryptReasons() { return $this->getParam("\x6d\165\163\x74\x45\156\143\x72\171\x70\x74\x52\145\x61\163\x6f\x6e\163", array()); } public function setMailStamps(array $stamps) { return $this->setParam("\163\164\x61\155\x70\x73", $stamps); } public function getMailStamps() { return $this->getParam("\163\x74\x61\x6d\x70\163", array()); } public function setMailStampMetadata($metadata) { return $this->setParam("\163\x74\x61\155\x70\x4d\145\x74\x61\144\x61\164\x61", $metadata); } public function getMailStampMetadata() { return $this->getParam("\x73\164\x61\x6d\x70\115\145\164\141\x64\141\x74\141", array()); } public function getMailerKey() { return $this->getParam("\155\141\151\x6c\x65\162\56\153\x65\x79"); } public function setTryMailers(array $mailers) { return $this->setParam("\155\141\151\x6c\x65\162\163\56\x74\x72\x79", $mailers); } public function setHTMLBody($html) { $this->setParam("\150\x74\155\154\55\142\x6f\144\x79", $html); return $this; } public function getBody() { return $this->getParam("\x62\157\144\171"); } public function getHTMLBody() { return $this->getParam("\150\x74\155\154\x2d\x62\x6f\x64\171"); } public function setIsErrorEmail($is_error) { $this->setParam("\x69\x73\x2d\x65\162\x72\157\162", $is_error); return $this; } public function getIsErrorEmail() { return $this->getParam("\151\x73\55\x65\x72\162\157\162", false); } public function getToPHIDs() { return $this->getParam("\x74\157", array()); } public function getRawToAddresses() { return $this->getParam("\162\x61\167\x2d\164\x6f", array()); } public function getCcPHIDs() { return $this->getParam("\143\x63", array()); } public function setMessageType($message_type) { return $this->setParam("\x6d\x65\163\x73\141\x67\145\x2e\164\171\x70\145", $message_type); } public function getMessageType() { return $this->getParam("\x6d\145\163\163\x61\x67\x65\56\x74\171\x70\145", PhabricatorMailEmailMessage::MESSAGETYPE); } public function setForceDelivery($force) { $this->setParam("\x66\x6f\x72\143\145", $force); return $this; } public function getForceDelivery() { return $this->getParam("\x66\x6f\162\x63\145", false); } public function setIsBulk($is_bulk) { $this->setParam("\x69\x73\55\x62\x75\x6c\153", $is_bulk); return $this; } public function getIsBulk() { return $this->getParam("\151\x73\x2d\x62\165\154\x6b"); } public function setThreadID($thread_id, $is_first_message = false) { $this->setParam("\164\x68\162\145\x61\144\55\x69\144", $thread_id); $this->setParam("\151\163\x2d\146\151\x72\163\x74\x2d\x6d\145\163\163\x61\147\x65", $is_first_message); return $this; } public function getThreadID() { return $this->getParam("\164\x68\162\x65\141\x64\55\x69\x64"); } public function getIsFirstMessage() { return (bool) $this->getParam("\x69\163\x2d\x66\x69\162\163\x74\55\x6d\145\x73\x73\x61\x67\x65"); } public function saveAndSend() { return $this->save(); } public function save() { if ($this->getID()) { return parent::save(); } $this->openTransaction(); $result = parent::save(); $editor = new PhabricatorEdgeEditor(); $edge_type = PhabricatorMetaMTAMailHasRecipientEdgeType::EDGECONST; $recipient_phids = array_merge($this->getToPHIDs(), $this->getCcPHIDs()); $expanded_phids = $this->expandRecipients($recipient_phids); $all_phids = array_unique(array_merge($recipient_phids, $expanded_phids)); foreach ($all_phids as $curr_phid) { $editor->addEdge($this->getPHID(), $edge_type, $curr_phid); } $editor->save(); $this->saveTransaction(); $mailer_task = PhabricatorWorker::scheduleTask("\120\150\x61\142\x72\151\143\x61\x74\157\162\115\x65\164\141\x4d\x54\101\127\x6f\162\x6b\x65\162", $this->getID(), array("\160\162\151\x6f\162\x69\x74\171" => PhabricatorWorker::PRIORITY_ALERTS)); return $result; } public function sendNow() { if ($this->getStatus() != PhabricatorMailOutboundStatus::STATUS_QUEUE) { throw new Exception(pht("\124\x72\171\151\156\147\40\164\x6f\x20\x73\145\x6e\x64\40\x61\x6e\40\141\x6c\x72\145\141\x64\171\x2d\163\145\156\x74\x20\x6d\141\x69\x6c\41")); } $mailers = self::newMailers(array("\157\165\164\142\x6f\x75\156\x64" => true, "\x6d\x65\144\x69\x61" => array($this->getMessageType()))); $try_mailers = $this->getParam("\x6d\x61\x69\154\145\x72\x73\x2e\164\x72\171"); if ($try_mailers) { $mailers = mpull($mailers, null, "\x67\x65\x74\x4b\x65\x79"); $mailers = array_select_keys($mailers, $try_mailers); } return $this->sendWithMailers($mailers); } public static function newMailers(array $constraints) { PhutilTypeSpec::checkMap($constraints, array("\x74\x79\x70\x65\x73" => "\157\x70\x74\x69\x6f\156\141\154\x20\154\x69\x73\x74\x3c\163\x74\x72\151\156\x67\x3e", "\151\156\142\157\x75\156\144" => "\157\x70\164\151\157\x6e\141\154\40\x62\x6f\157\154", "\x6f\x75\164\142\157\x75\156\144" => "\157\x70\x74\x69\157\x6e\141\154\40\x62\157\x6f\x6c", "\x6d\145\144\x69\x61" => "\x6f\x70\x74\151\157\156\x61\154\40\154\151\x73\164\74\163\164\x72\151\x6e\147\x3e")); $mailers = array(); $config = PhabricatorEnv::getEnvConfig("\143\154\x75\x73\164\x65\x72\x2e\155\141\151\x6c\x65\x72\163"); $adapters = PhabricatorMailAdapter::getAllAdapters(); $next_priority = -1; foreach ($config as $spec) { $type = $spec["\164\x79\160\x65"]; if (!isset($adapters[$type])) { throw new Exception(pht("\125\x6e\153\156\x6f\x77\156\40\x6d\x61\151\154\x65\x72\40\50\x22\x25\163\42\x29\41", $type)); } $key = $spec["\x6b\145\x79"]; $mailer = id(clone $adapters[$type])->setKey($key); $priority = idx($spec, "\x70\162\x69\x6f\x72\x69\164\171"); if (!$priority) { $priority = $next_priority; $next_priority--; } $mailer->setPriority($priority); $defaults = $mailer->newDefaultOptions(); $options = idx($spec, "\x6f\x70\164\x69\x6f\x6e\x73", array()) + $defaults; $mailer->setOptions($options); $mailer->setSupportsInbound(idx($spec, "\x69\x6e\x62\x6f\165\156\144", true)); $mailer->setSupportsOutbound(idx($spec, "\x6f\165\164\x62\157\x75\156\x64", true)); $media = idx($spec, "\x6d\x65\144\151\x61"); if ($media !== null) { $mailer->setMedia($media); } $mailers[] = $mailer; } if (isset($constraints["\x74\171\160\x65\163"])) { $types = $constraints["\x74\171\x70\145\x73"]; $types = array_fuse($types); foreach ($mailers as $key => $mailer) { $mailer_type = $mailer->getAdapterType(); if (!isset($types[$mailer_type])) { unset($mailers[$key]); } } } if (!empty($constraints["\151\x6e\x62\x6f\165\156\x64"])) { foreach ($mailers as $key => $mailer) { if (!$mailer->getSupportsInbound()) { unset($mailers[$key]); } } } if (!empty($constraints["\x6f\x75\164\142\157\165\x6e\x64"])) { foreach ($mailers as $key => $mailer) { if (!$mailer->getSupportsOutbound()) { unset($mailers[$key]); } } } if (!empty($constraints["\155\145\x64\x69\141"])) { foreach ($mailers as $key => $mailer) { $supports_any = false; foreach ($constraints["\155\x65\x64\151\x61"] as $medium) { if ($mailer->supportsMessageType($medium)) { $supports_any = true; break; } } if (!$supports_any) { unset($mailers[$key]); } } } $sorted = array(); $groups = mgroup($mailers, "\147\x65\x74\x50\162\151\157\x72\x69\164\x79"); krsort($groups); foreach ($groups as $group) { shuffle($group); foreach ($group as $mailer) { $sorted[] = $mailer; } } return $sorted; } public function sendWithMailers(array $mailers) { if (!$mailers) { $any_mailers = self::newMailers(array()); if ($any_mailers) { $void_message = pht("\116\157\40\x63\x6f\x6e\x66\151\x67\165\162\x65\144\40\155\x61\x69\x6c\145\x72\163\40\x73\x75\160\x70\x6f\162\164\x20\x73\145\156\144\151\156\147\x20\157\165\x74\x62\x6f\165\x6e\144\x20\155\141\151\x6c\56"); } else { $void_message = pht("\x4e\157\40\x6d\x61\151\154\x65\x72\163\x20\141\162\145\x20\143\157\156\x66\151\147\x75\162\x65\x64\56"); } return $this->setStatus(PhabricatorMailOutboundStatus::STATUS_VOID)->setMessage($void_message)->save(); } $actors = $this->loadAllActors(); $target_phid = head($this->getToPHIDs()); if (!$target_phid) { $target_phid = head($this->getCcPHIDs()); } $preferences = $this->loadPreferences($target_phid); $viewer = PhabricatorUser::getOmnipotentUser(); $files = $this->loadAttachedFiles($viewer); foreach ($files as $file) { $file->attachToObject($this->getPHID()); } $type_map = PhabricatorMailExternalMessage::getAllMessageTypes(); $type = idx($type_map, $this->getMessageType()); if (!$type) { throw new Exception(pht("\125\x6e\x61\142\154\145\x20\x74\x6f\x20\x73\145\156\144\40\x6d\145\x73\163\141\147\x65\x20\x77\x69\x74\x68\x20\x75\x6e\153\x6e\x6f\167\156\x20\x6d\145\x73\x73\141\147\145\x20\164\x79\160\x65\40\42\x25\x73\42\x2e", $type)); } $exceptions = array(); foreach ($mailers as $mailer) { try { $message = $type->newMailMessageEngine()->setMailer($mailer)->setMail($this)->setActors($actors)->setPreferences($preferences)->newMessage($mailer); } catch (Exception $ex) { $exceptions[] = $ex; continue; } if (!$message) { return $this->setStatus(PhabricatorMailOutboundStatus::STATUS_VOID)->save(); } try { $mailer->sendMessage($message); } catch (PhabricatorMetaMTAPermanentFailureException $ex) { $this->setStatus(PhabricatorMailOutboundStatus::STATUS_FAIL)->setMessage($ex->getMessage())->save(); throw $ex; } catch (Exception $ex) { $exceptions[] = $ex; continue; } $mailer_key = $mailer->getKey(); if ($mailer_key !== null) { $this->setParam("\155\141\151\154\x65\x72\x2e\x6b\x65\x79", $mailer_key); } $actor_list = array(); foreach ($actors as $actor) { $actor_list[$actor->getPHID()] = array("\x64\145\154\151\x76\145\162\x61\142\154\x65" => $actor->isDeliverable(), "\x72\x65\x61\x73\x6f\156\163" => $actor->getDeliverabilityReasons()); } $this->setParam("\x61\x63\x74\157\162\163\x2e\163\145\x6e\x74", $actor_list); $this->setParam("\162\157\x75\164\x69\x6e\147\56\163\x65\x6e\164", $this->getParam("\x72\157\x75\164\151\156\147")); $this->setParam("\162\x6f\x75\x74\x69\x6e\147\155\x61\x70\x2e\x73\145\156\164", $this->getRoutingRuleMap()); return $this->setStatus(PhabricatorMailOutboundStatus::STATUS_SENT)->save(); } $messages = array(); foreach ($exceptions as $ex) { $messages[] = $ex->getMessage(); } $messages = implode("\12\12", $messages); $this->setMessage($messages)->save(); if (count($exceptions) === 1) { throw head($exceptions); } throw new PhutilAggregateException(pht("\x45\x6e\x63\x6f\x75\156\x74\x65\162\145\144\x20\155\165\x6c\x74\x69\160\x6c\x65\40\x65\170\x63\x65\x70\164\x69\x6f\156\x73\x20\x77\x68\151\154\145\40\x74\x72\141\156\163\155\151\164\x74\151\x6e\147\x20\x6d\x61\151\x6c\56"), $exceptions); } public static function shouldMailEachRecipient() { return PhabricatorEnv::getEnvConfig("\x6d\x65\x74\141\155\164\x61\56\157\x6e\x65\55\x6d\x61\151\154\55\x70\x65\x72\x2d\162\145\143\x69\160\151\145\156\x74"); } public function buildRecipientList() { $actors = $this->loadAllActors(); $actors = $this->filterDeliverableActors($actors); return mpull($actors, "\x67\145\x74\120\110\111\x44"); } public function loadAllActors() { $actor_phids = $this->getExpandedRecipientPHIDs(); return $this->loadActors($actor_phids); } public function getExpandedRecipientPHIDs() { $actor_phids = $this->getAllActorPHIDs(); return $this->expandRecipients($actor_phids); } private function getAllActorPHIDs() { return array_merge(array($this->getParam("\146\162\x6f\155")), $this->getToPHIDs(), $this->getCcPHIDs()); } public function expandRecipients(array $phids) { if ($this->recipientExpansionMap === null) { $all_phids = $this->getAllActorPHIDs(); $this->recipientExpansionMap = id(new PhabricatorMetaMTAMemberQuery())->setViewer(PhabricatorUser::getOmnipotentUser())->withPHIDs($all_phids)->execute(); } $results = array(); foreach ($phids as $phid) { foreach ($this->recipientExpansionMap[$phid] as $recipient_phid) { $results[$recipient_phid] = $recipient_phid; } } return array_keys($results); } private function filterDeliverableActors(array $actors) { assert_instances_of($actors, "\x50\150\141\x62\162\151\x63\141\x74\x6f\x72\x4d\x65\164\x61\x4d\124\x41\101\143\x74\x6f\162"); $deliverable_actors = array(); foreach ($actors as $phid => $actor) { if ($actor->isDeliverable()) { $deliverable_actors[$phid] = $actor; } } return $deliverable_actors; } private function loadActors(array $actor_phids) { $actor_phids = array_filter($actor_phids); $viewer = PhabricatorUser::getOmnipotentUser(); $actors = id(new PhabricatorMetaMTAActorQuery())->setViewer($viewer)->withPHIDs($actor_phids)->execute(); if (!$actors) { return array(); } if ($this->getForceDelivery()) { foreach ($actors as $actor) { $actor->setDeliverable(PhabricatorMetaMTAActor::REASON_FORCE); } return $actors; } foreach ($this->getExcludeMailRecipientPHIDs() as $phid) { $actor = idx($actors, $phid); if (!$actor) { continue; } $actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_RESPONSE); } $deliverable = array(); foreach ($actors as $phid => $actor) { if ($actor->isDeliverable()) { $deliverable[] = $phid; } } foreach ($this->getMutedPHIDs() as $muted_phid) { $muted_actor = idx($actors, $muted_phid); if (!$muted_actor) { continue; } $muted_actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_MUTED); } $from_phid = $this->getParam("\146\x72\x6f\155"); $from_actor = idx($actors, $from_phid); if ($from_actor) { $from_user = id(new PhabricatorPeopleQuery())->setViewer($viewer)->withPHIDs(array($from_phid))->needUserSettings(true)->execute(); $from_user = head($from_user); if ($from_user) { $pref_key = PhabricatorEmailSelfActionsSetting::SETTINGKEY; $exclude_self = $from_user->getUserSetting($pref_key); if ($exclude_self) { $from_actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_SELF); } } } $all_prefs = id(new PhabricatorUserPreferencesQuery())->setViewer(PhabricatorUser::getOmnipotentUser())->withUserPHIDs($actor_phids)->needSyntheticPreferences(true)->execute(); $all_prefs = mpull($all_prefs, null, "\147\x65\x74\125\x73\145\162\120\x48\x49\x44"); $value_email = PhabricatorEmailTagsSetting::VALUE_EMAIL; $tags = $this->getParam("\x6d\x61\x69\154\x74\141\x67\x73"); if ($tags) { foreach ($all_prefs as $phid => $prefs) { $user_mailtags = $prefs->getSettingValue(PhabricatorEmailTagsSetting::SETTINGKEY); $send = false; foreach ($tags as $tag) { if ((int) idx($user_mailtags, $tag, $value_email) == $value_email) { $send = true; break; } } if (!$send) { $actors[$phid]->setUndeliverable(PhabricatorMetaMTAActor::REASON_MAILTAGS); } } } foreach ($deliverable as $phid) { switch ($this->getRoutingRule($phid)) { case PhabricatorMailRoutingRule::ROUTE_AS_NOTIFICATION: $actors[$phid]->setUndeliverable(PhabricatorMetaMTAActor::REASON_ROUTE_AS_NOTIFICATION); break; case PhabricatorMailRoutingRule::ROUTE_AS_MAIL: $actors[$phid]->setDeliverable(PhabricatorMetaMTAActor::REASON_ROUTE_AS_MAIL); break; default: break; } } $force_recipients = $this->getForceHeraldMailRecipientPHIDs(); $force_recipients = array_fuse($force_recipients); if ($force_recipients) { foreach ($deliverable as $phid) { if (isset($force_recipients[$phid])) { $actors[$phid]->setDeliverable(PhabricatorMetaMTAActor::REASON_FORCE_HERALD); } } } foreach ($all_prefs as $phid => $prefs) { $exclude = $prefs->getSettingValue(PhabricatorEmailNotificationsSetting::SETTINGKEY); if ($exclude) { $actors[$phid]->setUndeliverable(PhabricatorMetaMTAActor::REASON_MAIL_DISABLED); } } foreach ($actors as $phid => $actor) { if ($actor->getIsVerified()) { continue; } $actor->setUndeliverable(PhabricatorMetaMTAActor::REASON_UNVERIFIED); } return $actors; } public function getDeliveredHeaders() { return $this->getParam("\150\x65\x61\144\145\x72\163\56\x73\145\156\164"); } public function setDeliveredHeaders(array $headers) { $headers = $this->flattenHeaders($headers); return $this->setParam("\150\145\141\144\145\x72\x73\x2e\163\145\156\x74", $headers); } public function getUnfilteredHeaders() { $unfiltered = $this->getParam("\x68\145\141\144\x65\162\163\x2e\x75\x6e\x66\x69\x6c\x74\x65\162\145\144"); if ($unfiltered === null) { return $this->getDeliveredHeaders(); } return $unfiltered; } public function setUnfilteredHeaders(array $headers) { $headers = $this->flattenHeaders($headers); return $this->setParam("\150\145\141\x64\145\x72\x73\56\165\x6e\x66\151\x6c\x74\145\162\145\144", $headers); } private function flattenHeaders(array $headers) { assert_instances_of($headers, "\120\x68\141\142\162\151\x63\141\x74\157\162\115\141\151\x6c\110\x65\x61\144\145\162"); $list = array(); foreach ($list as $header) { $list[] = array($header->getName(), $header->getValue()); } return $list; } public function getDeliveredActors() { return $this->getParam("\x61\x63\x74\157\162\163\x2e\163\145\156\x74"); } public function getDeliveredRoutingRules() { return $this->getParam("\162\x6f\165\x74\x69\x6e\147\x2e\163\x65\156\x74"); } public function getDeliveredRoutingMap() { return $this->getParam("\x72\157\165\164\x69\156\147\155\x61\160\x2e\x73\145\156\x74"); } public function getDeliveredBody() { return $this->getParam("\142\x6f\x64\171\x2e\x73\145\156\x74"); } public function setDeliveredBody($body) { return $this->setParam("\142\157\144\x79\x2e\163\145\x6e\x74", $body); } public function getURI() { return "\x2f\155\141\151\154\x2f\x64\x65\x74\x61\x69\x6c\57" . $this->getID() . "\x2f"; } public function addRoutingRule($routing_rule, $phids, $reason_phid) { $routing = $this->getParam("\162\157\x75\164\x69\x6e\147", array()); $routing[] = array("\x72\157\165\x74\x69\156\x67\x52\x75\154\145" => $routing_rule, "\x70\x68\x69\x64\163" => $phids, "\162\x65\x61\x73\x6f\x6e\120\x48\x49\104" => $reason_phid); $this->setParam("\x72\x6f\165\x74\151\156\x67", $routing); $this->routingMap = null; return $this; } private function getRoutingRule($phid) { $map = $this->getRoutingRuleMap(); $info = idx($map, $phid, idx($map, "\x64\x65\x66\141\165\x6c\x74")); if ($info) { return idx($info, "\162\x75\154\145"); } return null; } private function getRoutingRuleMap() { if ($this->routingMap === null) { $map = array(); $routing = $this->getParam("\162\157\165\164\x69\x6e\147", array()); foreach ($routing as $route) { $phids = $route["\160\150\151\x64\x73"]; if ($phids === null) { $phids = array("\x64\145\146\141\165\x6c\164"); } foreach ($phids as $phid) { $new_rule = $route["\x72\157\165\164\x69\x6e\x67\122\165\x6c\x65"]; $current_rule = idx($map, $phid); if ($current_rule === null) { $is_stronger = true; } else { $is_stronger = PhabricatorMailRoutingRule::isStrongerThan($new_rule, $current_rule); } if ($is_stronger) { $map[$phid] = array("\x72\x75\x6c\145" => $new_rule, "\162\x65\141\x73\x6f\156" => $route["\x72\145\x61\x73\x6f\x6e\120\110\111\x44"]); } } } $this->routingMap = $map; } return $this->routingMap; } private function loadPreferences($target_phid) { $viewer = PhabricatorUser::getOmnipotentUser(); if (self::shouldMailEachRecipient()) { $preferences = id(new PhabricatorUserPreferencesQuery())->setViewer($viewer)->withUserPHIDs(array($target_phid))->needSyntheticPreferences(true)->executeOne(); if ($preferences) { return $preferences; } } return PhabricatorUserPreferences::loadGlobalPreferences($viewer); } public function shouldRenderMailStampsInBody($viewer) { $preferences = $this->loadPreferences($viewer->getPHID()); $value = $preferences->getSettingValue(PhabricatorEmailStampsSetting::SETTINGKEY); return $value == PhabricatorEmailStampsSetting::VALUE_BODY_STAMPS; } public function getCapabilities() { return array(PhabricatorPolicyCapability::CAN_VIEW); } public function getPolicy($capability) { return PhabricatorPolicies::POLICY_NOONE; } public function hasAutomaticCapability($capability, PhabricatorUser $viewer) { $actor_phids = $this->getExpandedRecipientPHIDs(); return in_array($viewer->getPHID(), $actor_phids); } public function describeAutomaticCapability($capability) { return pht("\x54\x68\145\x20\155\141\x69\154\x20\x73\145\x6e\144\145\162\x20\x61\x6e\144\40\x6d\145\x73\x73\x61\147\x65\x20\x72\145\x63\151\160\151\x65\x6e\164\x73\40\x63\x61\156\x20\141\x6c\x77\x61\x79\x73\40\163\145\x65\x20\x74\150\x65\40\x6d\141\151\x6c\x2e"); } public function destroyObjectPermanently(PhabricatorDestructionEngine $engine) { $files = $this->loadAttachedFiles($engine->getViewer()); foreach ($files as $file) { $engine->destroyObject($file); } $this->delete(); } }
Function Calls
None |
Stats
MD5 | 80da693b42041c5d7a3419eb7999af32 |
Eval Count | 0 |
Decode Time | 124 ms |