email - मेल मल्टीपार्ट/वैकल्पिक बनाम मल्टीपार्ट/मिश्रित




smtp content-type (5)

इयान के उदाहरण पर बिल्डिंग, मुझे इन ईमेल को अलग-अलग सादे टेक्स्ट, एचटीएमएल और एकाधिक अनुलग्नकों के साथ लिखने की समान आवश्यकता थी, लेकिन PHP का उपयोग करना। चूंकि हम संलग्नक के साथ ईमेल भेजने के लिए अमेज़ॅन एसईएस का उपयोग कर रहे हैं, इसलिए एपीआई को वर्तमान में sendRawEmail (...) फ़ंक्शन का उपयोग करके स्क्रैच से ईमेल बनाने की आवश्यकता है।

अधिक जांच के बाद (और सामान्य निराशा से अधिक), समस्या हल हो गई थी और PHP स्रोत कोड पोस्ट किया गया था ताकि यह किसी अन्य समस्या का सामना करने में दूसरों की सहायता कर सके। उम्मीद है कि यह किसी की मदद करेगा - इस समस्या पर काम करने के लिए मजबूर बंदरों की सेना अब थक गई है।

अमेज़ॅन एसईएस का उपयोग कर अनुलग्नक के साथ ईमेल भेजने के लिए PHP स्रोत कोड।

<?php

require_once('AWSSDKforPHP/aws.phar');

use Aws\Ses\SesClient;

/**
 * SESUtils is a tool to make it easier to work with Amazon Simple Email Service
 * Features:
 * A client to prepare emails for use with sending attachments or not
 * 
 * There is no warranty - use this code at your own risk.  
 * @author sbossen with assistance from Michael Deal
 * http://righthandedmonkey.com
 *
 * Update: Error checking and new params input array provided by Michael Deal
 * Update2: Corrected for allowing to send multiple attachments and plain text/html body
 *   Ref: Http://stackoverflow.com/questions/3902455/smtp-multipart-alternative-vs-multipart-mixed/
 */
class SESUtils {

    const version = "1.0";
    const AWS_KEY = "YOUR-KEY";
    const AWS_SEC = "YOUR-SECRET";
    const AWS_REGION = "us-east-1";
    const MAX_ATTACHMENT_NAME_LEN = 60;

    /**
     * Usage:
        $params = array(
          "to" => "[email protected]",
          "subject" => "Some subject",
          "message" => "<strong>Some email body</strong>",
          "from" => "[email protected]",
          //OPTIONAL
          "replyTo" => "[email protected]",
          //OPTIONAL
          "files" => array(
            1 => array(
               "name" => "filename1", 
              "filepath" => "/path/to/file1.txt", 
              "mime" => "application/octet-stream"
            ),
            2 => array(
               "name" => "filename2", 
              "filepath" => "/path/to/file2.txt", 
              "mime" => "application/octet-stream"
            ),
          )
        );

      $res = SESUtils::sendMail($params);

     * NOTE: When sending a single file, omit the key (ie. the '1 =>') 
     * or use 0 => array(...) - otherwise the file will come out garbled
     * ie. use:
     *    "files" => array(
     *        0 => array( "name" => "filename", "filepath" => "path/to/file.txt",
     *        "mime" => "application/octet-stream")
     * 
     * For the 'to' parameter, you can send multiple recipiants with an array
     *    "to" => array("[email protected]", "[email protected]")
     * use $res->success to check if it was successful
     * use $res->message_id to check later with Amazon for further processing
     * use $res->result_text to look for error text if the task was not successful
     * 
     * @param array $params - array of parameters for the email
     * @return \ResultHelper
     */
    public static function sendMail($params) {

        $to = self::getParam($params, 'to', true);
        $subject = self::getParam($params, 'subject', true);
        $body = self::getParam($params, 'message', true);
        $from = self::getParam($params, 'from', true);
        $replyTo = self::getParam($params, 'replyTo');
        $files = self::getParam($params, 'files');

        $res = new ResultHelper();

        // get the client ready
        $client = SesClient::factory(array(
                    'key' => self::AWS_KEY,
                    'secret' => self::AWS_SEC,
                    'region' => self::AWS_REGION
        ));

        // build the message
        if (is_array($to)) {
            $to_str = rtrim(implode(',', $to), ',');
        } else {
            $to_str = $to;
        }

        $msg = "To: $to_str\n";
        $msg .= "From: $from\n";

        if ($replyTo) {
            $msg .= "Reply-To: $replyTo\n";
        }

        // in case you have funny characters in the subject
        $subject = mb_encode_mimeheader($subject, 'UTF-8');
        $msg .= "Subject: $subject\n";
        $msg .= "MIME-Version: 1.0\n";
        $msg .= "Content-Type: multipart/mixed;\n";
        $boundary = uniqid("_Part_".time(), true); //random unique string
        $boundary2 = uniqid("_Part2_".time(), true); //random unique string
        $msg .= " boundary=\"$boundary\"\n";
        $msg .= "\n";

        // now the actual body
        $msg .= "--$boundary\n";

        //since we are sending text and html emails with multiple attachments
        //we must use a combination of mixed and alternative boundaries
        //hence the use of boundary and boundary2
        $msg .= "Content-Type: multipart/alternative;\n";
        $msg .= " boundary=\"$boundary2\"\n";
        $msg .= "\n";
        $msg .= "--$boundary2\n";

        // first, the plain text
        $msg .= "Content-Type: text/plain; charset=utf-8\n";
        $msg .= "Content-Transfer-Encoding: 7bit\n";
        $msg .= "\n";
        $msg .= strip_tags($body); //remove any HTML tags
        $msg .= "\n";

        // now, the html text
        $msg .= "--$boundary2\n";
        $msg .= "Content-Type: text/html; charset=utf-8\n";
        $msg .= "Content-Transfer-Encoding: 7bit\n";
        $msg .= "\n";
        $msg .= $body; 
        $msg .= "\n";
        $msg .= "--$boundary2--\n";

        // add attachments
        if (is_array($files)) {
            $count = count($files);
            foreach ($files as $file) {
                $msg .= "\n";
                $msg .= "--$boundary\n";
                $msg .= "Content-Transfer-Encoding: base64\n";
                $clean_filename = self::clean_filename($file["name"], self::MAX_ATTACHMENT_NAME_LEN);
                $msg .= "Content-Type: {$file['mime']}; name=$clean_filename;\n";
                $msg .= "Content-Disposition: attachment; filename=$clean_filename;\n";
                $msg .= "\n";
                $msg .= base64_encode(file_get_contents($file['filepath']));
                $msg .= "\n--$boundary";
            }
            // close email
            $msg .= "--\n";
        }

        // now send the email out
        try {
            $ses_result = $client->sendRawEmail(
                    array(
                'RawMessage' => array(
                    'Data' => base64_encode($msg)
                )
                    ), array(
                'Source' => $from,
                'Destinations' => $to_str
                    )
            );
            if ($ses_result) {
                $res->message_id = $ses_result->get('MessageId');
            } else {
                $res->success = false;
                $res->result_text = "Amazon SES did not return a MessageId";
            }
        } catch (Exception $e) {
            $res->success = false;
            $res->result_text = $e->getMessage().
                    " - To: $to_str, Sender: $from, Subject: $subject";
        }
        return $res;
    }

    private static function getParam($params, $param, $required = false) {
        $value = isset($params[$param]) ? $params[$param] : null;
        if ($required && empty($value)) {
            throw new Exception('"'.$param.'" parameter is required.');
        } else {
            return $value;
        }
    }

    /**
    Clean filename function - to get a file friendly 
    **/
    public static function clean_filename($str, $limit = 0, $replace=array(), $delimiter='-') {
        if( !empty($replace) ) {
            $str = str_replace((array)$replace, ' ', $str);
        }

        $clean = iconv('UTF-8', 'ASCII//TRANSLIT', $str);
        $clean = preg_replace("/[^a-zA-Z0-9\.\/_| -]/", '', $clean);
        $clean = preg_replace("/[\/| -]+/", '-', $clean);

        if ($limit > 0) {
            //don't truncate file extension
            $arr = explode(".", $clean);
            $size = count($arr);
            $base = "";
            $ext = "";
            if ($size > 0) {
                for ($i = 0; $i < $size; $i++) {
                    if ($i < $size - 1) { //if it's not the last item, add to $bn
                        $base .= $arr[$i];
                        //if next one isn't last, add a dot
                        if ($i < $size - 2)
                            $base .= ".";
                    } else {
                        if ($i > 0)
                            $ext = ".";
                        $ext .= $arr[$i];
                    }
                }
            }
            $bn_size = mb_strlen($base);
            $ex_size = mb_strlen($ext);
            $bn_new = mb_substr($base, 0, $limit - $ex_size);
            // doing again in case extension is long
            $clean = mb_substr($bn_new.$ext, 0, $limit); 
        }
        return $clean;
    }

}

class ResultHelper {

    public $success = true;
    public $result_text = "";
    public $message_id = "";

}

?>

ईमेल संदेश बनाते समय आपको टेक्स्ट और अनुलग्नक भेजते समय HTML और टेक्स्ट या multipart/mixed भेजते समय multipart/alternative में Content-Type सेट करना होता है।

तो यदि आप HTML, टेक्स्ट और अनुलग्नक भेजना चाहते हैं तो आप क्या करते हैं? दोनों का उपयोग करें?


महान उत्तर लैन!

इस काम को व्यापक उपकरणों में बनाने के लिए मैंने कुछ काम किया था। अंत में मैं उन ग्राहकों की सूची दूंगा जिन पर मैंने परीक्षण किया था।

  1. मैंने एक नया निर्माण कन्स्ट्रक्टर जोड़ा जिसमें पैरामीटर अनुलग्नक नहीं थे और उन्होंने माइम मल्टीपार्ट ("मिश्रित") का उपयोग नहीं किया। यदि आप केवल इनलाइन छवियां भेज रहे हैं तो मिश्रित करने की कोई आवश्यकता नहीं है।

    public Multipart build(String messageText, String messageHtml, List<URL> messageHtmlInline) throws MessagingException {
    
        final Multipart mpAlternative = new MimeMultipart("alternative");
        {
            //  Note: MUST RENDER HTML LAST otherwise iPad mail client only renders 
            //  the last image and no email
                addTextVersion(mpAlternative,messageText);
                addHtmlVersion(mpAlternative,messageHtml, messageHtmlInline);
        }
    
        return mpAlternative;
    }
    
  2. AddTextVersion विधि में मैंने सामग्री जोड़ते समय वर्णमाला को जोड़ा, शायद यह पारित किया जा सकता है / लेकिन मैंने इसे स्थिर रूप से जोड़ा है।

    textPart.setContent(messageText, "text/plain");
    to
    textPart.setContent(messageText, "text/plain; charset=UTF-8");
    
  3. अंतिम आइटम addImagesInline विधि में जोड़ रहा था। मैंने निम्नलिखित कोड द्वारा शीर्षलेख में छवि फ़ाइल नाम सेट करना जोड़ा। यदि आप ऐसा नहीं करते हैं तो कम से कम एंड्रॉइड डिफ़ॉल्ट मेल क्लाइंट पर इसमें इनलाइन छवियां होंगी जिनके पास अज्ञात नाम है और वे स्वचालित रूप से उन्हें डाउनलोड नहीं करेंगे और ईमेल में उपस्थित नहीं होंगे।

    for (URL img : embeded) {
        final MimeBodyPart htmlPartImg = new MimeBodyPart();
        DataSource htmlPartImgDs = new URLDataSource(img);
        htmlPartImg.setDataHandler(new DataHandler(htmlPartImgDs));
        String fileName = img.getFile();
        fileName = getFileName(fileName);
        String newFileName = cids.get(fileName);
        boolean imageNotReferencedInHtml = newFileName == null;
        if (imageNotReferencedInHtml) continue;
        htmlPartImg.setHeader("Content-ID", "<"+newFileName+">");
        htmlPartImg.setDisposition(BodyPart.INLINE);
        **htmlPartImg.setFileName(newFileName);**
        parent.addBodyPart(htmlPartImg);
    }
    

तो आखिरकार, यह उन ग्राहकों की सूची है जिन पर मैंने परीक्षण किया था। आउटलुक 2010, आउटलुक वेब ऐप, इंटरनेट एक्सप्लोरर 11, फ़ायरफ़ॉक्स, क्रोम, आउटलुक ऐप्पल के मूल ऐप का उपयोग करते हुए, ईमेल जीमेल के माध्यम से जा रहा है - ब्राउज़र मेल क्लाइंट, इंटरनेट एक्सप्लोरर 11, फ़ायरफ़ॉक्स, क्रोम, एंड्रॉइड डिफॉल्ट मेल क्लाइंट, ओएसएक्स आईफोन डिफ़ॉल्ट मेल क्लाइंट, जीमेल एंड्रॉइड पर मेल क्लाइंट, आईफोन पर जीमेल मेल क्लाइंट, याहू - ब्राउजर मेल क्लाइंट, इंटरनेट एक्सप्लोरर 11, फ़ायरफ़ॉक्स, क्रोम, एंड्रॉइड डिफॉल्ट मेल क्लाइंट, ओएसएक्स आईफोन डिफ़ॉल्ट मेल क्लाइंट के माध्यम से जा रहा ईमेल।

उम्मीद है कि किसी और की मदद करता है।


मैंने इस मुद्दे को मारा। इस वास्तुकला (लैन के उत्तर से) मेरे लिए काम किया। पाइथन में समाधान यहां है।

  • मिश्रित
    • विकल्प
      • टेक्स्ट
      • सम्बंधित
        • एचटीएमएल
        • इनलाइन छवि
        • इनलाइन छवि
    • आसक्ति
    • आसक्ति

मुख्य ईमेल निर्माण कार्य यहां दिया गया है:

def create_message_with_attachment(
    sender, to, subject, msgHtml, msgPlain, attachmentFile):
    """Create a message for an email.

    Args:
      sender: Email address of the sender.
      to: Email address of the receiver.
      subject: The subject of the email message.
      message_text: The text of the email message.
      file: The path to the file to be attached.

    Returns:
      An object containing a base64url encoded email object.
    """
    message = MIMEMultipart('mixed')
    message['to'] = to
    message['from'] = sender
    message['subject'] = subject

    message_alternative = MIMEMultipart('alternative')
    message_related = MIMEMultipart('related')

    message_related.attach(MIMEText(msgHtml, 'html'))
    message_alternative.attach(MIMEText(msgPlain, 'plain'))
    message_alternative.attach(message_related)

    message.attach(message_alternative)

    print "create_message_with_attachment: file:", attachmentFile
    content_type, encoding = mimetypes.guess_type(attachmentFile)

    if content_type is None or encoding is not None:
        content_type = 'application/octet-stream'
    main_type, sub_type = content_type.split('/', 1)
    if main_type == 'text':
        fp = open(attachmentFile, 'rb')
        msg = MIMEText(fp.read(), _subtype=sub_type)
        fp.close()
    elif main_type == 'image':
        fp = open(attachmentFile, 'rb')
        msg = MIMEImage(fp.read(), _subtype=sub_type)
        fp.close()
    elif main_type == 'audio':
        fp = open(attachmentFile, 'rb')
        msg = MIMEAudio(fp.read(), _subtype=sub_type)
        fp.close()
    else:
        fp = open(attachmentFile, 'rb')
        msg = MIMEBase(main_type, sub_type)
        msg.set_payload(fp.read())
        fp.close()
    filename = os.path.basename(attachmentFile)
    msg.add_header('Content-Disposition', 'attachment', filename=filename)
    message.attach(msg)

    return {'raw': base64.urlsafe_b64encode(message.as_string())}

एचटीएमएल / टेक्स्ट / अटैचमेंट युक्त ईमेल भेजने के लिए पूर्ण कोड यहां दिया गया है:

import httplib2
import os
import oauth2client
from oauth2client import client, tools
import base64
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from apiclient import errors, discovery
import mimetypes
from email.mime.image import MIMEImage
from email.mime.audio import MIMEAudio
from email.mime.base import MIMEBase

SCOPES = 'https://www.googleapis.com/auth/gmail.send'
CLIENT_SECRET_FILE1 = 'client_secret.json'
location = os.path.realpath(
    os.path.join(os.getcwd(), os.path.dirname(__file__)))
CLIENT_SECRET_FILE = os.path.join(location, CLIENT_SECRET_FILE1)
APPLICATION_NAME = 'Gmail API Python Send Email'

def get_credentials():
    home_dir = os.path.expanduser('~')
    credential_dir = os.path.join(home_dir, '.credentials')
    if not os.path.exists(credential_dir):
        os.makedirs(credential_dir)
    credential_path = os.path.join(credential_dir,
                                   'gmail-python-email-send.json')
    store = oauth2client.file.Storage(credential_path)
    credentials = store.get()
    if not credentials or credentials.invalid:
        flow = client.flow_from_clientsecrets(CLIENT_SECRET_FILE, SCOPES)
        flow.user_agent = APPLICATION_NAME
        credentials = tools.run_flow(flow, store)
        print 'Storing credentials to ' + credential_path
    return credentials

def SendMessageWithAttachment(sender, to, subject, msgHtml, msgPlain, attachmentFile):
    credentials = get_credentials()
    http = credentials.authorize(httplib2.Http())
    service = discovery.build('gmail', 'v1', http=http)
    message1 = create_message_with_attachment(sender, to, subject, msgHtml, msgPlain, attachmentFile)
    SendMessageInternal(service, "me", message1)

def SendMessageInternal(service, user_id, message):
    try:
        message = (service.users().messages().send(userId=user_id, body=message).execute())
        print 'Message Id: %s' % message['id']
        return message
    except errors.HttpError, error:
        print 'An error occurred: %s' % error
        return "error"

def create_message_with_attachment(
    sender, to, subject, msgHtml, msgPlain, attachmentFile):
    """Create a message for an email.

    Args:
      sender: Email address of the sender.
      to: Email address of the receiver.
      subject: The subject of the email message.
      message_text: The text of the email message.
      file: The path to the file to be attached.

    Returns:
      An object containing a base64url encoded email object.
    """
    message = MIMEMultipart('mixed')
    message['to'] = to
    message['from'] = sender
    message['subject'] = subject

    message_alternative = MIMEMultipart('alternative')
    message_related = MIMEMultipart('related')

    message_related.attach(MIMEText(msgHtml, 'html'))
    message_alternative.attach(MIMEText(msgPlain, 'plain'))
    message_alternative.attach(message_related)

    message.attach(message_alternative)

    print "create_message_with_attachment: file:", attachmentFile
    content_type, encoding = mimetypes.guess_type(attachmentFile)

    if content_type is None or encoding is not None:
        content_type = 'application/octet-stream'
    main_type, sub_type = content_type.split('/', 1)
    if main_type == 'text':
        fp = open(attachmentFile, 'rb')
        msg = MIMEText(fp.read(), _subtype=sub_type)
        fp.close()
    elif main_type == 'image':
        fp = open(attachmentFile, 'rb')
        msg = MIMEImage(fp.read(), _subtype=sub_type)
        fp.close()
    elif main_type == 'audio':
        fp = open(attachmentFile, 'rb')
        msg = MIMEAudio(fp.read(), _subtype=sub_type)
        fp.close()
    else:
        fp = open(attachmentFile, 'rb')
        msg = MIMEBase(main_type, sub_type)
        msg.set_payload(fp.read())
        fp.close()
    filename = os.path.basename(attachmentFile)
    msg.add_header('Content-Disposition', 'attachment', filename=filename)
    message.attach(msg)

    return {'raw': base64.urlsafe_b64encode(message.as_string())}


def main():
    to = "[email protected]"
    sender = "[email protected]"
    subject = "subject"
    msgHtml = "Hi<br/>Html Email"
    msgPlain = "Hi\nPlain Email"
    attachment = "/path/to/file.pdf"
    SendMessageWithAttachment(sender, to, subject, msgHtml, msgPlain, attachment)

if __name__ == '__main__':
    main()

संदेशों में सामग्री है। सामग्री टेक्स्ट, एचटीएमएल, डेटाहैंडलर या मल्टीपार्ट हो सकती है, और केवल एक ही सामग्री हो सकती है। मल्टीपार्ट्स में केवल बॉडीपार्ट्स हैं लेकिन एक से अधिक हो सकते हैं। बॉडीपार्ट्स, जैसे संदेश, में ऐसी सामग्री हो सकती है जिसे पहले ही वर्णित किया जा चुका है।

एचटीएमएल, टेक्स्ट और एक अटैचमेंट वाला एक संदेश इस तरह श्रेणीबद्ध रूप से देखा जा सकता है:

message
  mainMultipart (content for message, subType="related")
    ->htmlAndTextBodyPart (bodyPart1 for mainMultipart)
      ->htmlAndTextMultipart (content for htmlAndTextBodyPart, subType="alternative")
        ->textBodyPart (bodyPart2 for the htmlAndTextMultipart)
          ->text (content for textBodyPart)
        ->htmlBodyPart (bodyPart1 for htmlAndTextMultipart)
          ->html (content for htmlBodyPart)
    ->fileBodyPart1 (bodyPart2 for the mainMultipart)
      ->FileDataHandler (content for fileBodyPart1 )

और इस तरह के एक संदेश बनाने के लिए कोड:

    // the parent or main part if you will
    Multipart mainMultipart = new MimeMultipart("mixed");

    // this will hold text and html and tells the client there are 2 versions of the message (html and text). presumably text
    // being the alternative to html
    Multipart htmlAndTextMultipart = new MimeMultipart("alternative");

    // set text
    MimeBodyPart textBodyPart = new MimeBodyPart();
    textBodyPart.setText(text);
    htmlAndTextMultipart.addBodyPart(textBodyPart);

    // set html (set this last per rfc1341 which states last = best)
    MimeBodyPart htmlBodyPart = new MimeBodyPart();
    htmlBodyPart.setContent(html, "text/html; charset=utf-8");
    htmlAndTextMultipart.addBodyPart(htmlBodyPart);

    // stuff the multipart into a bodypart and add the bodyPart to the mainMultipart
    MimeBodyPart htmlAndTextBodyPart = new MimeBodyPart();
    htmlAndTextBodyPart.setContent(htmlAndTextMultipart);
    mainMultipart.addBodyPart(htmlAndTextBodyPart);

    // attach file body parts directly to the mainMultipart
    MimeBodyPart filePart = new MimeBodyPart();
    FileDataSource fds = new FileDataSource("/path/to/some/file.txt");
    filePart.setDataHandler(new DataHandler(fds));
    filePart.setFileName(fds.getName());
    mainMultipart.addBodyPart(filePart);

    // set message content
    message.setContent(mainMultipart);

यहां सबसे अच्छा है: अनुलग्नक और इनलाइन छवियों के साथ मल्टीपार्ट / मिश्रित माइम संदेश

और छवि: https://www.qcode.co.uk/images/mime-nesting-structure.png

From: [email protected]
To: [email protected]@qcode.co.uk
Subject: Example Email
MIME-Version: 1.0
Content-Type: multipart/mixed; boundary="MixedBoundaryString"

--MixedBoundaryString
Content-Type: multipart/related; boundary="RelatedBoundaryString"

--RelatedBoundaryString
Content-Type: multipart/alternative; boundary="AlternativeBoundaryString"

--AlternativeBoundaryString
Content-Type: text/plain;charset="utf-8"
Content-Transfer-Encoding: quoted-printable

This is the plain text part of the email.

--AlternativeBoundaryString
Content-Type: text/html;charset="utf-8"
Content-Transfer-Encoding: quoted-printable

<html>
  <body>=0D
    <img src=3D=22cid:masthead.png=40qcode.co.uk=22 width 800 height=3D80=
 =5C>=0D
    <p>This is the html part of the email.</p>=0D
    <img src=3D=22cid:logo.png=40qcode.co.uk=22 width 200 height=3D60 =5C=
>=0D
  </body>=0D
</html>=0D

--AlternativeBoundaryString--

--RelatedBoundaryString
Content-Type: image/jpgeg;name="logo.png"
Content-Transfer-Encoding: base64
Content-Disposition: inline;filename="logo.png"
Content-ID: <[email protected]>

amtsb2hiaXVvbHJueXZzNXQ2XHVmdGd5d2VoYmFmaGpremxidTh2b2hydHVqd255aHVpbnRyZnhu
dWkgb2l1b3NydGhpdXRvZ2hqdWlyb2h5dWd0aXJlaHN1aWhndXNpaHhidnVqZmtkeG5qaG5iZ3Vy
...
...
a25qbW9nNXRwbF0nemVycHpvemlnc3k5aDZqcm9wdHo7amlodDhpOTA4N3U5Nnkwb2tqMm9sd3An
LGZ2cDBbZWRzcm85eWo1Zmtsc2xrZ3g=

--RelatedBoundaryString
Content-Type: image/jpgeg;name="masthead.png"
Content-Transfer-Encoding: base64
Content-Disposition: inline;filename="masthead.png"
Content-ID: <[email protected]>

aXR4ZGh5Yjd1OHk3MzQ4eXFndzhpYW9wO2tibHB6c2tqOTgwNXE0aW9qYWJ6aXBqOTBpcjl2MC1t
dGlmOTA0cW05dGkwbWk0OXQwYVttaXZvcnBhXGtsbGo7emt2c2pkZnI7Z2lwb2F1amdpNTh1NDlh
...
...
eXN6dWdoeXhiNzhuZzdnaHQ3eW9zemlqb2FqZWt0cmZ1eXZnamhka3JmdDg3aXV2dWd5aGVidXdz
dhyuhehe76YTGSFGA=

--RelatedBoundaryString--

--MixedBoundaryString
Content-Type: application/pdf;name="Invoice_1.pdf"
Content-Transfer-Encoding: base64
Content-Disposition: attachment;filename="Invoice_1.pdf"

aGZqZGtsZ3poZHVpeWZoemd2dXNoamRibngganZodWpyYWRuIHVqO0hmSjtyRVVPIEZSO05SVURF
SEx1aWhudWpoZ3h1XGh1c2loZWRma25kamlsXHpodXZpZmhkcnVsaGpnZmtsaGVqZ2xod2plZmdq
...
...
a2psajY1ZWxqanNveHV5ZXJ3NTQzYXRnZnJhZXdhcmV0eXRia2xhanNueXVpNjRvNWllc3l1c2lw
dWg4NTA0

--MixedBoundaryString
Content-Type: application/pdf;name="SpecialOffer.pdf"
Content-Transfer-Encoding: base64
Content-Disposition: attachment;filename="SpecialOffer.pdf"

aXBvY21odWl0dnI1dWk4OXdzNHU5NTgwcDN3YTt1OTQwc3U4NTk1dTg0dTV5OGlncHE1dW4zOTgw
cS0zNHU4NTk0eWI4OTcwdjg5MHE4cHV0O3BvYTt6dWI7dWlvenZ1em9pdW51dDlvdTg5YnE4N3Z3
...
...
OTViOHk5cDV3dTh5bnB3dWZ2OHQ5dTh2cHVpO2p2Ymd1eTg5MGg3ajY4bjZ2ODl1ZGlvcjQ1amts
dfnhgjdfihn=

--MixedBoundaryString--

.

स्कीमा मल्टीपार्ट / संबंधित / वैकल्पिक

Header
|From: email
|To: email
|MIME-Version: 1.0
|Content-Type: multipart/mixed; boundary="boundary1";
Message body
|multipart/mixed --boundary1
|--boundary1
|   multipart/related --boundary2
|   |--boundary2
|   |   multipart/alternative --boundary3
|   |   |--boundary3
|   |   |text/plain
|   |   |--boundary3
|   |   |text/html
|   |   |--boundary3--
|   |--boundary2    
|   |Inline image
|   |--boundary2    
|   |Inline image
|   |--boundary2--
|--boundary1    
|Attachment1
|--boundary1
|Attachment2
|--boundary1
|Attachment3
|--boundary1--
|
.






mime