func EnvelopeFromPart(root *Part) (*Envelope, error) {
	e := &Envelope{
		Root:   root,
		header: &root.Header,
	}

	if detectMultipartMessage(root) {
		// Multi-part message (message with attachments, etc)
		if err := parseMultiPartBody(root, e); err != nil {
			return nil, err
		}
	} else {
		if detectBinaryBody(root) {
			// Attachment only, no text
			if root.Disposition == cdInline {
				e.Inlines = append(e.Inlines, root)
			} else {
				e.Attachments = append(e.Attachments, root)
			}
		} else {
			// Only text, no attachments
			if err := parseTextOnlyBody(root, e); err != nil {
				return nil, err
			}
		}
	}

	// Down-convert HTML to text if necessary
	if e.Text == "" && e.HTML != "" {
		// We always warn when this happens
		e.Root.addWarning(
			ErrorPlainTextFromHTML,
			"Message did not contain a text/plain part")
		var err error
		if e.Text, err = html2text.FromString(e.HTML); err != nil {
			// Downcoversion shouldn't fail
			e.Text = ""
			p := e.Root.BreadthMatchFirst(matchHTMLBodyPart)
			p.addError(
				ErrorPlainTextFromHTML,
				"Failed to downconvert HTML: %v",
				err)
		}
	}

	// Copy part errors into Envelope.
	if e.Root != nil {
		_ = e.Root.DepthMatchAll(func(part *Part) bool {
			// Using DepthMatchAll to traverse all parts, don't care about result.
			for i := range part.Errors {
				// Range index is needed to get the correct address, because range value points to
				// a locally scoped variable.
				e.Errors = append(e.Errors, part.Errors[i])
			}
			return false
		})
	}

	return e, nil
}
func EnvelopeFromPart(root *Part) (*Envelope, error) {
	e := &Envelope{
		Root:   root,
		header: &root.Header,
	}

	if detectMultipartMessage(root) {
		
		if err := parseMultiPartBody(root, e); err != nil {
			return nil, err
		}
	} else {
		if detectBinaryBody(root) {
			
			if root.Disposition == cdInline {
				e.Inlines = append(e.Inlines, root)
			} else {
				e.Attachments = append(e.Attachments, root)
			}
		} else {
			
			if err := parseTextOnlyBody(root, e); err != nil {
				return nil, err
			}
		}
	}

	
	if e.Text == "" && e.HTML != "" {
		
		e.Root.addWarning(
			ErrorPlainTextFromHTML,
			"Message did not contain a text/plain part")
		var err error
		if e.Text, err = html2text.FromString(e.HTML); err != nil {
			
			e.Text = ""
			p := e.Root.BreadthMatchFirst(matchHTMLBodyPart)
			p.addError(
				ErrorPlainTextFromHTML,
				"Failed to downconvert HTML: %v",
				err)
		}
	}

	
	if e.Root != nil {
		_ = e.Root.DepthMatchAll(func(part *Part) bool {
			
			for i := range part.Errors {
				
				
				e.Errors = append(e.Errors, part.Errors[i])
			}
			return false
		})
	}

	return e, nil
}
func EnvelopeFromPart ( root * Part ) ( * Envelope , error ) { e := & Envelope { Root : root , header : & root . Header , } if detectMultipartMessage ( root ) { // Multi-part message (message with attachments, etc) if err := parseMultiPartBody ( root , e ) ; err != nil { return nil , err } } else { if detectBinaryBody ( root ) { // Attachment only, no text if root . Disposition == cdInline { e . Inlines = append ( e . Inlines , root ) } else { e . Attachments = append ( e . Attachments , root ) } } else { // Only text, no attachments if err := parseTextOnlyBody ( root , e ) ; err != nil { return nil , err } } } // Down-convert HTML to text if necessary if e . Text == " " && e . HTML != " " { // We always warn when this happens e . Root . addWarning ( ErrorPlainTextFromHTML , " " ) var err error if e . Text , err = html2text . FromString ( e . HTML ) ; err != nil { // Downcoversion shouldn't fail e . Text = " " p := e . Root . BreadthMatchFirst ( matchHTMLBodyPart ) p . addError ( ErrorPlainTextFromHTML , " " , err ) } } // Copy part errors into Envelope. if e . Root != nil { _ = e . Root . DepthMatchAll ( func ( part * Part ) bool { // Using DepthMatchAll to traverse all parts, don't care about result. for i := range part . Errors { // Range index is needed to get the correct address, because range value points to // a locally scoped variable. e . Errors = append ( e . Errors , part . Errors [ i ] ) } return false } ) } return e , nil }
// EnvelopeFromPart uses the provided Part tree to build an Envelope, downconverting HTML to plain
// text if needed, and sorting the attachments, inlines and other parts into their respective
// slices.  Errors are collected from all Parts and placed into the Envelopes Errors slice.
EnvelopeFromPart uses the provided Part tree to build an Envelope downconverting HTML to plain text if needed and sorting the attachments inlines and other parts into their respective slices . Errors are collected from all Parts and placed into the Envelopes Errors slice .