i have code like this
Mailman::Application.run do
to 'email#local.com' do
## how to get subject, from and body in here
end
end
how to get subject, from and body from email in rails?
Use mail gem https://github.com/mikel/mail/
Mailman::Application.run do
default do
mail = Mail.new(message)
from = message.from.first
content = mail.parts[1].body.decoded
subject = message.subject
//your other code
end
end
Related
I'm following this tutorial: https://github.com/sendgrid/sendgrid-ruby/. Very straightforward. However, I want to avoid having a big chunk of code in my controller to send an email. It currently looks like this:
from = Email.new(email: 'some#email.com')
to = Email.new(email: 'some#email.com')
subject = 'Sending with SendGrid is Fun'
content = Content.new(type: 'text/plain', value: 'and easy to do anywhere, even with Ruby')
mail = Mail.new(from, subject, to, content)
sg = SendGrid::API.new(api_key: 'key')
response = sg.client.mail._('send').post(request_body: mail.to_json)
Ideally, I'd like to be able to trigger it from a service like: SendMail.new.perform() or some nice one-liner in the controller.
How would I abstract this code away from the controller and how would I call that new service/abstraction?
Twilio SendGrid developer evangelist here.
You can absolutely extract that from your controller, this is normally described as a service object.
I like to keep service objects in the app folder. You can do so by creating the directory app/services. Then create a file for the class, app/services/email_service.rb for example. In that file add the code to send the email, maybe something like this:
class EmailService
def self.call(from:, to:, subject:, content:)
self.new.send_email(from: from, to: to, subject: subject, content:
end
def initialize()
#sendgrid = SendGrid::API.new(api_key: Rails.application.credentials.sendgrid)
end
def send_email(from:, to:, subject:, content:)
from = Email.new(email: from)
to = Email.new(email: to)
content = Content.new(type: 'text/plain', value: content)
mail = Mail.new(from, subject, to, content)
response = #sendgrid.client.mail._('send').post(request_body: mail.to_json)
end
end
You can then call this service from your controller with the one liner:
EmailService.call(from: "me#mydomain.com", to: "you#yourdomain.com", subject: "My new email service", content: "It's pretty wonderful")
As a bonus, it's also easier to unit test the EmailService separate to the controller and to mock it out in controller tests.
If you are using rails, you can define it in your environment file and use one line code to send email from your controller.
production.rb
config.action_mailer.delivery_method = :sendmail
# Defaults to:
# config.action_mailer.sendmail_settings = {
# location: '/usr/sbin/sendmail',
# arguments: '-i'
# }
config.action_mailer.perform_deliveries = true
config.action_mailer.raise_delivery_errors = true
config.action_mailer.default_options = {from: 'no-reply#example.com'}
and in your controller
mail( :to => #user.email,
:subject => 'Thanks for signing up for our amazing app' )
best case for using sendmail is using it with an ActionMailer class. You can look it up at rails documentation.
I've been implementing the sendgrid-ruby gem to send email via SendGrid. I'm using templates exclusively for my messages to send. I've got everything working on the outbound side using the TemplateMailer implementation.
This is the code:
unique_args = {unique_args: {MyAuditNumber: "9999999"}}
# Create a sendgid recipient list
recipients = []
recipient = SendGrid::Recipient.new(to_email)
merge_vars.each do |mv|
Rails.logger.debug(mv)
recipient.add_substitution('*|' + mv["name"] + '|*', mv["content"])
end
recipients << recipient
# Create a sendgrid template
template = SendGrid::Template.new(template_id)
# Create a client
client = SendGrid::Client.new(api_key: Rails.configuration.sendgridkey)
mail_defaults = {
from: from_email,
from_name: from_name,
to: to_email,
to_name: to_name,
bcc: bcc,
html: ' ',
text: ' ',
subject: subject
}
mailer = SendGrid::TemplateMailer.new(client, template, recipients)
# send it
lres = mailer.mail(mail_defaults)
The last thing I want to do is to add a unique identifier to each message that I send.
I've read both the SendGrid documentation as well as several questions and other articles (
how to get response of email sent using sendgrid in rails app to save in database
http://thepugautomatic.com/2012/08/sendgrid-metadata-and-rails/
https://sendgrid.com/docs/Integrate/Code_Examples/SMTP_API_Header_Examples/ruby.html
)
I can tell that I need to add unique_args to the smtp API. But what I can't figure out is how to pass that into the SendGrid routines.
I've tried things like:
recipient.add_to_smtpapi( unique_args )
and
recipient.add_to_smtpapi( unique_args.to_json )
and
mail_defaults = {
smtpapi: unique_args,
from: from_email,
...
and
mail_defaults = {
smtpapi: unique_args.to_json,
from: from_email,
...
These attempts generally result in an error message like:
undefined method `add_filter' for "{\"unique_args\":{\"MyAuditNumber\":\"9999999\"}}":String
Does anyone know how to pass unique_args when using the TemplateMailer?
Based on gem documentation, what you should do is the following:
header = Smtpapi::Header.new
header.add_unique_arg("MyAuditNumber", "9999999")
mail_defaults = {
smtpapi: header
...
I am working on rails 2 application with sending email functionality. Now, I need to send inline image with the email.
I am using Mailer to send email. I tried lots of time using different ways but not succeed to send image inline in email. Below code i am using to send email.
# Controller
Mailer.delivery_my_opinion_reply(user, my_opinion, answer)
# Model / Mailer.rb
def my_opinion_reply(user, my_opinion, answer)
#subject = "My opinion"
#from = "#{Settings.site_name}"
#recipients = user.email
#content_type = "multipart/alternative"
#attachments.inline['test.jpg'] = File.read(RAILS_ROOT + "/public/system/att_images/728/original/ball1.jpg")
#body = {:question => my_question, :user => user}
end
I got error "undefined method inline for nil class"
try this way
#attachments.inline['image.png'] = File.read("app/assets/images/image.png")
mail(to: email, subject: "subject", content_type: "text/html")
In my app, I store emails.
I want to parse those emails for email addresses in the text, on the fly and replace them with a link (so that we send the email through the app).
e.g.
#email.body = "Hi Tom, Drop me a line at jerry#cheese.com."
I want some sort of helper that will translate that on the fly to:
#email.sanitized_body
"Hi Tom, Drop me a line at #{link_to "Email", email_send_email_path("jerry#cheese.com")}."
I've been around a few circles.
e.g. in a model
Class Email
def sanitized_body
text = self.body
emails = text.scan(/\b[A-Z0-9._%+-]+#[A-Z0-9.-]+\.[A-Z]{2,4}\b/i)
emails.each do |email|
text.gsub!("jerry#cheese.com", helper.link_to("email", "http://www.google.com"))
end
text
end
I'm sure there's a sensible way of doing this, probably with a helper but can't quite work it out...
module EmailsHelper
def sanitized_body(email_body)
text = email_body
emails = text.scan(/\b[A-Z0-9._%+-]+#[A-Z0-9.-]+\.[A-Z]{2,4}\b/i)
emails.each do |email|
text.gsub!("jerry#cheese.com", "#{link_to("email", "http://www.google.com")}")
end
text
end
end
Gets me almost there. But the text comes out as text in the string when displayed.
Any help much appreciated.
You should use html_safe for your text to be rendered as HTML code instead of a simple string.
module EmailsHelper
def sanitized_body(email_body)
text = email_body
emails = text.scan(/\b[A-Z0-9._%+-]+#[A-Z0-9.-]+\.[A-Z]{2,4}\b/i)
replace_text = "You text %s" % helper.link_to("email", "http://www.google.com")
emails.each do |email|
text.gsub!("jerry#cheese.com", replace_text.html_safe)
end
text
end
end
While fetching email, TMail appears to parse the email body twice,when I use this code.All the other parameters are fine(from_email,email_subject).
Any ideas?
def get_mail
Net::POP3.enable_ssl(OpenSSL::SSL::VERIFY_NONE)
Net::POP3.start('pop.gmail.com', 995, "uname","pass") do |pop|
mail_header=[];mail_subject=[];mail_body=[];mail_from=[]
unless pop.mails.empty?
pop.each_mail do |mail|
email = TMail::Mail.parse(mail.pop)
mail_subject = email.subject
mail_body = email.body
mail_from = email.from
email_obj=EmailedQueries.new
email_obj.save_email(mail_from, mail_subject, mail_body)
end
end
end
end
No idea ;-)
I've no clue what your real problem is. But have you tried the (new?) mail gem - it's used in Rails3: http://github.com/mikel/mail .