最近公司正在研发的一个邮件列表服务,因为需要将同一个话题的前后邮件串成线索,所以去了解了一些邮件头定义,以及如何识别邮件对话上下文的方法。
标准的邮件头里面定义了一个 In-Reply-To 字段,这个字段在 rfc822 中是这么[url=http://www.w3.org/Protocols/rfc822#z30]解释[/url]的:
[quote]4.6.2. IN-REPLY-TO
The contents of this field identify previous correspondence which this message answers. [/quote]
这个头很容易理解,它存放了当前邮件回复的邮件ID,比如用 gmail 回复邮件,邮件头里面会包含以下字段:
[quote]Message-ID: <CAEyJnUq2=7B_RRfe1=1iNVGh_Tqc5n=NJzrBzAJ8BEE9VnkE0Q@mail.gmail.com>
In-Reply-To: <tencent_1118E66B5C5AE62D25831465@qq.com>[/quote]
这样,各类邮件列表或者邮件客户端就可以识别这封邮件是回复了 <tencent_1118E66B5C5AE62D25831465@qq.com> 这封邮件的,而如果要回复这封gmail邮件,就应该把 Gmail 邮件的 Message-ID 放到 In-Reply-To。
于是公司的邮件列表服务就基于邮件的 In-Reply-To 信息做了一个 web 界面,邮件的收发在后台被串成一个个 Topic。测试过程中大部分邮箱(163,gmail,msn……)都能正常处理,却发现 QQ 邮箱每回一个邮件都新建了一个主题,似乎是没有正确识别它的上下文。于是用 QQ 回复一封邮件,打开原文查看邮件头(隐去我的email地址):
[quote]Delivered-To: chloe***@gmail.com
Received: by 10.182.28.233 with SMTP id e9cs131752obh;
Mon, 21 Nov 2011 19:18:14 -0800 (PST)
Received: by 10.231.8.143 with SMTP id h15mr3969665ibh.94.1321931893044;
Mon, 21 Nov 2011 19:18:13 -0800 (PST)
Return-Path: <chloe***@qq.com>
Received: from smtpbg52.qq.com (smtpbg52.qq.com. [64.71.138.43])
by mx.google.com with SMTP id m10si3572370icu.21.2011.11.21.19.18.12;
Mon, 21 Nov 2011 19:18:13 -0800 (PST)
Received-SPF: pass (google.com: domain of chloerei@qq.com designates 64.71.138.43 as permitted sender) client-ip=64.71.138.43;
Authentication-Results: mx.google.com; spf=pass (google.com: domain of chloerei@qq.com designates 64.71.138.43 as permitted sender) smtp.mail=chloe***@qq.com; dkim=neutral (no signature) header.i=@qq.com
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=qq.com; s=s0907;
t=1321931892; bh=AXXnKE4F5rR44xTUgYD2wpsmGbJ6mYVlVOK31SUjW3w=;
h=X-QQ-SSF:X-QQ-BUSINESS-ORIGIN:X-Originating-IP:X-QQ-STYLE:
X-QQ-mid:From:To:Subject:Mime-Version:Content-Type:
Content-Transfer-Encoding:Date:X-Priority:Message-ID:X-QQ-MIME:
X-Mailer:X-QQ-Mailer:X-QQ-ReplyHash;
b=aZ400d+i6ptIpZhMY6kLfgYh4QiS80cgiYeQgU4fxEZQYa8zUjytvkEd2kyJ/AJrW
lKQvyGam0JId/Ql1frfurdIjNDmcLh38a8dJJYvsGEkc6AcaAc3Ji6xethKolD7
X-QQ-SSF: 00010000000000F0000000000000000
X-QQ-BUSINESS-ORIGIN: 2
X-Originating-IP: 211.103.191.134
X-QQ-STYLE:
X-QQ-mid: webmail504t1321931889t662760
From: "=?gbk?B?Y2hsb2VyZWk=?=" <chloe***@qq.com>
To: "=?gbk?B?Y2hsb2VyZWk=?=" <chloe***@gmail.com>
Subject: =?gbk?B?u9i4tKO6suLK1LuwzOI=?=
Mime-Version: 1.0
Content-Type: multipart/alternative;
boundary="----=_NextPart_4ECB1471_DCF2B518_079AED38"
Content-Transfer-Encoding: 8Bit
Date: Tue, 22 Nov 2011 11:18:09 +0800
X-Priority: 3
Message-ID: <tencent_1118E66B5C5AE62D25831465@qq.com>
X-QQ-MIME: TCMime 1.0 by Tencent
X-Mailer: QQMail 2.x
X-QQ-Mailer: QQMail 2.x
X-QQ-ReplyHash: 971243411[/quote]
可以看到,长长的邮件头里面竟然就没有 In-Reply-To 字段。那么,丢了 In-Reply-To 字段,QQ 邮箱的会话功能又是怎么做到的呢?
看到最后一个字段,忽然明白了。
[quote]X-QQ-ReplyHash: 971243411[/quote]
这是只有腾讯自己才能识别的邮件头。
想不明白腾讯抛弃现有的标准邮件头不用,自建邮件头是为什么,这样的结果是除了少数像 Gmail 这样智能根据邮件全文判断上下文的邮件服务能正常识别线索外,其余为标准邮件协议而写的客户端都不能处理了。最终公司的邮件列表服务暂时放弃了支持非标准的 QQ 邮件。
标准的邮件头里面定义了一个 In-Reply-To 字段,这个字段在 rfc822 中是这么[url=http://www.w3.org/Protocols/rfc822#z30]解释[/url]的:
[quote]4.6.2. IN-REPLY-TO
The contents of this field identify previous correspondence which this message answers. [/quote]
这个头很容易理解,它存放了当前邮件回复的邮件ID,比如用 gmail 回复邮件,邮件头里面会包含以下字段:
[quote]Message-ID: <CAEyJnUq2=7B_RRfe1=1iNVGh_Tqc5n=NJzrBzAJ8BEE9VnkE0Q@mail.gmail.com>
In-Reply-To: <tencent_1118E66B5C5AE62D25831465@qq.com>[/quote]
这样,各类邮件列表或者邮件客户端就可以识别这封邮件是回复了 <tencent_1118E66B5C5AE62D25831465@qq.com> 这封邮件的,而如果要回复这封gmail邮件,就应该把 Gmail 邮件的 Message-ID 放到 In-Reply-To。
于是公司的邮件列表服务就基于邮件的 In-Reply-To 信息做了一个 web 界面,邮件的收发在后台被串成一个个 Topic。测试过程中大部分邮箱(163,gmail,msn……)都能正常处理,却发现 QQ 邮箱每回一个邮件都新建了一个主题,似乎是没有正确识别它的上下文。于是用 QQ 回复一封邮件,打开原文查看邮件头(隐去我的email地址):
[quote]Delivered-To: chloe***@gmail.com
Received: by 10.182.28.233 with SMTP id e9cs131752obh;
Mon, 21 Nov 2011 19:18:14 -0800 (PST)
Received: by 10.231.8.143 with SMTP id h15mr3969665ibh.94.1321931893044;
Mon, 21 Nov 2011 19:18:13 -0800 (PST)
Return-Path: <chloe***@qq.com>
Received: from smtpbg52.qq.com (smtpbg52.qq.com. [64.71.138.43])
by mx.google.com with SMTP id m10si3572370icu.21.2011.11.21.19.18.12;
Mon, 21 Nov 2011 19:18:13 -0800 (PST)
Received-SPF: pass (google.com: domain of chloerei@qq.com designates 64.71.138.43 as permitted sender) client-ip=64.71.138.43;
Authentication-Results: mx.google.com; spf=pass (google.com: domain of chloerei@qq.com designates 64.71.138.43 as permitted sender) smtp.mail=chloe***@qq.com; dkim=neutral (no signature) header.i=@qq.com
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=qq.com; s=s0907;
t=1321931892; bh=AXXnKE4F5rR44xTUgYD2wpsmGbJ6mYVlVOK31SUjW3w=;
h=X-QQ-SSF:X-QQ-BUSINESS-ORIGIN:X-Originating-IP:X-QQ-STYLE:
X-QQ-mid:From:To:Subject:Mime-Version:Content-Type:
Content-Transfer-Encoding:Date:X-Priority:Message-ID:X-QQ-MIME:
X-Mailer:X-QQ-Mailer:X-QQ-ReplyHash;
b=aZ400d+i6ptIpZhMY6kLfgYh4QiS80cgiYeQgU4fxEZQYa8zUjytvkEd2kyJ/AJrW
lKQvyGam0JId/Ql1frfurdIjNDmcLh38a8dJJYvsGEkc6AcaAc3Ji6xethKolD7
X-QQ-SSF: 00010000000000F0000000000000000
X-QQ-BUSINESS-ORIGIN: 2
X-Originating-IP: 211.103.191.134
X-QQ-STYLE:
X-QQ-mid: webmail504t1321931889t662760
From: "=?gbk?B?Y2hsb2VyZWk=?=" <chloe***@qq.com>
To: "=?gbk?B?Y2hsb2VyZWk=?=" <chloe***@gmail.com>
Subject: =?gbk?B?u9i4tKO6suLK1LuwzOI=?=
Mime-Version: 1.0
Content-Type: multipart/alternative;
boundary="----=_NextPart_4ECB1471_DCF2B518_079AED38"
Content-Transfer-Encoding: 8Bit
Date: Tue, 22 Nov 2011 11:18:09 +0800
X-Priority: 3
Message-ID: <tencent_1118E66B5C5AE62D25831465@qq.com>
X-QQ-MIME: TCMime 1.0 by Tencent
X-Mailer: QQMail 2.x
X-QQ-Mailer: QQMail 2.x
X-QQ-ReplyHash: 971243411[/quote]
可以看到,长长的邮件头里面竟然就没有 In-Reply-To 字段。那么,丢了 In-Reply-To 字段,QQ 邮箱的会话功能又是怎么做到的呢?
看到最后一个字段,忽然明白了。
[quote]X-QQ-ReplyHash: 971243411[/quote]
这是只有腾讯自己才能识别的邮件头。
想不明白腾讯抛弃现有的标准邮件头不用,自建邮件头是为什么,这样的结果是除了少数像 Gmail 这样智能根据邮件全文判断上下文的邮件服务能正常识别线索外,其余为标准邮件协议而写的客户端都不能处理了。最终公司的邮件列表服务暂时放弃了支持非标准的 QQ 邮件。