In my Rails (Rails 7) app, I have some small assets (a logo and a favicon), which I want to render in production as well as in development.
I put the assets in /app/assets/images.
Since setting # config.assets.compile = true
is not recommended, i run RAILS_ENV=production bundle exec rake assets:precompile
. It then builds a whole lot of files (it runs esbuild app/javascript/application.tsx
since I have a typescript react app running in this rails app.) and puts them in /public/assets/
. But this folder is .gitignore
d by default. Since the folder is approx 5.5 Mb I can see why. Now, heroku docs tell me to add /public/assets/
to git and then my assets should show, but why then is this directory gitignored by default?
Am I missing something? Should I just remove the dir from my .gitignore file?
Or could I just put the assets in the public
folder directly? If so, how do I add an image referencing the public folder in an erb file?
CodePudding user response:
Thanks for the comments, I went with adding the assets to the public folder directly and this works fine. It would be nice though if Heroku would either support a way to generate the assets after deployment by default, or describe an option to do it like I did in their docs.
CodePudding user response:
The home for static assets is the /public
folder. In a default Rails 7 app you will find some error pages (e.g. /public/404.html
) and icons (e.g. /public/favicon.ico
) already in that folder. Files in this folder will be available both directly, example.com/favicon.ico
, and under the public path, example.com/public/favicon.ico
. Serving public files can be disabled, see below.
To answer your sub-question, "how do I add an image referencing the public folder in an erb file?" you need to make sure you tell Rails it's an absolute path, not a relative one somewhere in the asset pipeline. This is done with a leading forward slash.
The following compares including a logo called logo.png
when it's stored in app/assets/images
vs /public
<%= image_tag "logo.png" %>
<!-- becomes <img src="/assets/logo-1f04fdc3ec379029cee88d56e008774df299be776f88e7a9fe5.png"> or similar -->
<%= image_tag "/logo.png" %>
<!-- note the leading slash. This becomes <img src="/logo.png"> -->
<img src="/logo.png">
<!-- or use plain HTML if you don't need/want to use the helper -->
You can also use sub-directories; /public/images/logo.png
would be available at /images/logo.png
(or image_tag "/images/logo.png"
).
The second paragraph of chapter 2 of The Asset Pipeline Rails Guide contians more information. It mentions that this functionality depends on whether config.public_file_server.enabled
is set.
In Rails 7 that config defaults to ENV["RAILS_SERVE_STATIC_FILES"].present?
in config/production.rb
. If you're using Heroku you can check this variable with heroku config:get RAILS_SERVE_STATIC_FILES
.
The guide also has more information on how to adjust all this behaviour to have these files served by your upstream web server (e.g. nginx) or from a CDN.