You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Python的exchangelib中添加自定义头发送手动加密S/MIME邮件

Hey there! Since exchangelib doesn’t include built-in support for S/MIME encryption, manually constructing your encrypted message with the required headers is the right approach. Here’s a step-by-step guide to make this work:

1. Prepare Your Encrypted S/MIME Content

First, you’ll need to generate the base64-encoded PKCS#7 encrypted content (the smime.p7m data). You mentioned you already know how to do this with OpenSSL—make sure this encrypted content includes everything you want in the email (body + any attachments). For context, if you’re including attachments, you’ll first build a standard MIME message with those attachments, then encrypt that entire message using the recipient’s public key to get your final base64 string.

2. Use Exchangelib’s mime_content to Control the Full MIME Message

Instead of letting exchangelib auto-generate the email structure, you can pass a complete MIME-formatted string directly using the mime_content attribute of the Message object. This lets you define all custom headers exactly as you need them.

Here’s a code example:

from exchangelib import Account, Message, Mailbox

# Replace these with your actual details
encrypted_smime_content = "YOUR_BASE64_ENCODED_PKCS7_DATA_HERE"
your_email = "your-email@example.com"
recipient_email = "recipient@example.com"
exchange_username = "your-exchange-username"
exchange_password = "your-exchange-password"

# Connect to your Exchange account (use your existing connection logic)
account = Account(
    primary_smtp_address=your_email,
    credentials=(exchange_username, exchange_password),
    autodiscover=True,
    access_type="delegate"
)

# Build the full MIME message string with all required headers
mime_message = f"""MIME-Version: 1.0
Content-Type: application/pkcs7-mime; name="smime.p7m"; smime-type=enveloped-data
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename="smime.p7m"
Content-Description: S/MIME Encrypted Message

{encrypted_smime_content}
"""

# Create the message and set the MIME content
msg = Message(
    account=account,
    subject="S/MIME Encrypted Test Email"
)
msg.mime_content = mime_message.encode("utf-8")

# Add recipients
msg.to_recipients = [Mailbox(email_address=recipient_email)]

# Send the email
msg.send()

3. Bonus: Building and Encrypting a Message with Attachments

If you need to include attachments in the encrypted email, first build a standard MIME message with those attachments, then encrypt that entire message. Here’s how you can do that with Python’s built-in email module and OpenSSL:

from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.image import MIMEImage
import subprocess
import tempfile

# Step 1: Build a regular MIME message with body and attachments
plain_msg = MIMEMultipart()
plain_msg["Subject"] = "Original Message Content"
plain_msg["From"] = your_email
plain_msg["To"] = recipient_email

# Add plain text body
body = MIMEText("This is the unencrypted body text", "plain")
plain_msg.attach(body)

# Add an image attachment (adjust for your file type)
with open("your-image.jpg", "rb") as f:
    img_attachment = MIMEImage(f.read())
    img_attachment.add_header("Content-Disposition", "attachment", filename="your-image.jpg")
    plain_msg.attach(img_attachment)

# Step 2: Write the plain message to a temp file for OpenSSL
with tempfile.NamedTemporaryFile(mode="w", delete=False) as f:
    f.write(plain_msg.as_string())
    temp_in_path = f.name

with tempfile.NamedTemporaryFile(mode="r", delete=False) as f:
    temp_out_path = f.name

# Step 3: Encrypt the message with OpenSSL (use recipient's public cert)
subprocess.run(
    [
        "openssl", "smime", "-encrypt",
        "-in", temp_in_path,
        "-out", temp_out_path,
        "-outform", "PEM",
        "-certfile", "recipient-public-cert.pem"
    ],
    check=True
)

# Step 4: Extract the base64 content (strip PEM headers)
with open(temp_out_path, "r") as f:
    encrypted_content = f.read().replace("-----BEGIN PKCS7-----", "").replace("-----END PKCS7-----", "").strip()

# Now use this encrypted_content in the first code example to send the email

Key Notes

  • Using mime_content gives you full control over the email’s headers and content, so exchangelib won’t override or auto-generate any of the S/MIME-specific headers you need.
  • Make sure you encrypt the entire MIME message (body + attachments) before passing it to exchangelib—don’t encrypt just the body text if you have attachments.

内容的提问来源于stack exchange,提问作者Breakfast Serial

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 04:08:00