Zend\Mime\Part: getEncodedStream() returns wrong lineend in the conext of a mail #3174

Closed
kbabioch opened this Issue Dec 5, 2012 · 1 comment

Comments

Projects
None yet
2 participants
Contributor

kbabioch commented Dec 5, 2012

Hi,

I'm no expert on email headers and topics coming along with this. However I'm pretty sure that I've stumbled upon something that wasn't considered properly. To my best knowledge the only option to send an attachment by mail right now with ZF2 is to built up the message containing the different MIME parts "manually" as there is no "createAttachment" function.

In my case it looks something like this:

$text = new MimePart($mail['body']);
$text->type = \Zend\Mime\Mime::TYPE_TEXT;

$file = new MimePart(fopen($mail['attachment_filepath'], 'r'));
$file->encoding = \Zend\Mime\Mime::ENCODING_BASE64;
$file->type = finfo_file(finfo_open(), $mail['attachment_filepath'], FILEINFO_MIME_TYPE);
$file->disposition = \Zend\Mime\Mime::DISPOSITION_ATTACHMENT;
$file->filename =basename($mail['attachment_filepath']);

$mail['body'] = new MimeMessage();
$mail['body']->setParts(array($text, $file));

$message = new Message();
$message->setBody($mail['body']);
$message->setFrom($mail['from']);
$message->addTo($mail['to']);
$message->setSubject($mail['subject']);

$transport->send($message);

This works fine - more or less - for small files, but not for "big" ones. The problem is the following: The attachment gets base64 encoded by "getEncodedStream()" within \Zend\Mime\Part. It will be broken down into lines, where each line is 76 characters long. The break character is "Mime::LINEEND", which in itself is "\n".

In the context of a mail "\r\n" must be used for a proper linebreak. "\n" won't be recognized, so basically the complete attachment is considered to be in one line, which will result in an error once the line limit is reached. The server will respond with something like "Syntax error - line to long".

As already said I'm in no way or form an expert on these topics and not too familiar with the RFCs involved, so I'm not quite sure why "Mime::LINEEND" is "\n" rather than "\r\n", but in case that a simple "\n" is also valid in some cases, a switch of some sort might be needed. Maybe this could be realized as a parameter to "getEncodedStream()".

Contributor

kbabioch commented Dec 12, 2012

For the time being the issue could be solved by handing over the complete file content via file_get_contents() instead of a resource with fopen(), as the linebreaking of a string will be done correctly in that case. However it is not the most elegant solution (e.g. because of the RAM usage) and there even might be cases where this is not possible (e.g. when dealing with network streams). I've submitted a pull request with a change that is pretty much straightforward, see d94b15c.

Maks3w closed this Jan 19, 2013

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment