如何解密S/MIME加密邮件并保留原始邮件头?
如何解密S/MIME加密邮件并保留原始邮件头?
嘿,我之前也碰到过一模一样的问题,折腾了好一阵才搞明白原因和解决办法,给你详细说说:
为什么解密后会丢邮件头?
其实核心原因是S/MIME加密的结构特性:当你收到的是完全加密的S/MIME邮件时,原始的Subject、To、From这些核心头,其实是被打包进了PKCS#7的加密块里,而你保存的EML文件外层只有Content-Type、Content-Transfer-Encoding这些描述加密格式的头。默认的openssl smime -decrypt命令有时候会只提取解密后的正文部分,而忽略掉加密块里的原始头——或者是你保存的EML文件不完整,只截取了加密内容部分。
解决办法分两种情况:
情况1:保存了完整的加密EML文件
直接用带完整参数的openssl命令,让它完整解析整个邮件结构,解密后会自动还原所有原始头:
openssl smime -decrypt -in 你的加密邮件.eml -out 解密后的完整邮件.eml -inkey 你的私钥文件.pem -certfile 你的证书文件.pem
这个命令会直接解析整个EML的MIME结构,把加密块里的原始邮件(包括所有头和正文)完整解密出来,不会丢任何头。
情况2:默认命令还是丢头(或者你只提取了加密内容)
如果上面的命令还是不行,大概率是你的邮件采用了“明文头+加密正文”的分离结构,这时候需要手动拆分合并:
- 提取明文头:用文本编辑器打开加密EML,把开头的To、From、Subject、Date这些头复制出来,保存成
headers.txt,注意最后要加一个空行(邮件头和正文的分隔线是必须的)。 - 提取加密正文:把EML里Content-Type下面的base64加密内容单独复制出来,保存成
encrypted_content.b64。 - 解密正文:用openssl解密这个加密块:
openssl smime -decrypt -in encrypted_content.b64 -inform der -out decrypted_body.eml -inkey 你的私钥文件.pem -certfile 你的证书文件.pem
- 合并文件:把
headers.txt和decrypted_body.eml的内容合并成一个新文件,就是带完整原始头的解密邮件了。
小提示
- 一定要确保你用的是完整的私钥和对应证书,如果密钥和证书不匹配,解密过程会失败或者输出异常内容。
- 保存EML的时候,要从邮件客户端导出完整的邮件内容,不要只保存加密附件部分。
备注:内容来源于stack exchange,提问作者Binarus
相关产品推荐
相关产品推荐

