Index: branches/5.2.x/core/kernel/utility/email.php =================================================================== --- branches/5.2.x/core/kernel/utility/email.php +++ branches/5.2.x/core/kernel/utility/email.php @@ -409,11 +409,7 @@ { $this->_collectRecipients(); - $header_mapping = Array ( - EmailTemplate::RECIPIENT_TYPE_TO => 'To', - EmailTemplate::RECIPIENT_TYPE_CC => 'Cc', - EmailTemplate::RECIPIENT_TYPE_BCC => 'Bcc', - ); + $header_mapping = $this->getHeaderMapping(); $default_email = $this->Application->ConfigValue('DefaultEmailSender'); $this->recipients = array_map(Array ($this, '_transformRecipientsIntoPairs'), $this->recipients); @@ -452,6 +448,7 @@ $this->_overwriteToRecipient(); $this->_addRecipientByUserId(); $this->_addRecipientFromParams(); + $this->_moveDirectRecipients(); if ( ($this->emailTemplate->GetDBField('Type') == EmailTemplate::TEMPLATE_TYPE_ADMIN) && !$this->recipients[EmailTemplate::RECIPIENT_TYPE_TO] ) { // admin email template without direct recipient -> send to admin @@ -574,6 +571,47 @@ } /** + * Move recipients, that were added manually via "$this->sender->Add*" methods. + * + * @return void + * @access protected + */ + protected function _moveDirectRecipients() + { + foreach ( $this->getHeaderMapping() as $recipient_type => $header_name ) { + $manual_recipients = $this->sender->GetRecipientsByHeader($header_name); + + if ( !$manual_recipients ) { + continue; + } + + foreach ( $manual_recipients as $manual_recipient ) { + $this->recipients[$recipient_type][] = array( + 'RecipientName' => $manual_recipient['Name'], + 'RecipientAddressType' => EmailTemplate::ADDRESS_TYPE_EMAIL, + 'RecipientAddress' => $manual_recipient['Email'], + ); + } + + $this->sender->SetHeader($header_name, ''); + } + } + + /** + * Returns mapping between recipient type and header name. + * + * @return array + */ + protected function getHeaderMapping() + { + return array( + EmailTemplate::RECIPIENT_TYPE_TO => 'To', + EmailTemplate::RECIPIENT_TYPE_CC => 'Cc', + EmailTemplate::RECIPIENT_TYPE_BCC => 'Bcc', + ); + } + + /** * This is default recipient, when we can't determine actual one * * @return void Index: branches/5.2.x/core/kernel/utility/email_send.php =================================================================== --- branches/5.2.x/core/kernel/utility/email_send.php +++ branches/5.2.x/core/kernel/utility/email_send.php @@ -1958,6 +1958,69 @@ } /** + * Returns list of recipients from given header. + * + * @param string $header_name Header name. + * + * @return array + */ + public function GetRecipientsByHeader($header_name) + { + if ( !isset($this->headers[$header_name]) ) { + return array(); + } + + $decoded_header = $this->decodeHeader($this->headers[$header_name]); + $recipients = $this->GetRecipients($decoded_header); + + if ( $recipients === false ) { + return array(); + } + + return $recipients; + } + + /** + * Decodes header value. + * + * @param string $header_value Header value. + * + * @return string + */ + protected function decodeHeader($header_value) + { + while ( preg_match('/(=\?([^?]+)\?(Q|B)\?([^?]*)\?=)/i', $header_value, $matches) ) { + $encoded = $matches[1]; + $charset = $matches[2]; + $encoding = $matches[3]; + $text = $matches[4]; + + switch ( strtoupper($encoding) ) { + case 'B': + $text = base64_decode($text); + break; + + case 'Q': + $text = str_replace('_', ' ', $text); + preg_match_all('/=([a-f0-9]{2})/i', $text, $matches); + + foreach ( $matches[1] as $value ) { + $text = str_replace('=' . $value, chr(hexdec($value)), $text); + } + break; + } + + $header_value = mb_convert_encoding( + str_replace($encoded, $text, $header_value), + $this->charset, + $charset + ); + } + + return $header_value; + } + + /** * Sets "Subject" header. * * @param string $subject message subject @@ -2084,4 +2147,4 @@ { $this->_logData = $log_data; } - } \ No newline at end of file + }