Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rails 4 static assets in public/ or app/assets/

Tags:

Sorry if this is a lengthy buildup to a simple question, but I wanted to get my thoughts clear.

I've used Rails 4 on a couple projects now and I've been using image_tag('/assets/image.png') to get around the changes to how asset path helpers work in Rails 4. That is until today when I decided to learn more about the changes and found this first change note in sprockets-rails. I've also noted that the ASSET_PUBLIC_DIRECTORIES in /actionview/lib/action_view/helpers/asset_url_helper.rb#L170 in Rails helpers only point to public folders. It became pretty obvious to me that if you are accessing static files, Rails wants you to use use the public folder.

So now that I've figured this out, I just can't understand why the edge rails docs clearly state this:

In previous versions of Rails, all assets were located in subdirectories of public such as images, javascripts and stylesheets. With the asset pipeline, the preferred location for these assets is now the app/assets directory.

image_path in practice generates a uri to the public/images folder which is totally contrary.

And to sum this all up I do need to use all available helpers and digest builders, because I end up deploying my assets to S3 with asset_sync.

So my question is just; is there a correct place to put images/non-compiled assets and use asset_path helpers? All the documentation and every other stack overflow conversation is about people using the app/assets folder, but sprockets-rails wants us to use public for non-digest assets. Are the docs and info on the web just in need of an update, or are others just making due with prepending all asset paths with /assets/?

UPDATE: I think I did actually have an issue where I wasn't restarting my development server and images in app/assets/images were not showing up so it would fallback to public. Also note that I was using asset helpers in my paperclip default_url (which is referenced as the way to point to assets in several stack overflow answers I found, however using the asset path helpers with interpolated options in paperclip will also fallback to public, because the uninterpolated asset name wouldn't be found as an existing file obviously.

like image 603
Taylor j. Eke Avatar asked Nov 22 '13 02:11

Taylor j. Eke


People also ask

How do you Precompile an asset?

To compile your assets locally, run the assets:precompile task locally on your app. Make sure to use the production environment so that the production version of your assets are generated. A public/assets directory will be created. Inside this directory you'll find a manifest.

What are assets in Rails?

The asset pipeline provides a framework to concatenate and minify or compress JavaScript and CSS assets. It also adds the ability to write these assets in other languages such as CoffeeScript, Sass and ERB. Prior to Rails 3.1 these features were added through third-party Ruby libraries such as Jammit and Sprockets.

What does rake assets Clean do?

The clean it removes the old versions of the precompiled assets while leaving the new assets in place. Show activity on this post. rake assets:clean removes compiled assets. It is run by cap deploy:assets:clean to remove compiled assets, generally from a remote server.

What is Require_tree?

The require_tree directive tells Sprockets to recursively include all JavaScript files in the specified directory into the output. These paths must be specified relative to the manifest file.

How are assets served from a Rails site?

In the default Rails development environment assets are served through a middleware called sprockets. In production however most one off Rails deployments will put their ruby server behind reverse HTTP proxy server such as Nginx which can load balance their sites and can serve static files directly.

Should I use public or app/assets for assets?

Any assets under public will be served as static files by the application or web server when config.public_file_server.enabled is set to true. You should use app/assets for files that must undergo some pre-processing before they are served. In production, Rails precompiles these files to public/assets by default.

How to set the asset host in rails?

To set your asset host in Rails, you need to set config.asset_host in config/environments/production.rb: You only need to provide the "host", this is the subdomain and root domain, you do not need to specify a protocol or "scheme" such as http:// or https://.

Can assets be placed in the public hierarchy?

Assets can still be placed in the public hierarchy. Any assets under public will be served as static files by the application or web server when config.public_file_server.enabled is set to true. You should use app/assets for files that must undergo some pre-processing before they are served.


1 Answers

When you use rake assets:precompile, Rails moves all of the assets from your app/assets folder, to public/assets. This is as a normal browser does not have access to your app directory, but does have access to public.

So, to answer your question, here are my thoughts. If your images are for your sites layout e.g logos or backgrounds, then you should store them in the app/assets/images directory, however, if the images are user generated, such as profile images, then these should be stored directly in something such as public/images. Ideally you would store those in S3 or a CDN, but you're already doing that.

As a bonus, Carrierwave, a Rails image upload gem, uses a public/images type path as the default store for its images, as you can see in their config file:

    # Override the directory where uploaded files will be stored.
    # This is a sensible default for uploaders that are meant to be mounted:
     def store_dir
     "images/#{model.class.to_s.underscore}/#{mounted_as}/#{model.id}"
     end

Hope this helps!

like image 112
Amar H-V Avatar answered Oct 18 '22 10:10

Amar H-V