【问题标题】:Saving HTML email with inline images to PS or PDF with Procmail使用 Procmail 将带有内嵌图像的 HTML 电子邮件保存为 PS 或 PDF
【发布时间】:2016-05-31 16:06:59
【问题描述】:

我需要一些建议/推动正确的方向。

我编写了一些小脚本,它们接收传入的 HTML 电子邮件,将其转换为 PostScript,然后通过 CUPS 将其发送到指定的打印机。打印机基于电子邮件的收件人。

我正在使用以下方法来实现这一点;

  1. 进出口
  2. Procmail
  3. HTML2PS
  4. 两个自定义脚本(发布在下面)

流程

  1. Exim 收到一封电子邮件并传递给 Procmail
  2. .procmailrc 调用自定义脚本“process_mail”,将主题和内容作为参数传递
  3. “process_mail”将内容拉入一个函数并调用“get_html_from_message”(我还没有对主题做任何事情)
  4. “get_html_from_message”转储除 HTML 之外的所有内容
  5. 然后将 HTML 转换为 PostScript
  6. PostScript 文件被发送到指定的打印机。

问题

  1. 在 HTML2PS 阶段会生成错误,并将 NDR 发送回发件人,说明打开图像时出错。 打开 cid:logo.jpg 时出错
  2. PostScript 文件已成功打印,但显然不包含电子邮件中的图像。

我的问题是:如何从电子邮件中取出这些图像,以便它们在 PostScript 文件中成功打印出来?

如果 PostScript 不适合,我很乐意转换为 PDF,但即使转换为 PDF,我也没有图像,因为我无法获取它们。

.procmailrc

SHELL=/bin/bash

# Extract the subject and normalise
SUBJECT=`formail -x"Subject: "\
| /usr/bin/tr '[:space:][:cntrl:][:punct:]' '_' | expand | sed -e     's/^[_]*//' -e 's/[_]*$//'`
YMD=`date +%Y%m%d`

MAKE_SURE_DIRS_EXIST=`
mkdir -p received_mail/backup
if [ ! -z ${SUBJECT} ]
then
    mkdir -p received_mail/${YMD}/${SUBJECT}
else
    mkdir -p received_mail/${YMD}/no_subject
fi
`

# Backup all received mail into the backup directory appending to a file named by date
:0c
received_mail/backup/${YMD}.m

# If no subject, just store the mail
:0c
* SUBJECT ?? ^^^^
received_mail/${YMD}/no_subject/.

# Else there is a subject, generate a unique filemane, place the received email 
# in that file and then execute process_mail passing the filename and subject as parameters
:0Eb
| f=`uuidgen`; export f; cat > received_mail/${YMD}/${SUBJECT}/${f};     $HOME/bin/process_mail received_mail/${YMD}/${SUBJECT}/${f} "${SUBJECT}"

# and don't deliver to standard mail, don't want to clutter up the inbox. 
:0
/dev/null

process_mail

#/bin/bash

# Test Printer
printer=$(whoami)

file=$1
subject=$2

function process_rrs {
typeset file
file=$1
cat $file \
| $HOME/bin/get_html_from_message \
| html2ps \
| lp -d ${printer} -o media=a4 2>&1
}

case "$subject" in
*)
    process_rrs $file
    ;;
esac

get_html_from_message

cat | awk '
BEGIN {
typeout=0
}
{
if($0 ~ /<html/)
    typeout=1
if($0 ~ /^------=/)
    typeout=0
if(typeout)
    print $0
}'

编辑:格式化

【问题讨论】:

  • 你有一个useless use of cat
  • export f 似乎是多余的。导出使变量对子流程可见;但这里似乎没有子进程正在使用这个变量。
  • 谢谢。我会在早上研究这个。一直在学习:)

标签: exim procmail html2ps


【解决方案1】:

我已经想出了如何实现这一点。详情如下。所有这些都在两个负载平衡的 CentOS 6 机器上运行。

应用程序

  1. 进出口
  2. 杯子
  3. Mhonarc(不在 repo 中。RPM 和网站在这里 https://www.mhonarc.org/
  4. Procmail
  5. HTML2ps

工作原理

  1. 一封电子邮件被发送到两个盒子上都存在的用户帐户。
  2. Exim 管道将电子邮件发送到 Procmail
  3. Procmail 在用户主目录中查找 .procmailrc 并获取 行动。
  4. Mhonarc 将电子邮件转换为 HTML 文件,保存图像和附件。
  5. 使用“sed”,打开 HTML 文件并查找电子邮件的开头 () 并将所有文本收集到文件末尾
  6. 再次管道到“sed”以删除由 Mhonarc 添加的多余 HTML 标记(hr 标记)
  7. 管道到 Html2ps 以转换为 PostScript
  8. 管道到指定打印机(打印机名称与用户帐户相同)

使用上述过程,我能够将其放到一个脚本中,即 .procmailrc。这就是我在 .procmailrc 文件中写的内容。

SHELL=/bin/bash

# Designate the printer. Printer names match usernames so you don't have to manually change 60+ files. 
printer=`whoami`

# Generate a unique ID
f=`uuidgen`

# Convert email, including headers and body into a HTML file and save off the images using MHONARC https://www.mhonarc.org/
# Open file and search <!--X-Body-of-Message--> string using SED and collect all text to EOF.
# Pipe the result into SED again to remove unwanted HTML tags added by MHONARC
# Pipe result into HTML2PS to convert to PostScript
# Pipe PostScript file to the designated printer
:0E
| mhonarc -single > ${f}.html; sed -n '/^<!--X-Body-of-Message-->$/ { s///; :a; n; p; ba; }' ${f}.html | sed -e '/<hr>/d' | html2ps | lp -d ${printer} -o media=a4 2>&1

# Finally, delete the email
:0
/dev/null

我不太了解“sed”,可能有更简单的方法来实现这一点。我会在某个时候进一步调查。

希望这对某人有帮助:)

【讨论】:

  • 感谢分享!如果图像是附加的,Monharc 将保存它们,但如果它们是链接的(即从服务器加载)则不会。您是否知道如何使您的工作流程在这种情况下工作? Monharc 不会转换包含正确链接的图像的 .eml...
【解决方案2】:

问题可能是对 HTML 在电子邮件中的表示方式的理解不完整。通常会有一个包含一个 HTML 部分和多个图像的 MIME 多部分。 HTML 在图像链接中使用cid: 寻址方案来引用这些同级部分。但是如果你只提取 HTML,它就不再存在于它有任何兄弟的上下文中。 (即使您将所有部分提取到文件中,cid: 通常也不会映射到本地文件。也许您可以对 HTML 进行后处理以解决该问题;但我认为您的方法可能应该重新考虑。您是否考虑过使用具有原生 HTML 支持以呈现这些消息的邮件客户端?)

一个简单的xmlstarlet 脚本或类似的从任何img 链接的src 属性中去除cid: 前缀应该不难,但如果您尝试,可能会发现您需要做的其他事情这条路。

【讨论】:

  • 嗨。感谢您的信息。该系统位于无头 CentOS 机器上。这些电子邮件来自发送票证的云服务,我们每天将处理数百甚至数千个,因此手动打印将不起作用。最初不需要图像,这就是它以这种方式编写的原因,但是唉,现在他们想要图像。我不必使用这些脚本,我总是可以写一些别的东西。你知道有什么方法可以做到这一点吗?感谢您对 MIME 的深入了解,我缺乏这方面的知识。
  • 我隐约认为你可以无头运行 Thunderbird;但我自己没有这方面的经验,编写脚本可能有点挑战性。
  • 有趣。我会考虑这个作为一个选项
猜你喜欢
  • 2012-03-22
  • 1970-01-01
  • 1970-01-01
  • 2011-01-14
  • 2012-07-29
  • 2015-07-29
  • 2017-07-04
  • 2017-03-16
  • 1970-01-01
相关资源
最近更新 更多