如何在PHP中发送电子邮件附件

时间:2009-09-30 13:46:28

标签: php

  <?php
  // array with filenames to be sent as attachment
  $files = array("sendFiles.php");

  // email fields: to, from, subject, and so on
  $to = "dfjdsoj@googlemail.com";
  $from = "mail@mail.com";
  $subject ="My subject";
  $message = "A logo has been sen't by". $_SESSION['loggedin_business_name'];
  $headers = "From: $from";

  // boundary 
  $semi_rand = md5(time()); 
  $mime_boundary = "==Multipart_Boundary_x{$semi_rand}x";

  // headers for attachment
  $headers .= "\nMIME-Version: 1.0\n" . "Content-Type: multipart/mixed;\n" . " boundary=\"{$mime_boundary}\"";

  // multipart boundary
  $message = "This is a multi-part message in MIME format.\n\n" . "--{$mime_boundary}\n" . "Content-Type: text/plain; charset=\"iso-8859-1\"\n" . "Content-Transfer-Encoding: 7bit\n\n" . $message . "\n\n";
  $message .= "--{$mime_boundary}\n";

  // preparing attachments
  for($x=0;$x<count($files);$x++){
      $file = fopen($files[$x],"rb");
      $data = fread($file,filesize($files[$x]));
      fclose($file);
      $data = chunk_split(base64_encode($data));
      $message .= "Content-Type: {\"application/octet-stream\"};\n" . " name=\"$files[$x]\"\n" .
      "Content-Disposition: attachment;\n" . " filename=\"$files[$x]\"\n" .
      "Content-Transfer-Encoding: base64\n\n" . $data . "\n\n";
      $message .= "--{$mime_boundary}\n";       
  }

  // send       
  echo sizeof($files);
  $ok = @mail($to, $subject, $message, $headers);
  if ($ok) {
      echo "<p>mail sent to $to!</p>";
  } else {
      echo "<p>mail could not be sent!</p>";
  }
  ?>

我收到一封包含sendfiles.php的电子邮件,然后是一个文本文件ATT00424.txt。数量每次都在变化。发送到我的Gmail,没关系!非常奇怪!


$files = array("sendFiles.php");

  // email fields: to, from, subject, and so on

  $to = "hdfiuhufsadhfu@yaho.com";

  $from = "mail@mail.com";

  $subject ="My subject";

  $message = "A logo has been sen't by". $_POST['loggedin_business_name'];

  $headers = "From: $from";

  // boundary

  $semi_rand = md5(time());

  $mime_boundary = "==Multipart_Boundary_x{$semi_rand}x";

// headers for attachment

  $headers .= "\r\nMIME-Version: 1.0\r\n" . "Content-Type: multipart/mixed;\r\n" . " boundary=\"{$mime_boundary}\"";
  // multipart boundary

  $message = "This is a multi-part message in MIME format.\r\n" . "--{$mime_boundary}\r\n" . "Content-Type: text/plain; charset=\"iso-8859-1\"\r\n" . "Content-Transfer-Encoding: 7bit\r\n" . $message . "\r\n";

  $message .= "--{$mime_boundary}\r\n";
  // preparing attachments

  for($x=0;$x<count($files);$x++){

      $file = fopen($files[$x],"rb");

      $data = fread($file,filesize($files[$x]));

      fclose($file);

      $data = chunk_split(base64_encode($data));

      $message .= "Content-Type: {\"application/octet-stream\"};\r\n" . " name=\"$files[$x]\"\r\n" .

      "Content-Disposition: attachment;\r\n" . " filename=\"$files[$x]\"\r\n" .

      "Content-Transfer-Encoding: base64\r\n" . $data . "\r\n";

      $message .= "--{$mime_boundary}\r\n";

  }

在代码中添加CRLF修复了附件问题但是现在消息“A logo has sen't by”已经消失。这是为什么?

5 个答案:

答案 0 :(得分:2)

尝试使用CRLF(\ r \ n)换行符。对于这些事情,Outlook可能会有点滑稽。

答案 1 :(得分:2)

Use phpMailer()

<?php 
require_once('phpmailer.php');

$mail = new PHPMailer(true); // the true param means it will throw exceptions on errors, which we need to catch
$mail->IsSendmail(); // telling the class to use SendMail transport

try {
    $mail->AddReplyTo('email@example.com', 'First Last');
    $mail->AddAddress('John@example.com', 'John Doe');

    $mail->SetFrom('email@example.com', 'First Last');
    $mail->Subject  =  "Subject Line";
    $mail->AltBody    = "Alternate Text"; // optional, comment out and test

    $mail->WordWrap     =   50; // set word wrap    
    $mail->Body = "This is the body of the email";
    $mail->IsHTML(true); // send as HTML

    // Single or Multiple File Attachments
    $mail->AddAttachment('../path-to-file.pdf', 'File-Name.pdf');
    $mail->Send(); // Try to send email
    //echo "Message Sent OK<p></p>\n";
    } catch (phpmailerException $e) {
        echo $e->errorMessage(); //Pretty error messages from PHPMailer
    } catch (Exception $e) {
        echo $e->getMessage(); //Boring error messages from anything else!
}
// end try


?>

答案 2 :(得分:1)

您可以使用此课程

<?php   

/*   
Usage   
=====   
    set $this->to
    set $this->subject
    set $this->message (with html tags)
    set $this->from (Optional)
    set $this->cc (this can be an array or a variable) (Optional)
    set $this->bcc (this can be an array or a variable) (Optional)
    set $this->reply_to (Optional)
    set $this->return_path (Optional)
    set $this->x_mailer (Optional)
    set $this->attach_file_name (this can be an array or a variable) (Optional)

    $this->SendMail();

This function returns an array of 2 elements which e[0] = true (on success) or false and e[1] = message
*/

class EMail
{
    var $to;
    var $from;
    var $cc;
    var $bcc;
    var $reply_to;
    var $return_path;
    var $x_mailer;
    var $subject;
    var $message;
    var $attach_file_name;

    function EMail()
    {
        $this->to = "";
        $this->subject = "";
        $this->message = "";
        $this->from = "Administrator <admin@" . $_SERVER['SERVER_NAME'] . ">";
        $this->cc = "";
        $this->bcc = "";
        $this->reply_to = $this->from;
        $this->return_path = $this->from;
        $this->x_mailer = "PHP v" . phpversion();
        $this->attach_file_name = "";
    }

    function makeFileName ($url)
    {
        $pos=true;
        $PrePos=0;
        while (!$pos==false)
        {
            $pos = strpos($url,'\\',$PrePos);
            if ($pos===false)
            {
                $temp = substr($url,$PrePos);
            }
            else
            {
                $PrePos = $pos + 1;
            }
        }
        return $temp;
    }

    function processAttachment()
    {
        if(is_array($this->attach_file_name))
        {
            $s = sizeof($this->attach_file_name);
            for($i=0; $i<$s; $i++)
            {
                if($this->attach_file_name[$i] != "")
                {
                    $handle = fopen($this->attach_file_name[$i], 'rb');
                    $file_contents = fread($handle, filesize($this->attach_file_name[$i]));
                    $Attach['contents'][$i] = chunk_split(base64_encode($file_contents));
                    fclose($handle);
                    $Attach['file_name'][$i] = $this->makeFileName ($this->attach_file_name[$i]);
                    $pos=true;
                    $PrePos=0;
                    while (!$pos==false)
                    {
                        $pos = strpos($this->attach_file_name[$i], '.', $PrePos);
                        if ($pos===false)
                        {
                            $Attach['file_type'][$i] = substr($this->attach_file_name[$i], $PrePos);
                        }
                        else
                        {
                            $PrePos = $pos+1;
                        }
                    }
                }
            }
            return $Attach;
        }
        else
        {
            $handle = fopen($this->attach_file_name, 'rb');
            $file_contents = fread($handle, filesize($this->attach_file_name));
            $Attach['contents'][0] = chunk_split(base64_encode($file_contents));
            fclose($handle);
            $Attach['file_name'][0] = $this->makeFileName ($this->attach_file_name);
            $pos=true;
            $PrePos=0;
            while (!$pos==false)
            {
                $pos = strpos($this->attach_file_name, '.', $PrePos);
                if ($pos===false)
                {
                    $Attach['file_type'][0] = substr($this->attach_file_name, $PrePos);
                }
                else
                {
                    $PrePos = $pos+1;
                }
            }
        }
        return $Attach;
    }

    function validateMailAddress($MAddress)
    {
        if (eregi("@", $MAddress) && eregi(".", $MAddress))
        {
            return true;
        }
        else
        {
            return false;
        }
    }

    function Validate()
    {
        if(is_array($this->to))
        {
            $msg[0] = false;
            $msg[1] = "You should provide only one receiver email address";
            return $msg;
        }
        if(is_array($this->from))
        {
            $msg[0] = false;
            $msg[1] = "You should provide only one sender email address";
            return $msg;
        }
        if($this->to == "")
        {
            $msg[0] = false;
            $msg[1] = "You should provide a receiver email address";
            return $msg;
        }
        if($this->subject == "")
        {
            $msg[0] = false;
            $msg[1] = "You should provide a subject for your email";
            return $msg;
        }
        if($this->message == "")
        {
            $msg[0] = false;
            $msg[1] = "You should provide message for your email";
            return $msg;
        }
        if(!$this->validateMailAddress($this->to))
        {
            $msg[0] = false;
            $msg[1] = "Receiver E-Mail Address is not valid";
            return $msg;
        }
        if(!$this->validateMailAddress($this->from))
        {
            $msg[0] = false;
            $msg[1] = "Sender E-Mail Address is not valid";
            return $msg;
        }
        if(is_array($this->cc))
        {
            $s = sizeof($this->cc);
            for($i=0; $i<$s; $i++)
            {
                if(!$this->validateMailAddress($this->cc[$i]) && $this->cc[$i] != "")
                {
                    $msg[0] = false;
                    $msg[1] = $this->cc[$i] . " is not a valid E-Mail Address";
                    return $msg;
                }
            }
        }
        else
        {
            if(!$this->validateMailAddress($this->cc) && $this->cc[$i] != "")
            {
                $msg[0] = false;
                $msg[1] = "CC E-Mail Address is not valid";
                return $msg;
            }
        }
        if(is_array($this->bcc))
        {
            $s = sizeof($this->bcc);
            for($i=0; $i<$s; $i++)
            {
                if(!$this->validateMailAddress($this->bcc[$i]) && $this->bcc[$i] != "")
                {
                    $msg[0] = false;
                    $msg[1] = $this->bcc[$i] . " is not a valid E-Mail Address";
                    return $msg;
                }
            }
        }
        else
        {
            if(!$this->validateMailAddress($this->bcc) && $this->bcc[$i] != "")
            {
                $msg[0] = false;
                $msg[1] = "BCC E-Mail Address is not valid";
                return $msg;
            }
        }
        if(is_array($this->reply_to))
        {
            $msg[0] = false;
            $msg[1] = "You should provide only one Reply-to address";
            return $msg;
        }
        else
        {
            if(!$this->validateMailAddress($this->reply_to))
            {
                $msg[0] = false;
                $msg[1] = "Reply-to E-Mail Address is not valid";
                return $msg;
            }
        }
        if(is_array($this->return_path))
        {
            $msg[0] = false;
            $msg[1] = "You should provide only one Return-Path address";
            return $msg;
        }
        else
        {
            if(!$this->validateMailAddress($this->return_path))
            {
                $msg[0] = false;
                $msg[1] = "Return-Path E-Mail Address is not valid";
                return $msg;
            }
        }
        $msg[0] = true;
        return $msg;
    }

    function SendMail()
    {
        $mess = $this->Validate();
        if(!$mess[0])
        {
            return $mess;
        }

        # Common Headers
        $headers  = "From: " . $this->from . "\r\n";
        $headers .= "To: <" . $this->to . ">\r\n";

        if(is_array($this->cc))
        {
            $headers .= "Cc: " . implode(", ", $this->cc) . "\r\n";
        }
        else
        {
            if($this->cc != "")
                $headers .= "Cc: " . $this->cc . "\r\n";
        }

        if(is_array($this->bcc))
        {
            $headers .= "BCc: " . implode(", ", $this->bcc) . "\r\n";
        }
        else
        {
            if($this->bcc != "")
                $headers .= "BCc: " . $this->bcc . "\r\n";
        }

        // these two to set reply address
        $headers .= "Reply-To: " . $this->reply_to . "\r\n";
        $headers .= "Return-Path: " . $this->return_path . "\r\n";

        // these two to help avoid spam-filters
        $headers .= "Message-ID: <message-on " . date("d-m-Y h:i:s A") . "@".$_SERVER['SERVER_NAME'].">\r\n";
        $headers .= "X-Mailer: " . $this->x_mailer . "\r\n";
        $headers .= "MIME-Version: 1.0\r\n";

        # Tell the E-Mail client to look for multiple parts or chunks
        $headers .= "Content-type: multipart/mixed; boundary=AttachMail0123456\r\n";

        # Message Starts here
        $msg  = "--AttachMail0123456\r\n";

        $msg .= "Content-type: multipart/alternative; boundary=AttachMail7890123\r\n\r\n";
        $msg .= "--AttachMail7890123\r\n";

        $msg .= "Content-Type: text/plain; charset=iso-8859-1\r\n";
        $msg .= "Content-Transfer-Encoding: quoted-printable\r\n\r\n";

        $msg .= strip_tags($this->message) . "\r\n";

        $msg .= "--AttachMail7890123\r\n";

        $msg .= "Content-Type: text/html; charset=iso-8859-1\r\n";
        $msg .= "Content-Transfer-Encoding: quoted-printable\r\n\r\n";

        $msg .= "<html><head></head><body>" . $this->message . "</body></html>\r\n";

        $msg .= "--AttachMail7890123--\r\n";


        if($this->attach_file_name != "" || is_array($this->attach_file_name))
        {
            $Attach = $this->processAttachment();

            $s = sizeof($Attach['file_name']);
            for($i=0; $i<$s; $i++)
            {
                # Start of Attachment chunk
                $msg .= "--AttachMail0123456\r\n";

                if ($Attach['file_type'][$i]=="gif")
                {
                    $msg .= "Content-Type: image/gif; name=" . $Attach['file_name'][$i] . "\r\n";
                }
                elseif ($Attach['file_type'][$i]=="jpg" || $Attach['file_type'][$i]=="jpeg")
                {
                    $msg .= "Content-Type: image/jpeg; name=" . $Attach['file_name'][$i] . "\r\n";
                }
                else
                {
                    $msg .= "Content-Type: application/file; name=" . $Attach['file_name'][$i] . "\r\n";
                }

                $msg .= "Content-Transfer-Encoding: base64\r\n";
                $msg .= "Content-Disposition: attachment; filename=" . $Attach['file_name'][$i] . "\r\n\r\n";

                $msg .= $Attach['contents'][$i] . "\r\n";
            }
        }

        $msg .= "--AttachMail0123456--";

        $result = mail($this->to, $this->subject, $msg, $headers);
        if ($result)
        {
            $mess[0] = true;
            $mess[1] = "Mail Successfully delivered";
        }
        else
        {
            $mess[0] = false;       
            $mess[1] = "Mail can not be send this time. Please try latter.";
        }
        return $mess;
    }
}
?>

答案 3 :(得分:0)

$from = stripslashes("from@demo.com");
$to = stripslashes("to@to.com");
$subject =$_POST['subject'];  
$message = $_POST['mailbody'];  

// Temporary paths of selected files  
$file1 = $_FILES['file1']['tmp_name'];  
$file2 = $_FILES['file2']['tmp_name'];  
$file3 = $_FILES['file3']['tmp_name'];  

// File names of selected files  
$filename1 = $_FILES['file1']['name'];  
$filename2 = $_FILES['file2']['name'];  
$filename3 = $_FILES['file3']['name'];  

// array of filenames to be as attachments  
$files = array($file1, $file2, $file3);  
$filenames = array($filename1, $filename2, $filename3);  

// include the from email in the headers  
$headers = "From: $from";  

// boundary  
$time = md5(time());  
$boundary = "==Multipart_Boundary_x{$time}x";  

// headers used for send attachment with email  
$headers .= "\nMIME-Version: 1.0\n" . "Content-Type: multipart/mixed;\n" . " boundary=\"{$boundary}\"";  

// multipart boundary  
$message = "--{$boundary}\n" . "Content-Type: text/plain; charset=\"iso-8859-1\"\n" . "Content-Transfer-Encoding: 7bit\n\n" . $message . "\n\n";  
$message .= "--{$boundary}\n";  

// attach the attachments to the message  
for($x = 0; $x < count($files); $x++){

    if($files[$x] != ""){

        $file = fopen($files[$x],"r");  
        $content = fread($file,filesize($files[$x]));  
        fclose($file);  
        $content = chunk_split(base64_encode($content));  
        $message .= "Content-Type: {\"application/octet-stream\"};\n" . " name=\"$files[$x]\"\n" . "Content-Disposition: attachment;\n" . " filename=\"$filenames[$x]\"\n" . "Content-Transfer-Encoding: base64\n\n" . $content . "\n\n";  
        $message .= "--{$boundary}\n";
    }
}  

// sending mail  
$sendmail = mail($to, $subject, $message, $headers);

答案 4 :(得分:-1)

据我了解,Outlook在收到带有混合编码的部分中的邮件时会创建ATT12345.txt附件。如果在更改编码(或新的MIME部分)后无法转换邮件的其余部分,则会将其余部分转储到附件中,并附带您已看到的通用名称。似乎Gmail比Outlook更好地处理格式(不足为奇)。

我不是Outlook专家(从不接触过这个东西),但看起来好像this answer on SO可能会有所帮助(检查你的$ mime_boundary变量是否在最后一部分之后进行了' - ')。