Troubleshooting
I isolated the process into three components: the email builder (my code), the mailer application, and the sending application (in this case, smtp through postfix). I followed the below process to troubleshoot:
- Changed the mailer application to use the built in PHP mail() function, and I also tried sending using a completely different SMTP box. The problem was persistent no matter what process was used to send the mail.
- I found the place in my code where the completed HTML was being handed off to the mailer application. Adding in a file_put_contents, I could then examine the exact data before it went to the mailer. Taking a look at it through a hex editor revealed that the body did not contain the offending characters
- Finally, I found another mailer application (I was using phpmailer). Swiftmailer is an alternative to phpmailer. I figured that if it was obscure bug with phpmailer, changing the mailing application would clear it up. This also did not solve the problem.
So if everything was working correctly, where could the problem crop up? The only place left to look was the encoding scheme for the emails. Scouring the internet, I found a few suggestions that the problem may be related to the message encoding. In this case, it appeared the problem stemmed from (possibly) a 75 character limit in quoted-printable encodings. This didn't help me, as my emails were being sent using 8-bit encoding.
The solution
Just to see what happened, I changed the encoding settings on phpmailer to use base64 encoding using $mail->Encoding="base64". This solved my problem, though I don't admit to knowing exactly why.
Note: don't confuse this with character set issues. In the past I have seen situations where utf-8 text was being read into an email and sent as ISO-8859-1. When having weird characters showing up in your emails, this is most often the problem (or vice versa).
Archived Comments
Hello,
Your problem is rather similar to what I am having, here is an example of what my text might look like: "he would perf! orm his operation".
You see the "! " inserted in the middle of "perform". How odd. It is messing up my html emails because it'll interrupt the source code.
I do not fully understand your solution- would you mind illustrating in some more detail what it was you did to fix this very similar problem you were having?
I am only sending my html mails using the mail() function built into PHP, and I am encoding that email using charset=iso-8859-1 though it doesn't seem to matter if I use utf-8.
Very hopefully in SLC,
Nik
Posted by Nik on January 18th, 2008
Nik,
I think you're confusing character encoding with mime content transfer encoding.
First, if you're sending using ISO-8859-1, you need to make sure your database or wherever you're getting the text from is delivering it is in the same encoding format (see my earlier posts).
If so, try looking at the mime transfer encoding (base64, 8-bit, quoted-printable, etc). I use phpmailer (http://phpmailer.codeworxtech.com/) to send emails, and i'd recommend it.
A quick look at the mail() php manual page, it appears that the following setting may help you:
"Apparently if using the mbstring library, and using overriden functions, the "mail" command appears to use "Content-Transfer-Encoding: BASE64" by default. Which if you combine it with PEAR Mail_Mime you'll get mails that, although they appear RFC compliant, not mailer can read correctly.
To fix this it appears you should add a fixed header in the mail command (this one assumes the pear mime module is 7bit clean, perhaps 8bit would also be fine)
$headers['Content-Transfer-Encoding'] = '7bit';"
Good luck,
Jeremy
Posted by Jeremy on February 04th, 2008
Nik,
Also, you might take a look at the email content in a hex editor to figure out whether the exclamation point is really an exclamation point or just confusion over the text encoding of the email.
Posted by Jeremy on February 04th, 2008
Have you tried inserting your own line breaks? How long of an email are we talking about? The SMTP server may be inserting it's own line breaks at will to keep any single line from being over a certain limit. Base64 has a limit of 76 characters per line, so if you look at the character output you should see a nicely aligned block of text.
Posted by James on February 28th, 2008
rtyey
Posted by Anonymous on June 02nd, 2008
Hi guys,
I also had the rogue "!" problem Nik was having, i.e. "perform" comes out as "per !form"
It was driving me crazy until I googled and found this.
I am using phpmailer as Jeremy is (it's good I recommend it - no pont re-inventing the wheel) and my problems were solved by adding the suggested fix:
$mail->Encoding="base64";
Thanks guys, you saved my weekend and health!
cheers
Alex
Posted by Alex Seymour on February 22nd, 2009
I think the reason setting $phpmailer->Encoding = "base64"; cures the random spaces is because it causes the data to get encoded into a form which adheres to the 998 octets per line limit. For me the problem was happening when the HTML in the email had lines which exceeded 998 chars before a line break. See http://en.wikipedia.org/wiki/MIME#Content-Transfer-Encoding
Posted by Jon Nott on June 17th, 2009
Thanks a mil! Worked perfectly!
Posted by Jeff on August 28th, 2009
Absolutely genius - just the problem I was having. A white space being inserted in phpMailer scripts randomly after a certain char count. I had tried to resolve this for AGES! This should be documented in the phpMailer files. Pat on back to all.
Posted by Lewis on December 15th, 2009
Awesome, thanks for the solution. I did change phpmailer class from 8bit to base64 and it worked like a charm. I'd been changing all sorts of variables for the past few hours trying to get those exclamation marks to go away.
Posted by Victor on January 13th, 2010
I had this same problem using the Pear Mail_Mime class. By using base64 encoding when preparing the email the problem was fixed. You need to set the encoding with the $mime->get() method like so.. $body = $mime->get(array('html_encoding'=>'base64'));
Hope this helps
Posted by Freed on March 30th, 2010
This was very helpful. I dropped in the line of code with the base64 encoding change and it fixed my problem. Thank you very much for posting.
Posted by L on July 13th, 2010
Adding a /n/r into your PHP code at every 990 characters or less fixes the problem if you're using PHP's standard mail() function. The extra space (which in reality is a linebreak and a space was breaking longs links in my messages. Not anymore! Thanks for the posts everyeone!
Posted by Zoltan on August 05th, 2010
I have exactly the same problem. Sometimes it a space in the middle of the word, sometimes it messes up the html syntax (eg. doesn't close a )...
adding /n/r does not seem to help, and I am not quite sure where/how to add $mail->Encoding="base64";.
Using the standard php mail command, in this syntax:
if (mail($to,$subject,$msg,$headers)) {
header('Location: complete.php');
} else
{
header('Location: incomplete.php');
}
NB. These are the headers:
$headers = "MIME-Version: 1.0rn";
$headers .= "Content-type: text/html; charset=iso-8859-1rn";
Any help would be truly appreciated!
Posted by Richard Crampton on October 27th, 2010
Thankyou, thankyou, thankyou. Saved my day and a lot of debugging with a lot of potential error sources! Thanks for taking the time to write this up.
Posted by Kristian on October 27th, 2010
Thnx for the tip, it works 100%
Posted by Marcel on November 06th, 2010