Peter Nixey
Peter Nixey

Reputation: 16565

In actionmailer how can you override the default_url_options at runtime?

I need to be able to generate links to sites that all run off my app but which have different domains (I'm running a whitelabel service).

The email being sent on behalf of these domains to set a different host depending on the mailing.

Normally I'd setup the host value application.rb:

config.action_mailer.default_url_options[:host] = 'myhost.com'

However, because my host varies according to the link I'm trying to do this at runtime instead.

user_mailer.rb:

Rails.configuration.action_mailer.default_url_options[:host] = new_host
mail(...)

The problem is that every time I run this it continues to use whatever's defined in application.rb. I can't seem to get the application to respect the newly defined value of default_url_optiions[:host]. What am I doing wrong?

Upvotes: 1

Views: 1742

Answers (2)

Artin Boghosian
Artin Boghosian

Reputation: 311

The default_url_options method is set on ActionMailer using class_attribute which is defined in ActiveSupport core extensions for Class. According to the documentation it also provides an instance level accessor that can be overridden on a per instance basis without affecting the class level method. So you should be able to override the host setting directly for each email

class UserMailer < ActionMailer::Base
  def welcome(user)
    @user = user

    # don't need this if you override #mail method.
    self.default_url_options = default_url_options.merge(host: @user.host)

    mail(to: user.email, subject: "Welcome")
  end

  # might be better to override mail method if you need it for all emails in
  # a particular mailer
  private

  def mail(headers, &block)
    self.default_url_options = default_url_options.merge(host: @user.host)

    super
  end
end

This should allow you to modify the setting at runtime; please ignore the @user.host call and replace it with however you would determine the host.

Upvotes: 4

Tigraine
Tigraine

Reputation: 23648

If there aren't a whole lot of views you could simply define the host on the url_for helper, and if there are too many views I'd suggest you write your own helper that wraps the url_for helper with the :host => 'mysite.com'.

Upvotes: 1

Related Questions