使用Mailmerge發(fā)送定制郵件
Mailmerge 是一個可以定制群發(fā)郵件的命令行程序,它可以處理簡單和復(fù)雜的郵件。
電子郵件還是生活的一部分,盡管有種種不足,它仍然是大多數(shù)人發(fā)送信息的最佳方式,尤其是在按隊列將郵件發(fā)送給收件人的自動化方式中。
作為 Fedora 社區(qū)行動和影響協(xié)調(diào)員,我的工作之一就是給人們發(fā)送資助旅行相關(guān)的好消息,我經(jīng)常通過電子郵件做這些事。這里,我將給你展示如何使用 Mailmerge 向一群人發(fā)送定制郵件的,Mailmerge 是一個可以處理簡單和復(fù)雜的郵件的命令行程序。
安裝 Mailmerge
在 Fedora 中,Mailmerge 已經(jīng)打包可用,你可以通過在命令行中運行 sudo dnf install python3-mailmerge
來安裝它。你還可以使用 pip
命令從 PyPi 中安裝,具體可以參閱該項目的 README。
配置 Mailmerge
三個配置文件控制著 Mailmerge 的工作模式。運行 mailmerge --sample
,將生成配置文件模板。這些文件包括:
mailmerge_server.conf:
這里保存著 SMTP 服務(wù)端郵件發(fā)送相關(guān)詳細(xì)配置,但你的密碼 不 在這里保存。mailmerge_database.csv:
這里保存每封郵件的定制數(shù)據(jù),包括收件人的電子郵件地址。mailmerge_template.txt:
這里保存電子郵件的文本,文本中包含占位符,這些占位符會使用mailmerge_database.csv
中的數(shù)據(jù)替換。
Server.conf
配置模板文件 mailmerge_server.conf
包含幾個大家應(yīng)該很熟悉的例子。如果你曾經(jīng)往手機上添加過電子郵件或者設(shè)置過桌面電子郵件客戶端,那你就應(yīng)該看到過這些數(shù)據(jù)。需要提醒的是要記得把你的用戶名更新到這個文件中,尤其是在你使用模板所提供的配置時。
Database.csv
mailmerge_database.csv
這個配置文件稍微有點復(fù)雜。最起碼要將郵件接收者的電子郵件地址保存在這里,其它在電子郵件中任何需要替換的定制信息也要保存在這里。推薦在創(chuàng)建本文件的占位符列表時,同步編輯 mailmerge_template.txt
文件。我發(fā)現(xiàn)一個有效的做法是,使用電子表格軟件錄入這些數(shù)據(jù),完成后導(dǎo)出為 CSV 文件。使用下面的示例文件:
email,name,number
myself@mydomain.com,"Myself",17
bob@bobdomain.com,"Bob",42
可以你向這兩個人發(fā)送電子郵件,使用他們的名字并告訴他們一個數(shù)字。這個示例文件雖然不是特別有趣,但應(yīng)用了一個重要的原則,那就是:始終讓自己處于郵件接收列表的首位。這樣你可以在向列表全員發(fā)送郵件之前,先給自己發(fā)送一個測試郵件,以驗證郵件的效果是否如你預(yù)期。
任何包含半角逗號的值,都 必須 以半角雙引號("
)封閉。如果恰好在半角雙引號封閉的區(qū)域需要有一個半角雙引號,那就在同一行中連續(xù)使用兩個半角雙引號。引號的規(guī)則比較有趣,去 Python 3 中關(guān)于 CSV 的內(nèi)容中 一探究竟吧。
Template.txt
我的工作之一,就是為我們 Fedora 貢獻(xiàn)者會議 Flock 發(fā)送與旅行基金有關(guān)的信息。通過簡單的郵件告訴有關(guān)的人,他被選中為旅行基金支持的幸運者,以及相應(yīng)基金支持的詳細(xì)信息。與接收者相關(guān)的具體信息之一就是我們可以為他的旅行提供多少資助。下面是一份我的節(jié)略后的模板文件(為了簡潔,已經(jīng)移除大量的文本):
$ cat mailmerge_template.txt
TO: {{Email}}
SUBJECT: Flock 2019 Funding Offer
FROM: Brian Exelbierd <bexelbie@redhat.com>
Hi {{Name}},
I am writing you on behalf of the Flock funding committee. You requested funding for your attendance at Flock. After careful consideration we are able to offer you the following funding:
Travel Budget: {{Travel_Budget}}
<<snip>>
模板的起頭定義了郵件的接收者、發(fā)送者和主題。在空行之后,是郵件的內(nèi)容。該郵件需要從 database.csv
文件中獲取接收者的 Email
、Name
和 Travel_Budget
。注意,上述這些占位符是由雙大括?。?nbsp;{{
、}}
)封閉的。相應(yīng)的 mailmerge_database.csv
如下:
$ cat mailmerge_database.csv
Name,Email,Travel_Budget
Brian,bexelbie@redhat.com,1000
PersonA,persona@fedoraproject.org,1500
PèrsonB,personb@fedoraproject.org,500
注意,我把自己的信息放在了首條,這是為了測試方便。除了我,還有另外兩個人的信息在文檔中。列表中的第二個人 PèrsonB,他的名字中有一個包含變音符號的字母,Mailmerge 會對這類字母自動編碼。
以上包含了模板的全部知識點:寫上你自己的電子郵件信息,并編寫好以雙大括弧封閉的占位符。接下來創(chuàng)建用來提供前述占位符具體值的數(shù)據(jù)文件?,F(xiàn)在測試一下電子郵件的效果。
測試并發(fā)送簡單郵件
試運行
測試從郵件的試運行開始,試運行就是講郵件內(nèi)容顯示出來,所有的占位符都會被具體值取代。默認(rèn)情況下,如果你運行不帶參數(shù)的命令 mailmerge
,它將對收件列表中的第一個人進(jìn)行試運行:
$ mailmerge
>>> encoding ascii
>>> message 0
TO: bexelbie@redhat.com
SUBJECT: Flock 2019 Funding Offer
FROM: Brian Exelbierd <bexelbie@redhat.com>
MIME-Version: 1.0
Content-Type: text/plain; charset="us-ascii"
Content-Transfer-Encoding: 7bit
Date: Sat, 20 Jul 2019 18:17:15 -0000
Hi Brian,
I am writing you on behalf of the Flock funding committee. You requested funding for your attendance at Flock. After careful consideration we are able to offer you the following funding:
Travel Budget: 1000
<<snip>>
>>> sent message 0 DRY RUN
>>> No attachments were sent with the emails.
>>> Limit was 1 messages. To remove the limit, use the --no-limit option.
>>> This was a dry run. To send messages, use the --no-dry-run option.
從試運行生成的郵件中(列表中的 message 0
,和計算機中很多計數(shù)場景一樣,計數(shù)從 0 開始),可以看到我的名字及旅行預(yù)算是正確的。如果你想檢視所有的郵件,運行 mailmerge --no-limit
,告訴 Mailmerge 不要僅僅處理第一個收件人的信息。下面是第三個收件人郵件的試運行結(jié)果,用來測試特殊字符的編碼:
>>> message 2
TO: personb@fedoraproject.org
SUBJECT: Flock 2019 Funding Offer
FROM: Brian Exelbierd <bexelbie@redhat.com>
MIME-Version: 1.0
Content-Type: text/plain; charset="iso-8859-1"
Content-Transfer-Encoding: quoted-printable
Date: Sat, 20 Jul 2019 18:22:48 -0000
Hi P=E8rsonB,
沒有問題,P=E8rsonB
是 PèrsonB
的編碼形式。
發(fā)送測試信息
現(xiàn)在,運行 mailmerge --no-dry-run
,Mailmerge 將向收件人列表中的第一個人發(fā)送電子郵件:
$ mailmerge --no-dry-run
>>> encoding ascii
>>> message 0
TO: bexelbie@redhat.com
SUBJECT: Flock 2019 Funding Offer
FROM: Brian Exelbierd <bexelbie@redhat.com>
MIME-Version: 1.0
Content-Type: text/plain; charset="us-ascii"
Content-Transfer-Encoding: 7bit
Date: Sat, 20 Jul 2019 18:25:45 -0000
Hi Brian,
I am writing you on behalf of the Flock funding committee. You requested funding for your attendance at Flock. After careful consideration we are able to offer you the following funding:
Travel Budget: 1000
<<snip>>
>>> Read SMTP server configuration from mailmerge_server.conf
>>> host = smtp.gmail.com
>>> port = 587
>>> username = bexelbie@redhat.com
>>> security = STARTTLS
>>> password for bexelbie@redhat.com on smtp.gmail.com:
>>> sent message 0
>>> No attachments were sent with the emails.
>>> Limit was 1 messages. To remove the limit, use the --no-limit option.
在倒數(shù)第 4 行,它將要求你輸入你的密碼。如果你使用的是雙因素認(rèn)證或者域控制登錄,那就需要創(chuàng)建應(yīng)用密碼來繞過這些控制。如果你使用的是 Gmail 或者類似的系統(tǒng),可以直接在界面上完成密碼驗證。如果不行的話,聯(lián)系你的郵件系統(tǒng)管理員。上述這些操作不會影響郵件系統(tǒng)的安全性,但是仍然有必要采用復(fù)雜的安全性好的密碼。
我在我的郵件收件箱中,看到了這封格式美觀的測試郵件。如果測試郵件看起來沒有問題,那就可以運行 mailmerge --no-dry-run --no-limit
發(fā)送所有的郵件了。
發(fā)送復(fù)雜郵件
只有充分了解了 Jinja2 模板 ,你才可能充分領(lǐng)略 Mailmerge 真正的威力。在郵件模板中使用條件語句及附帶附件,是很有用的。下面就是一個復(fù)雜郵件的模板及對應(yīng)的數(shù)據(jù)文件:
$ cat mailmerge_template.txt
TO: {{Email}}
SUBJECT: Flock 2019 Funding Offer
FROM: Brian Exelbierd <bexelbie@redhat.com>
ATTACHMENT: attachments/{{File}}
Hi {{Name}},
I am writing you on behalf of the Flock funding committee. You requested funding for your attendance at Flock. After careful consideration we are able to offer you the following funding:
Travel Budget: {{Travel_Budget}}
{% if Hotel == "Yes" -%}
Lodging: Lodging in the hotel Wednesday-Sunday (4 nights)
{%- endif %}
<<snip>>
$ cat mailmerge_database.csv
Name,Email,Travel_Budget,Hotel,File
Brian,bexelbie@redhat.com,1000,Yes,visa_bex.pdf
PersonA,persona@fedoraproject.org,1500,No,visa_person_a.pdf
PèrsonB,personb@fedoraproject.org,500,Yes,visa_person_b.pdf
在這個郵件中有兩項新內(nèi)容。首先是附件,我需要向參加國際旅行的人發(fā)送簽證邀請信,幫助他們來 Flock,文件頭的 ATTACHMENT
部分說明了要包含什么文件;為了保持我的文檔目錄清晰,我將所有需要作為附件的文檔保存于附件子目錄下。其次是包含了關(guān)于賓館的條件信息,因為有些人的旅行資金包含了住宿費用,我需要對涉及住宿的人員訴及相關(guān)信息,而這是通過 if
判斷實現(xiàn)的:
{% if Hotel == "Yes" -%}
Lodging: Lodging in the hotel Wednesday-Sunday (4 nights)
{%- endif %}
這和大多數(shù)編程語言中的 if
判斷是一樣的。Jinja2 實力非凡,可以實現(xiàn)多級判斷。通過包含數(shù)據(jù)元素控制郵件內(nèi)容,能大大簡化相關(guān)的日常工作??崭竦恼_使用對郵件的易讀性很重要。if
和 endif
語句中的短線( -
)是 Jinja2 控制 空白字符 的一部分。這里面選項很多,所以還是要通過試驗找到最適合自己的方式。
在上面的例子中,我在數(shù)據(jù)文件擴充了 Hotel
和 File
兩個字段,這些字段的值控制著賓館信息和附件文件名。另外,在上例中,我和 PèrsonB 有住宿資助,但 PersonA 沒有。
對于簡單郵件和復(fù)雜郵件而言,試運行及正式發(fā)送郵件的操作都是相同的??烊ピ囋嚢?!
你還可以嘗試在郵件頭中使用條件判斷( if
… endif
),比如你可以使發(fā)送給在數(shù)據(jù)庫中的某人的郵件包含附件,或者改變對部分人改變發(fā)送人的信息。
Mailmerge 的優(yōu)點
Mailmerge 是用來批量發(fā)送定制郵件的簡潔而高效的工具。每個人只接受到他需要的信息,其它額外的操作和細(xì)節(jié)都是透明的。
我還發(fā)現(xiàn),即使是在發(fā)送簡單的集團郵件時,相對于使用 CC 或者 BCC 向一組受眾發(fā)送一封郵件,采用 Mailmerge 也是非常高效的。很多人使用了郵件過濾,那些不是直接發(fā)給他們的郵件,他們一律不會立刻處理。使用 Mailmerge 保證了每名接收者收到的就是自己的郵件。所有的信息會對接收者進(jìn)行正確過濾,再也不會有人無意間回復(fù)到整個郵件組。