我正在努力输入任何电子邮件并输出等效的 XML 编码。
我从小处着手,使用其中一个电子邮件标头——“发件人标头”
以下是 From Header 的示例:
From: John Doe <john@doe.org>
我希望它转换成这个 XML:
<From>
<Mailbox>
<DisplayName>John Doe</DisplayName>
<Address>john@doe.org</Address>
</Mailbox>
</From>
我想使用词法分析器“Alex”(http://www.haskell.org/alex/doc/html/)来分解(标记)From Header。
我想使用解析器“Happy”(http://www.haskell.org/happy/)来处理标记并生成解析树。
然后我想使用序列化程序来遍历解析树并输出 XML。
From Header 的格式由 Internet 消息格式 (IMF)、RFC 5322 ( https://www.rfc-editor.org/rfc/rfc5322 ) 指定。
以下是 From Headers 和所需 XML 输出的更多示例:
从没有显示名称的标题:
From: <john@doe.org>
所需的 XML 输出:
<From>
<Mailbox>
<Address>john@doe.org</Address>
</Mailbox>
</From>
来自没有显示名称且地址周围没有尖括号的标题:
From: john@doe.org
所需的 XML 输出:
<From>
<Mailbox>
<Address>john@doe.org</Address>
</Mailbox>
</From>
来自具有多个邮箱的 Header,每个邮箱用逗号分隔:
From: <john@doe.org>, "Simon St. John" <simon@stjohn.org>, sally@smith.org
所需的 XML 输出:
<From>
<Mailbox>
<Address>john@doe.org</Address>
</Mailbox>
<Mailbox>
<DisplayName>Simon St. John</DisplayName>
<Address>simon@stjohn.org</Address>
</Mailbox>
<Mailbox>
<Address>sally@smith.org</Address>
</Mailbox>
</From>
RFC 5322 说注释的语法是:( … )。这是一个包含评论的 From Header:
From: (this is a comment) "John Doe" <john@doe.org>
我希望在词法分析期间删除所有评论。
所需的 XML 输出是这样的:
<From>
<Mailbox>
<DisplayName>John Doe</DisplayName>
<Address>john@doe.org</Address>
</Mailbox>
</From>
RFC 说,可以在 From Header 中散布“折叠空格”。这是一个 From Header,第一行是 From: 标记,第二行是显示名称,第三行是地址:
From:
"John Doe"
<john@doe.org>
XML 输出不应受折叠空格的影响:
<From>
<Mailbox>
<DisplayName>John Doe</DisplayName>
<Address>john@doe.org</Address>
</Mailbox>
</From>
RFC 说,地址中的 @ 字符之后可以是括在括号中的字符串,例如:
From: "John Doe" <john@[website]>
我必须承认,我从未见过与此相关的电子邮件。尽管如此,RFC 说它是允许的,所以我当然希望我的词法分析器和解析器处理这样的输入。这是所需的输出:
<From>
<Mailbox>
<DisplayName>John Doe</DisplayName>
<Address>john@[website]</Address>
</Mailbox>
</From>
错误处理
如果 From Header 不正确,我希望生成一个错误。以下是一些错误的 From Headers 示例和所需的输出:
显示名称错误地放在地址之后:
From: <john@doe.org> "John Doe"
输出应指定发现错误的位置:
serialize: parse error at line 1 and column 22. Error occurred at "John Doe"
此 From Header 在显示名称前有一个错误的“23”:
From: 23 "John Doe" <john@doe.org>
同样,输出应指定发现错误的位置:
serialize: parse error at line 1 and column 10. Error occurred at "John Doe"
您能否展示如何实现词法分析器、解析器和序列化器?