Error with PHP mail(): Multiple or malformed newlines found in additional_header
Had just the similar problem.
It came out of the blue. No PHP Code was changed.
What was changed: PHP was upgraded 5.5.25-1 to 5.5.26.
A security risk in PHP mail()
function has been fixed and extra newlines in additional_headers
are allowed no more. Because extra newlines mean: now starts the email message (and we surely don't want somebody to inject some newlines through headers followed by an evil message).
What previously have worked fine, e.g. just having extra newlines after headers or even passing the whole message to additional_headers
, will function no more.
Solution:
- Sanitize your headers. No multiple newlines in
additional_headers
argument. These count as "multiple or malformed newlines":\r\r, \r\0, \r\n\r\n, \n\n, \n\0
. - Use
additional_headers
for headers only. Email message (multipart or not, with ir without attachments, etc) belongs inmessage
argument, not in headers.
PHP Security Bug report: https://bugs.php.net/bug.php?id=68776
C Code diff how its fixed: http://git.php.net/?p=php-src.git;a=blobdiff;f=ext/standard/mail.c;h=448013a472a3466245e64b1cb37a9d1b0f7c007e;
hp=1ebc8fecb7ef4c266a341cdc701f0686d6482242;hb=9d168b863e007c4e15ebe4d2eecabdf8b0582e30;
hpb=eee8b6c33fc968ef8c496db8fb54e8c9d9d5a8f9
mail() error in PHP: Multiple or malformed newlines found in additional_header
Your problem is that you're trying to send message body as headers, as mentioned in the comments to your question.
Trying to send MIME mail attachments via mail()
is probably considered torture in some countries. There are plenty of libraries to do this for you, I use the PEAR Mail_Mime package.
function mail_attachment($filename, $mailto, $from_mail, $from_name, $replyto, $subject, $message) {
include("Mail.php");
include("Mail/mime.php");
$headers = [
"To"=>$mailto,
"From"=>"$from_name <$from_mail>",
"Reply-To"=>$replyto
"Subject"=>$subject,
"Date"=>date(DATE_RFC822),
];
$msg = new Mail_mime();
$mail =& Mail::factory("smtp");
$msg->setTXTBody($message);
$msg->addAttachment(file_get_contents($filename), "application/pdf", basename($filename), false);
$body = $msg->get();
$headers = $msg->headers($headers);
$mail->send($email_address, $headers, $body);
}
Regex to get string between curly braces
If your string will always be of that format, a regex is overkill:
>>> var g='{getThis}';
>>> g.substring(1,g.length-1)
"getThis"
substring(1
means to start one character in (just past the first {
) and ,g.length-1)
means to take characters until (but not including) the character at the string length minus one. This works because the position is zero-based, i.e. g.length-1
is the last position.
For readers other than the original poster: If it has to be a regex, use /{([^}]*)}/
if you want to allow empty strings, or /{([^}]+)}/
if you want to only match when there is at least one character between the curly braces. Breakdown:
/
: start the regex pattern{
: a literal curly brace(
: start capturing[
: start defining a class of characters to capture^}
: "anything other than}
"
]
: OK, that's our whole class definition*
: any number of characters matching that class we just defined
)
: done capturing
}
: a literal curly brace must immediately follow what we captured
/
: end the regex pattern
Multiple or malformed newlines found in additional_header
You're inserting your message into your headers:
$headers .= $message.$el;
so you'll have
From: someone@somewhere.com
blah: blah
Hi mom!
Content-type: blah blah
which is an illegal email.
Send attachments with PHP Mail()?
I agree with @MihaiIorga in the comments – use the PHPMailer script. You sound like you're rejecting it because you want the easier option. Trust me, PHPMailer is the easier option by a very large margin compared to trying to do it yourself with PHP's built-in mail()
function. PHP's mail()
function really isn't very good.
To use PHPMailer:
- Download the PHPMailer script from here: http://github.com/PHPMailer/PHPMailer
- Extract the archive and copy the script's folder to a convenient place in your project.
- Include the main script file --
require_once('path/to/file/class.phpmailer.php');
Now, sending emails with attachments goes from being insanely difficult to incredibly easy:
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\Exception;
$email = new PHPMailer();
$email->SetFrom('you@example.com', 'Your Name'); //Name is optional
$email->Subject = 'Message Subject';
$email->Body = $bodytext;
$email->AddAddress( 'destinationaddress@example.com' );
$file_to_attach = 'PATH_OF_YOUR_FILE_HERE';
$email->AddAttachment( $file_to_attach , 'NameOfFile.pdf' );
return $email->Send();
It's just that one line $email->AddAttachment();
-- you couldn't ask for any easier.
If you do it with PHP's mail()
function, you'll be writing stacks of code, and you'll probably have lots of really difficult to find bugs.
Related Topics
Laravel 5.2 Validation Error Not Appearing in Blade
What Kind of String Is This? How to Unserialize This String
PHP: Convert Any String to Utf-8 Without Knowing the Original Character Set, or At Least Try
Login to Remote Site With PHP Curl
PHP - Get Bool to Echo False When False
Using Jquery Ajax to Retrieve Data from MySQL
Isset() and Empty() - What to Use
Sending Email Via PHP Mail Function Goes to Spam
Forcing a Simplexml Object to a String, Regardless of Context
PHP Echo VS PHP Short Echo Tags
Find a Matching or Closest Value in an Array
How to Find the Mime Type of a File With PHP
Why Is Facebook PHP Sdk Getuser Always Returning 0
Insert/Update Helper Function Using Pdo
Correctly Determine If Date String Is a Valid Date in That Format