使用Python3的简单S/MIME电子邮件

python-smail的Python项目详细描述


这个库使得在Python中创建S/MIME消息变得很简单。它支持签名(使用RSA密钥), 加密(在AES128-CBC、AES192-CBC或AES256-CBC模式下使用公钥)以及两者的组合- 其中,首先对消息进行签名,然后对结果进行加密(“enveloped”)。在

< Python smail的基础是oscrypto库,它提供了OpenSSL的C绑定的访问权。 并实现了许多高级和低级功能。另外使用asn1crypto,它是“一个快速、纯粹的 用于解析和序列化ASN.1结构的Python库。“。在

要求

  • Python 3.5+
  • ASN1加密
  • 振荡器

示例

加密

下面的代码以PEM格式加载Bob的公钥并使用它进行加密 S/MIME格式的电子邮件:

import os
from email.mime.text import MIMEText
from email.utils import formatdate
from smail import encrypt_message

message = MIMEText("This a plain text body!")
message['Date'] = formatdate(localtime=True)
message['From'] = "AliceRSA@example.com"
message['To'] = "BobRSA@example.com"
message['Subject'] = "Text Message - Encrypted"

cert = os.path.join('tests', 'testdata', 'BobRSASignByCarl.pem')

encrypted_message = encrypt_message(message, [cert])
print(encrypted_message.as_string())

输出:

^{pr2}$

签署

下面的代码以PEM格式加载Alice的私钥和公钥,并将其用于 以S/MIME格式签名电子邮件:

import os
from email.mime.text import MIMEText
from email.utils import formatdate
from smail import sign_message

message = MIMEText("This a plain text body!")
message['Date'] = formatdate(localtime=True)
message['From'] = "AliceRSA@example.com"
message['To'] = "BobRSA@example.com"
message['Subject'] = "Text Message - Signed"

key_signer = os.path.join('tests', 'testdata', 'AlicePrivRSASign.pem')
cert_signer = os.path.join('tests', 'testdata', 'AliceRSASignByCarl.pem')

signed_message = sign_message(message, key_signer, cert_signer)
print(signed_message.as_string())

输出:

MIME-Version: 1.0
Content-Type: multipart/signed; protocol="application/x-pkcs7-signature"; micalg="sha-256"; boundary="----39D1127DF0061CD9BB50644B14CCEF86"
Date: Tue, 17 Mar 2020 20:02:11 +0100
From: AliceRSA@example.com
To: BobRSA@example.com
Subject: Plain Text Message

This is an S/MIME signed message

------39D1127DF0061CD9BB50644B14CCEF86
Content-Type: text/plain; charset="us-ascii"
MIME-Version: 1.0
Content-Transfer-Encoding: 7bit

This a plain text body!
------39D1127DF0061CD9BB50644B14CCEF86
Content-Type: application/x-pkcs7-signature; name="smime.p7s"
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename="smime.p7s"

MIIEIwYJKoZIhvcNAQcCoIIEFDCCBBACAQExDzANBglghkgBZQMEAgEFADALBgkq
hkiG9w0BBwGgggIwMIICLDCCAZWgAwIBAgIQRjRrx4AAVrwR024uxBCzsDANBgkq
hkiG9w0BAQUFADASMRAwDgYDVQQDEwdDYXJsUlNBMB4XDTk5MDkxOTAxMDg0N1oX
DTM5MTIzMTIzNTk1OVowEzERMA8GA1UEAxMIQWxpY2VSU0EwgZ8wDQYJKoZIhvcN
AQEBBQADgY0AMIGJAoGBAOCJczmN2PX16Id2OX9OsAW7U4PeD7er3H3HdSkNBS5t
Et+mhibU0m+qWCn8l+z6glEPMIC+sVCeRkTxLLvYMs/GaG8H2bBgrL7uNAlqE/X3
BQWT3166NVbZYf8Zf8mB5vhs6odAcO+sbSx0ny36VTq5mXcCpkhSjE7zVzhXdFdf
AgMBAAGjgYEwfzAMBgNVHRMBAf8EAjAAMA4GA1UdDwEB/wQEAwIGwDAfBgNVHSME
GDAWgBTp4JAnrHggeprTTPJCN04irp44uzAdBgNVHQ4EFgQUd9K00bdMioqjzkWd
zuw8oDrj/1AwHwYDVR0RBBgwFoEUQWxpY2VSU0FAZXhhbXBsZS5jb20wDQYJKoZI
hvcNAQEFBQADgYEAPnBHqEjME1iPylFxa042GF0EfoCxjU3MyqOPzH1WyLzPbrMc
WakgqgWBqE4lradwFHUv9ceb0Q7pY9Jkt8ZmbnMhVN/0uiVdfUnTlGsiNnRzuErs
L2Tt0z3Sp0LF6DeKtNufZ+S9n/n+dO/q+e5jatg/SyUJtdgadq7rm9tJsCIxggG3
MIIBswIBATAmMBIxEDAOBgNVBAMTB0NhcmxSU0ECEEY0a8eAAFa8EdNuLsQQs7Aw
DQYJYIZIAWUDBAIBBQCggeQwGAYJKoZIhvcNAQkDMQsGCSqGSIb3DQEHATAcBgkq
hkiG9w0BCQUxDxcNMjAwMzE3MTkwMzExWjAvBgkqhkiG9w0BCQQxIgQgUif5fULV
gZhmFxie/WS5nFWC/LtbcHtu/+jQU6vglvQweQYJKoZIhvcNAQkPMWwwajALBglg
hkgBZQMEASowCwYJYIZIAWUDBAEWMAsGCWCGSAFlAwQBAjAKBggqhkiG9w0DBzAO
BggqhkiG9w0DAgICAIAwDQYIKoZIhvcNAwICAUAwBwYFKw4DAgcwDQYIKoZIhvcN
AwICASgwDQYJKoZIhvcNAQEBBQAEgYAG/ZqevJVJYWtImeIG/HHVe0F6gXEpFx43
FbsNV6kaFBOrfkgLICl/a6HaYu9xCHdS7bmiLlDs6qeofmyRAZgUBdDKySm+yjZc
V1VLPuFuL9+BDcXarthOSnn4wbdRBhceRu7w8OnyoTtrwP58c0MiQVtyBQq1FuPZ
WBKduWYjIg==

------39D1127DF0061CD9BB50644B14CCEF86--

加密

下面的代码以PEM格式加载Alice的私钥和公钥以及Bob的公钥,并使用 它以S/MIME格式对电子邮件(从Alice到Bob)进行签名和加密:

import os
from email.mime.text import MIMEText
from email.utils import formatdate
from smail import sign_and_encrypt_message

message = MIMEText("This a plain text body!")
message['Date'] = formatdate(localtime=True)
message['From'] = "AliceRSA@example.com"
message['To'] = "BobRSA@example.com"
message['Subject'] = "Text Message - Signed and Encrypted"

key_signer = os.path.join('tests', 'testdata', 'AlicePrivRSASign.pem')
cert_signer = os.path.join('tests', 'testdata', 'AliceRSASignByCarl.pem')

cert = os.path.join('tests', 'testdata', 'BobRSASignByCarl.pem')

signed_encrypted_message = sign_and_encrypt_message(message, key_signer, cert_signer, [cert])
print(signed_encrypted_message.as_string())

输出:

MIME-Version: 1.0
Content-Type: application/pkcs7-mime; smime-type=enveloped-data; name=smime.p7m
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename=smime.p7m
Date: Tue, 17 Mar 2020 20:05:34 +0100
From: AliceRSA@example.com
To: BobRSA@example.com
Subject: Text Message - Signed and Encrypted

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
e3FI2iig5N6ytDwcN2MGTzr0SuhUe+JEQys2z2A=

致谢

Python SMAIL深受python-smime的启发,实际上是该代码库的一个分支。所有学分转到 原作者。在

许可证

此软件是在Apache许可证2.0下授权的。请参见中的许可证文件 许可证全文的顶部分发目录。在

版本控制

此软件遵循Semantic Versioning

欢迎加入QQ群-->: 979659372 Python中文网_新手群

推荐PyPI第三方库


热门话题
我可以用C++代码使用java代码吗?   java使用JSR303在派生类中提供更具体的约束   java在这个查找唯一路径数算法中我做错了什么?   java如何为2个不同的服务提供商使用2个不同的SSL证书?   java在Gridview上绘制文本   java使用连接for循环构建字符串名   java StringBuilder拆分无法处理某些文件   java事件关注EditText   Java Web Start“找不到URL的缓存资源”   java程序从命令行运行的速度比在Eclipse中慢   java为什么HttpServletRequest会截断#字符上的url输入?   java自定义折叠工具栏平滑标题大小调整   使用Mockito对安卓 java中调用另一个静态函数的函数进行单元测试   http在java客户机中使用cachecontrol头   java如何使用。是否使用Delimiter从输入文件中排除标点符号和数字?   使用上下文作为参数/参数的java   java更有效地从Jar中提取文件   java为多个JButton提供相同的actionListener