News:

Bored?  Looking to kill some time?  Want to chat with other SMF users?  Join us in IRC chat or Discord

Main Menu

Mails from RC3 curious

Started by hop, November 10, 2006, 06:40:11 PM

Previous topic - Next topic

hop

Hello,

after upgrading from 1.0.9 to 1.1.RC3 the mails the board send are curious.

Example:

X-Mailer: SMF Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: quoted-printable
Message-Id: <[email protected]>
X-UIDL: +5m"!Z>=!!H!1"!'cj!!

Hallo xxx,  Diese E-Mail wurde gesendet, weil Sie die 'Passwort vergessen' Funktion benutzt haben. Um ein neues Passwort einzugeben, klicken Sie bitte auf folgenden Link:  hxxp:xxxxxx.de/index.php=3Faction=3Dreminder;sa=3Dsetpassword;u=3D1;code=3D1a9c7264d5 [nonactive]  IP: 84.60.249.30  Benutzername: xxx  Lieben Gru=C3=9F, das Board Team.

The user can not click this link because "ndex.php=3Faction=" 3F .

Is there any help for this Problem. What can I do ?

Hans


Compuart

#1
We've fixed several bugs regarding the mail system. Try replacing the sendmail() and mimespecialchars() functions in Subs-Post.php by the following two functions:

Code (Subs-Post.php) Select
function sendmail($to, $subject, $message, $from = null, $message_id = null, $send_html = false, $priority = 1, $hotmail_fix = null)
{
global $webmaster_email, $context, $modSettings, $txt, $scripturl;

// Use sendmail if it's set or if no SMTP server is set.
$use_sendmail = empty($modSettings['mail_type']) || $modSettings['smtp_host'] == '';

// Line breaks need to be \r\n only in windows or for SMTP.
$line_break = $context['server']['is_windows'] || !$use_sendmail ? "\r\n" : "\n";

// So far so good.
$mail_result = true;

// If the recipient list isn't an array, make it one.
$to_array = is_array($to) ? $to : array($to);

// Sadly Hotmail doesn't support character sets properly.
if ($hotmail_fix === null)
{
$hotmail_to = array();
foreach ($to_array as $i => $to_address)
{
if (preg_match('~@hotmail.[a-zA-Z\.]{2,6}$~i', $to_address) === 1)
{
$hotmail_to[] = $to_address;
$to_array = array_diff($to_array, array($to_address));
}
}

// Call this function recursively for the hotmail addresses.
if (!empty($hotmail_to))
$mail_result = sendmail($hotmail_to, $subject, $message, $from, $message_id, $send_html, $priority, true);

// The remaining addresses no longer need the fix.
$hotmail_fix = false;

// No other addresses left? Return instantly.
if (empty($to_array))
return $mail_result;
}

// Get rid of slashes and entities.
$subject = un_htmlspecialchars(stripslashes($subject));
// Make the message use the proper line breaks.
$message = str_replace(array("\r", "\n"), array('', $line_break), stripslashes($message));

// Make sure hotmail mails are sent as HTML so that HTML entities work.
if ($hotmail_fix && !$send_html)
{
$send_html = true;
$message = strtr($message, array($line_break => '<br />' . $line_break));
$message = preg_replace('~(' . preg_quote($scripturl, '~') . '([?/][\w\-_%\.,\?&;=#]+)?)~', '<a href="$1">$1</a>', $message);
}

list (, $from_name) = mimespecialchars(addcslashes($from !== null ? $from : $context['forum_name'], '<>()\'\\"'), true, $hotmail_fix, $line_break);
list (, $subject) = mimespecialchars($subject, true, $hotmail_fix, $line_break);

// Construct the mail headers...
$headers = 'From: "' . $from_name . '" <' . (empty($modSettings['mail_from']) ? $webmaster_email : $modSettings['mail_from']) . '>' . $line_break;
$headers .= $from !== null ? 'Reply-To: <' . $from . '>' . $line_break : '';
$headers .= 'Return-Path: ' . (empty($modSettings['mail_from']) ? $webmaster_email: $modSettings['mail_from']) . $line_break;
$headers .= 'Date: ' . gmdate('D, d M Y H:i:s') . ' +0000' . $line_break;

if ($message_id !== null && empty($modSettings['mail_no_message_id']))
$headers .= 'Message-ID: <' . md5($scripturl . microtime()) . '-' . $message_id . strstr(empty($modSettings['mail_from']) ? $webmaster_email : $modSettings['mail_from'], '@') . '>' . $line_break;
$headers .= 'X-Mailer: SMF' . $line_break;

// pass this to the integration before we start modifying the output -- it'll make it easier later
if (isset($modSettings['integrate_outgoing_email']) && function_exists($modSettings['integrate_outgoing_email']))
{
if ($modSettings['integrate_outgoing_email']($subject, $message, $headers) === false)
return false;
}

$charset = isset($context['character_set']) ? $context['character_set'] : $txt['lang_character_set'];

list ($charset, $message, $encoding) = mimespecialchars($message, false, $hotmail_fix, $line_break);

// Sending HTML?  Let's plop in some basic stuff, then.
if ($send_html)
{
// This should send a text message with MIME multipart/alternative stuff.
$mime_boundary = 'SMF-' . md5($message . time());
$headers .= 'Mime-Version: 1.0' . $line_break;
$headers .= 'Content-Type: multipart/alternative; boundary="' . $mime_boundary . '"' . $line_break;
$headers .= 'Content-Transfer-Encoding: ' . ($encoding == '' ? '7bit' : $encoding);

// Save the original message...
$orig_message = $message;

// But, then, dump it and use a plain one for dinosaur clients.
$message = un_htmlspecialchars(strip_tags(strtr($orig_message, array('</title>' => $line_break)))) . $line_break . '--' . $mime_boundary . $line_break;

// This is the plain text version.  Even if no one sees it, we need it for spam checkers.
$message .= 'Content-Type: text/plain; charset=' . $charset . $line_break;
$message .= 'Content-Transfer-Encoding: ' . ($encoding == '' ? '7bit' : $encoding) . $line_break . $line_break;
$message .= un_htmlspecialchars(strip_tags(strtr($orig_message, array('</title>' => $line_break)))) . $line_break . "--" . $mime_boundary . $line_break;

// This is the actual HTML message, prim and proper.  If we wanted images, they could be inlined here (with multipart/related, etc.)
$message .= 'Content-Type: text/html; charset=' . $charset . $line_break;
$message .= 'Content-Transfer-Encoding: ' . ($encoding == '' ? '7bit' : $encoding) . $line_break . $line_break;
$message .= $orig_message . $line_break . "--" . $mime_boundary . '--';
}
// Text is good too.
else
{
$headers .= 'Content-Type: text/plain; charset=' . $charset . $line_break;
if ($encoding != '')
$headers .= 'Content-Transfer-Encoding: ' . $encoding;
}

// SMTP or sendmail?
if ($use_sendmail)
{
$subject = strtr($subject, array("\r" => '', "\n" => ''));
if (!empty($modSettings['mail_strip_carriage']))
{
$message = strtr($message, array("\r" => ''));
$headers = strtr($headers, array("\r" => ''));
}

foreach ($to_array as $to)
{
if (!mail(strtr($to, array("\r" => '', "\n" => '')), $subject, $message, $headers))
{
log_error(sprintf($txt['mail_send_unable'], $to));
$mail_result = false;
}

// Wait, wait, I'm still sending here!
@set_time_limit(300);
if (function_exists('apache_reset_timeout'))
apache_reset_timeout();
}
}
else
$mail_result = $mail_result && smtp_mail($to_array, $subject, $message, $send_html ? $headers : "Mime-Version: 1.0" . $line_break . $headers);

// Everything go smoothly?
return $mail_result;
}


Code (Subs-Post.php) Select
function mimespecialchars($string, $with_charset = true, $hotmail_fix = false, $line_break = "\r\n")
{
global $context;

$charset = $context['character_set'];

// This is the fun part....
if (preg_match_all('~&#(\d{3,8});~', $string, $matches) !== 0 && !$hotmail_fix)
{
// Let's, for now, assume there are only 'ish characters.
$simple = true;

foreach ($matches[1] as $entity)
if ($entity > 128)
$simple = false;
unset($matches);

if ($simple)
$string = preg_replace('~&#(\d{3,8});~e', 'chr(\'$1\')', $string);
else
{
// Try to convert the string to UTF-8.
if (!$context['utf8'] && function_exists('iconv'))
$string = @iconv($context['character_set'], 'UTF-8', $string);

$fixchar = create_function('$n', '
if ($n < 128)
return chr($n);
elseif ($n < 2048)
return chr(192 | $n >> 6) . chr(128 | $n & 63);
elseif ($n < 65536)
return chr(224 | $n >> 12) . chr(128 | $n >> 6 & 63) . chr(128 | $n & 63);
else
return chr(240 | $n >> 18) . chr(128 | $n >> 12 & 63) . chr(128 | $n >> 6 & 63) . chr(128 | $n & 63);');

$string = preg_replace('~&#(\d{3,8});~e', '$fixchar(\'$1\')', $string);

// Unicode, baby.
$charset = 'UTF-8';
}
}

// Convert all special characters to HTML entities...just for Hotmail :-\
if ($hotmail_fix && ($context['utf8'] || function_exists('iconv') || $context['character_set'] === 'ISO-8859-1'))
{
if (!$context['utf8'] && function_exists('iconv'))
$string = @iconv($context['character_set'], 'UTF-8', $string);

$entityConvert = create_function('$c', '
if (strlen($c) === 1 && ord($c{0}) <= 0x7F)
return $c;
elseif (strlen($c) === 2 && ord($c{0}) >= 0xC0 && ord($c{0}) <= 0xDF)
return "&#" . (((ord($c{0}) ^ 0xC0) << 6) + (ord($c{1}) ^ 0x80)) . ";";
elseif (strlen($c) === 3 && ord($c{0}) >= 0xE0 && ord($c{0}) <= 0xEF)
return "&#" . (((ord($c{0}) ^ 0xE0) << 12) + ((ord($c{1}) ^ 0x80) << 6) + (ord($c{2}) ^ 0x80)) . ";";
elseif (strlen($c) === 4 && ord($c{0}) >= 0xF0 && ord($c{0}) <= 0xF7)
return "&#" . (((ord($c{0}) ^ 0xF0) << 18) + ((ord($c{1}) ^ 0x80) << 12) + ((ord($c{2}) ^ 0x80) << 6) + (ord($c{3}) ^ 0x80)) . ";";
else
return "";');

// Convert all 'special' characters to HTML entities.
return array($charset, preg_replace('~([\x80-\x{10FFFF}])~eu', '$entityConvert("\1")', $string), '7bit');
}

// We don't need to mess with the subject line if no special characters were in it..
elseif (!$hotmail_fix && preg_match('~([^\x09\x0A\x0D\x20-\x7F])~', $string) === 1)
{
// Base64 encode.
$string = base64_encode($string);

// Show the characterset and the transfer-encoding for header strings.
if ($with_charset)
$string = '=?' . $charset . '?B?' . $string . '?=';

// Break it up in lines (mail body).
else
$string = chunk_split($string, 76, $line_break);

return array($charset, $string, 'base64');
}

else
return array($charset, $string, '7bit');
}


These functions use a different encoding of emails that seems to somehow be better supported by several mail clients.
Hendrik Jan Visser
Former Lead Developer & Co-founder www.simplemachines.org
Personal Signature:
Realitynet.nl -> ExpeditieRobinson.net / PekingExpress.org / WieIsDeMol.Com

hop

It works fine now with your modifikation. Thank you :)

Hans

Compuart

I'm glad it did. Thanks for coming back to us on this.
Hendrik Jan Visser
Former Lead Developer & Co-founder www.simplemachines.org
Personal Signature:
Realitynet.nl -> ExpeditieRobinson.net / PekingExpress.org / WieIsDeMol.Com

vhv_alex

I ran into this problem too and after applied Compuart's fixes, everything okie now.

Thank you so much :)
www.joomlaviet.org [nofollow]

Markku

I was having the same issue, thanks for the fix, Compuart!
Official Finnish Joomla! partner site
http://www.joomlaportal.fi

yago101

that changes fixed the mail code, but... I saw this (5 different times from 5 different IPs) at the error log:

http://www.museabuse.com/smf/index.php?action=register2 [nofollow]

8: Undefined index: is_windows
Archivo: /web/htdocs/www.museabuse.com/home/smf/Sources/Subs-Post.php
Línea: 520

so... it doesn't work correctly, sorry  :'(

Compuart

That might be caused because of a version incompatibility. Search in Load.php for:
// This determines the server... not used in many places, except for login fixing.

and make sure that the $context['server'] array following that comment looks like:
$context['server'] = array(
'is_iis' => isset($_SERVER['SERVER_SOFTWARE']) && strpos($_SERVER['SERVER_SOFTWARE'], 'Microsoft-IIS') !== false,
'is_apache' => isset($_SERVER['SERVER_SOFTWARE']) && strpos($_SERVER['SERVER_SOFTWARE'], 'Apache') !== false,
'is_cgi' => isset($_SERVER['SERVER_SOFTWARE']) && strpos(php_sapi_name(), 'cgi') !== false,
'is_windows' => stristr(PHP_OS, 'WIN') !== false,
'iso_case_folding' => ord(strtolower(chr(138))) === 154,
'complex_preg_chars' => @version_compare(PHP_VERSION, '4.3.3') != -1,
);
Hendrik Jan Visser
Former Lead Developer & Co-founder www.simplemachines.org
Personal Signature:
Realitynet.nl -> ExpeditieRobinson.net / PekingExpress.org / WieIsDeMol.Com

yago101


Advertisement: