【问题标题】:Email Forwarding like Craigslist - Rails像 Craigslist 一样的电子邮件转发 - Rails
【发布时间】:2011-08-30 01:12:01
【问题描述】:

我正在尝试做 craigslist 的匿名电子邮件所做的事情,但使用 Rails,也很便宜。能够在电子邮件中添加标题对我来说很重要,这就是为什么基本的电子邮件转发不起作用的原因。

我想到的一种方法是 SMTP 服务器,每当我通过 POP/IMAP 阅读电子邮件时,我都会向电子邮件的真正收件人发送一封电子邮件,其中包含正确的 FROM 地址并添加标题。这可行,但 SMTP 服务器相对昂贵。

另一种方法是转发/重定向电子邮件,但在中间添加标题。我找不到任何服务或宝石来做到这一点。

请不要只说“电子邮件管道”,因为这实际上意味着将电子邮件提供给您的 Rails 程序,收到电子邮件后您会做什么?你实际上是如何转发它的。

有什么想法吗?

【问题讨论】:

    标签: ruby-on-rails email email-forwarding


    【解决方案1】:

    您需要一个使用域的电子邮件地址,该域具有您的系统管理员可以控制的 MX 服务器。这可能是您的主域的子域。那么你要做的,是配置 MTA 软件(Exim、Postfix...希望不是 qMail!)以将该电子邮件传送到 Rails:

    http://guides.rubyonrails.org/action_mailer_basics.html#receiving-emails

    如果 MTA 未与 rails 应用程序本身安装在同一台服务器上,则您必须将电子邮件传送到一个小的临时转发器脚本,该脚本执行将电子邮件发送到您的应用程序的操作,其中然后您手动将其传递给您的邮件。

    在您的邮件程序中,您可以访问所有标题、正文、附件等。如果您在主题或回复地址中放置了一些唯一标识符,您就可以决定要实例化哪个邮件程序来转发邮寄给它的预定收件人。

    我们还没有这样做,但出于同样的原因,我们将这样做。但是,如果您不熟悉配置 MTA,这可能有点过头了。你有系统管理员可以完成这个任务吗?

    在代码级别,我会这样做:

    1. 用户 A (id = 1234) 向用户 B (id = 5678) 发送电子邮件

    2. 从您拥有的任何您想要的地址发送电子邮件,但将Reply-To: 设置为Reply-To: <mail-1234-5678-abcdefabcd1234567890abcdefabcdef@usermessages.your-domain.com> 之类的东西

      这绝对是这项工作的关键。它包括发件人的 ID、收件人的 ID 和防止伪造的校验和。校验和可以从每个用户唯一的盐生成,并且很简单:

      checksum = Digest::MD5.hexdigest("#{sender.id}-#{recipient.id}-#{sender.mailer_salt}")

    3. 现在,当您通过为“usermessages.your-domain.com”域配置的 MX 收到回复时,您要做的第一件事是通过解析 To: 字段来识别发件人和收件人。您可以通过split'ing 部分轻松识别发件人和收件人。然后,您可以生成校验和并确保它匹配,以确保没有人试图恶意发送邮件,就好像它来自另一个用户一样。

    4. 一旦您弄清楚了所涉及的用户,请继续发送另一封电子邮件,其中一个特殊的 Reply-To: 标头(显然,ID 颠倒了,摘要使用不同的盐完成)。

    这是一个非常基本但功能完善的示例。您可以将此摘要放在您想要的任何位置,前提是它会在回复返回时保留(这使得 Reply-To: 标头非常适合。某些服务使用主题行代替。

    我会避免使盐成为用户控制的东西,例如用户的密码哈希,因为如果用户更改该信息(更改他们的密码),校验和将不再有效。

    【讨论】:

    • 感谢您的回复!我对管道部分很好。我想我不明白的是“将电子邮件转发给预期的收件人”。我希望我的发件人:地址是发送电子邮件的人。但是,据我了解,如果您拥有自己的邮寄服务,那么更改发件人地址是非常糟糕的做法,并且通常会使您被过滤掉。这是真的吗?
    • 没错,您永远不应该向不属于您的地址发送“发件人”电子邮件……这很可能会卡在垃圾邮件过滤器中。我以为你还是想匿名做这件事?我将通过更深入地讨论我将如何设计它来更新我的答案。
    • 查看我修改后的答案,了解有关在 Rails 级别做什么的技术讨论。请记住,我没有这样做;我一直在考虑,因为我们也会这样做。
    • 还请注意 Steve 的回答,即当您已经启动并准备好通过 HTTP 使用的环境时,避免将邮件直接传送到 Rails。
    • 嗯,我想更改发件人地址的原因是因为 craigslist 实际上就是这样做的。它会将电子邮件转发给他们,让它看起来像是我发送的。我认为可靠地做到这一点的唯一方法是通过像 sendgrid 这样的服务?
    【解决方案2】:

    如果您的应用程序要扩展,尤其是跨多个服务器,那么我不会推荐默认的 Rails 接收电子邮件方式。看看我写的一篇博文 here 关于一些选项。

    基本前提是您希望在一个包罗万象的域中接收邮件。您可以使用 imap/pop3 从 gmail 之类的服务器转发/收集,也可以使用 CloudMailin 之类的服务来负责将消息传递到您的应用程序。您可以给每个用户一个唯一的地址,甚至只使用消息的一次性部分,例如 normal+disposable@domain.com。

    那么这只是使用mail gem 来检查消息并添加您需要的任何标题并再次发送消息的情况。同样,您可以使用自己的电子邮件服务器进行此交付,或者如果您想提高您的交付能力,则可以依赖 Amazon 的 Simple Email Service 等服务。

    【讨论】:

    • 感谢您的回复。我没有看过亚马逊的简单电子邮件服务。这会让我控制 from: 标头,使其看起来像是从最初发送电子邮件的人发送的?
    • 我同意您在博客文章中提到的内容... Rails 文档建议您执行此操作的方式(通过管道,这将导致惊人的环境初始化开销)小于理想的。您肯定希望将其发布到您的应用中。
    • 问得好,塔里克。我还没有使用过亚马逊的 SES(还没有),但我想我读到它确实可以让您发送 from 您选择的地址。 (设置 From: 标头很容易——它是 DKIM 等,您需要防止客户相信您的邮件是网络钓鱼和 From: 标头伪造)。问题是您必须手动验证每个发件人......如果您控制发件人地址,这没有问题,但如果您想让您的应用程序的任何用户成为通过 Amazon SES 的发件人,则会出现问题。
    猜你喜欢
    • 2014-02-07
    • 1970-01-01
    • 1970-01-01
    • 2011-09-23
    • 2012-10-19
    • 2011-08-22
    • 1970-01-01
    • 2013-07-29
    • 2011-11-25
    相关资源
    最近更新 更多