Ruby-on-rails Rails - 邮件,以纯文本形式获取正文

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/4868205/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-03 00:16:29  来源:igfitidea点击:

Rails - Mail, getting the body as Plain Text

ruby-on-railsruby-on-rails-3herokuactionmailer

提问by AnApprentice

Given: message = Mail.new(params[:message])

鉴于: message = Mail.new(params[:message])

as seen here: http://docs.heroku.com/cloudmailin

如下所示:http: //docs.heroku.com/cloudmailin

It shows how to get the message.body as HTML, how to do you get the plain/text version?

它显示了如何将 message.body 获取为 HTML,如何获取纯文本版本?

Thanks

谢谢

回答by Steve Smith

The code above:

上面的代码:

message = Mail.new(params[:message])

will create a new instance of the mail gemfrom the full message. You can then use any of the methods on that message to get the content. You can therefore get the plain content using:

将从完整消息创建邮件 gem的新实例。然后,您可以使用该消息上的任何方法来获取内容。因此,您可以使用以下方法获取纯内容:

message.text_part

or the HTML with

或 HTML 与

message.html_part

These methods will just guess and find the first part in a multipart message of either text/plain or text/html content type. CloudMailin also provides these as convenience methods however via params[:plain] and params[:html]. It's worth remembering that the message is never guaranteed to have a plain or html part. It may be worth using something like the following to be sure:

这些方法只会猜测并找到 text/plain 或 text/html 内容类型的多部分消息中的第一部分。CloudMailin 也通过 params[:plain] 和 params[:html] 提供了这些作为方便的方法。值得记住的是,永远不能保证消息具有纯文本或 html 部分。可能值得使用以下内容来确保:

plain_part = message.multipart? ? (message.text_part ? message.text_part.body.decoded : nil) : message.body.decoded
html_part = message.html_part ? message.html_part.body.decoded : nil

As a side note it's also important to extract the content encoding from the message when you use these methods and make sure that the output is encoded into the encoding method you desire (such as UTF-8).

作为旁注,使用这些方法时从消息中提取内容编码也很重要,并确保将输出编码为您想要的编码方法(例如 UTF-8)。

回答by fiedl

What is Mail?

什么是Mail

The messagedefined in the question appears to be an instance of the same Mailor Mail::Messageclass, which is also used in ActionMailer::Base, or in the mailman gem.

message问题中所定义似乎是相同的一个实例MailMail::Message类,它也被用在ActionMailer::Base,或在邮递员宝石

I'm not sure where this is integrated into rails, but Steve Smith has pointed outthat this is defined in the mail gem.

我不确定它是在哪里集成到 rails 中的,但Steve Smith 指出这是在mail gem 中定义的。

Extracting a Part From a Multipart Email

从多部分电子邮件中提取部分

In the gem's readme, there is an example section on reading multipart emails.

在 gem 的自述文件中,有一个关于阅读多部分电子邮件示例部分

Besides the methods html_partand text_part, which simply find the first part of the corresponding mime type, one can access and loop through the parts manually and filter by the criteria as needed.

除了方法html_partand text_part,它只是简单地找到相应 mime 类型的第一部分,还可以手动访问和循环这些部分,并根据需要按条件过滤。

message.parts.each do |part|
  if part.content_type == 'text/plain'
    # ...
  elsif part.content_type == 'text/html'
    # ...
  end 
end

The Mail::Partis documented here.

Mail::Part记录在这里

Encoding Issues

编码问题

Depending on the source of the received mail, there might be encoding issues. For example, rails could identify the wrong encoding type. If, then, one tries to convert the body to UTF-8 in order to store it in the database (body_string.encode('UTF-8')), there might be encoding errors like

根据接收邮件的来源,可能存在编码问题。例如,rails 可以识别错误的编码类型。那么,如果有人试图将正文转换为 UTF-8 以将其存储在数据库 ( body_string.encode('UTF-8')) 中,则可能会出现编码错误,例如

Encoding::UndefinedConversionError - "\xFC" from ASCII-8BIT to UTF-8

(like in this SO question).

(就像在这个 SO question 中一样)。

In order to circumvent this, one can readout the charset from the message part and tell rails what charset it has been before encoding to UTF-8:

为了规避这一点,可以从消息部分读出字符集并告诉 rails 在编码为 UTF-8 之前它是什么字符集:

encoding = part_to_use.content_type_parameters['charset']
body = part_to_use.body.decoded.force_encoding(encoding).encode('UTF-8')

Here, the decodedmethod removes the header lines, as shown in the encoding section of the mail gem's readme.

在这里,该decoded方法删除了标题行,如邮件 gem 自述文件编码部分所示。

EDIT: Hard Encoding Issues

编辑:硬编码问题

If there are really hard encoding issues, the former approach does not solve, have a look at the excellent charlock_holmes gem.

如果确实存在硬编码问题,前一种方法无法解决,请查看优秀的charlock_holmes gem

After adding this gem to the Gemfile, there is a more reliable way to convert email encodings, using the detect_encodingmethod, which is added to Strings by this gem.

将此 gem 添加到 后Gemfile,有一种更可靠的方法来转换电子邮件编码,使用detect_encoding方法,该方法由此 gem 添加到 Strings。

I found it helpful to define a body_in_utf8method for mail messages. (Mail::Partalso inherits from Mail::Message.):

我发现定义body_in_utf8邮件消息的方法很有帮助。(Mail::Part也继承自Mail::Message.):

module Mail
  class Message
    def body_in_utf8
      require 'charlock_holmes/string'
      body = self.body.decoded
      if body.present?
        encoding = body.detect_encoding[:encoding]
        body = body.force_encoding(encoding).encode('UTF-8')
      end
      return body
    end
  end
end

Summary

概括

# select the part to use, either like shown above, or as one-liner
part_to_use = message.html_part || message.text_part || message

# readout the encoding (charset) of the part
encoding = part_to_use.content_type_parameters['charset'] if part_to_use.content_type_parameters

# get the message body without the header information
body = part_to_use.body.decoded

# and convert it to UTF-8
body = body.force_encoding(encoding).encode('UTF-8') if encoding

EDIT: Or, after defining a body_in_utf8method, as shown above, the same as one-liner:

编辑:或者,定义一个body_in_utf8方法后,如上所示,与单行相同:

(message.html_part || message.text_part || message).body_in_utf8

回答by Kirill Bezrukov

email = Mail.new(params[:message])
text_body = (email.text_part || email.html_part || email).body.decoded

I'm using this solution on RedmineCRM Helpdesk plugin

我在RedmineCRM 帮助台插件上使用此解决方案

回答by W. Andrew Loe III

I believe if you call message.text_part.body.decoded you will get it converted to UTF-8 for you by the Mail gem, the documentation isn't 100% clear on this though.

我相信如果你调用 message.text_part.body.decoded ,你会通过 Mail gem 将它转换为 UTF-8,不过文档并不是 100% 清楚。

回答by Dhanshree

Save HTML Body Format in Rails USE <%= @email.body.html_safe%> This will send text written in email text editor as it is to email.

在 Rails 中保存 HTML 正文格式 USE <%= @email.body.html_safe%> 这会将在电子邮件文本编辑器中编写的文本发送到电子邮件。