Reputation: 1907
I have Rails 6, my preview class located in
mailer/previews/devise_mailer_preview.rb:
class DeviseMailerPreview < ActionMailer::Preview
...
end
And when I run application locally, everything is going fine, I can see my email previews on http://localhost:3000/rails/mailers/devise_mailer/confirmation_instructions
address. But now Im trying to deploy application on server, and found that when I run bundle exec rails c production
, I got the error:
/home/deploy/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/zeitwerk-2.3.0/lib/zeitwerk/loader/callbacks.rb:17:in `on_file_autoloaded': expected file /home/deploy/project/releases/20200627024908/app/mailer/previews/devise_mailer_preview.rb to define constant Previews::DeviseMailerPreview, but didn't (Zeitwerk::NameError)
After that I've checked locally RAILS_ENV=production rails c
, and got same.
If I will rename DeviseMailerPreview class to Previews::DeviseMailerPreview, it will be broken and I cannot see emails on development, because Rails 6, accordingly to docs, expect exactly that name.
More of that, I've found in this article, that zeitwerk can be configured with autoload_paths
param to avoid ruby's NameError. I found that I have it my config/application.rb:
config.load_defaults 6.0
Anyway I tried to add same row in my config/environments/production.rb file, but it didn't help.
What am I doing wrong and how can I fix it? Thanks in advance!
Upvotes: 2
Views: 2020
Reputation: 2324
In Rails 6, previews are added to the autoload paths only if options.show_previews
is true, which is not by default in the production environment. See the source code here.
The reason for this is that previews are supposed to be an aid for development, and they are generally not something you want to be able to look at in production.
However, you can set that flag to true
in production if you want.
There's another derivative: By storing the previews under app/mailers
, Rails is going to eager load them because app/mailers
is in the autoload paths. If app/mailers/previews
is not in the autoload paths, eager loading will fail due to the namespace mismatch. Either you have them enabled in all environments, or else is better to have them in a separate location, like the default.
Upvotes: 1
Reputation: 318
Add preview_path
to the autoload_paths
and zeitwerk will expect DeviseMailerPreview
constant to be defined.
# development.rb
config.action_mailer.preview_path = Rails.root.join("app/mailers/previews")
# application.rb
config.autoload_paths << Rails.root.join("app/mailers/previews")
Upvotes: 1
Reputation: 543
Your Mailer preview file is located in mailer/previews/devise_mailer_preview.rb
, so I'm assuming it's full path is app/mailer/previews/devise_mailer_preview.rb
The docs says
In the above example, the preview class for
UserMailer
should be namedUserMailerPreview
and located intest/mailers/previews/user_mailer_preview.rb
So put your devise_mailer_preview.rb
file to test/mailers/previews/devise_mailer_preview.rb
or in your config/application.rb
add this line and restart:
config.action_mailer.preview_path = "#{Rails.root}/app/mailers/previews"
Actually the answer was in the docs itself.
Upvotes: 0