I'm upgrading to rails 3.1 and I need to have the /images directory be an alias to /assets. Is this possible? The reason being I don't want emails that I have sent out to clients which have direct links to files in /images to break.
Is this possible at the web server level? I'm on nginx.
You can do this in nginx
location /images {
alias /usr/share/rails_app/public/assets/images;
}
Though I think the bigger problem will be when you run
rake assets:precompile
It will add a md5hash string to your images. This hash string is added to force browsers to download changed images, so it doesn't use the browser cache. Since the names of the images will be different. It might make more sense to host the old images in a static directory with nginx.
Related
I have been handed a Ruby Project that creates a document and serves it to the user, when I try to access the file on a local environment it it is delivered correctly, (this is the code that does so).
filepath = Rails.root.join("public",#records.document.url)
send_file (filepath)
So I know the file is constructed correctly and sending it to the user using send_file works at least in a local environment.
But when it's deployed on the production server (running Amazon EC2, ubuntu, deployed with dokku) I get a 500 Internal server error:
ActionController::MissingFile (Cannot read file *path of the file*)
Few things I'm noticing: doing a find / -iname "*filename*" tells me the file is stored in var/lib/docker/overlay2/*container_name*/merged/app/public/filename and var/lib/docker/overlay2/*container_name*/diff/app/public/filename but the result of joining Rails.root with the filename is app/public/filename, do I need to pass send_file the whole filepath?
I googled for a couple hours and it seems nginx has no access to the public folder because it's running in the host machine while the app is inside a container? How would I know if that is the case and if so, how should I serve the file?
The person who originally wrote the code told me to use OpenURI.open_uri() but googling it doesn't seem to turn up anything applicable to the situation.
Nothing you're doing here actually makes sense - its sounds like you're just following a bunch of misinformation down a bunch of rabbit holes.
The way this is supposed to work is that the files in /public - not /app/public are served directly by the HTTP server (NGinX or Apache) in production and your Rails application in development (so you don't have to configure a local HTTP server). The /app directory is for your application code and uncompiled assets. Do not serve files from there - ever.
The /public directory is used for your compiled assets and stuff like robots.txt, the default error pages and various icons. Serving the files directly by your HTTP server is far more efficient then serving them through your Rails application. You can do a litmus test to see if serving static assets are working by sending curl -v YOUR_URL/robots.txt.
If this isn't working in production you need to check your NGinX configuration. There is no shortage of guides on how to serve static files with NGinX and Docker.
Serving files with a Rails controller and send_data / send_file should only be done when its actually needed:
The file is not a static file or something that can be compiled at deploy time.
You need to provide access control to the files with your application.
Your proxying files from another source.
prentend that I have a file in .../web/main.dart and when I'm serving the app ( webdev serve web:8080) it will be located in localhost:8080/main.dart.js and the packages in localhost:8080/packages/ is there anyway to move them to localhost:8080/foo/main.dart and localhost/foo/packages/ ?
Basically add /foo/ to all dartdevc generated dictories.
No, that is not supported by the default dev server (and is unlikely ever to be).
The typical way to do this would be to set up a separate server, which delegates all things under the /foo route to the dev server, and strips out /foo from the path.
In this blog, it says that assets pipeline will compile, compress, and preprocess your assets from your app/assets and then placed the out into public/assets. I don't understand the below where it says you can set up a Nginx or Apache server to preprocess your assets for you after the it already has been outputed to the public/assets. Is it saying that you can choose to have additional servers such as Apache/Nginx to do the preprocessing for your while the Rails server does the compiling/compressing?
bundle exec rake assets:precompile
This will create (by default) an assets directory in your public/
folder. It will then add all the compressed and compiled files into
that directory, in the appropriate formats and with the new digested
versions. You can then set up Nginx or Apache to server those files
directly so that Rails doesn’t have to deliver them (and run the
on-the-fly preprocessing, etc.) itself.
I don't understand the below where it says you can set up a Nginx or Apache server to preprocess your assets for you…
It doesn't say that. It does say the following:
You can then set up Nginx or Apache to server [sic] those files…
There's a difference between preprocessing and serving files. What this documentation is suggesting is that if you're using a server like nginx, you can configure it to handle requests to assets that exist in your public/assets folder. This alleviates your Rails app from handling those requests.
Pre-processing is still handled by Rails in advance of nginx coming into the picture.
So we have resources in the grails-app/assets folder, i.e: javascript files, stylesheets and other documents.
Some of these documents are user docs which would have to have the option of being updated in production mode. When you usually add something to this assets folder, the grails app doesn't detect this change until after redeploying the app which would cause the folder to be reprocessed.
Is there any way to detect these changes in production systems or an alternate location other than the assets folder where grails would pick up this new/updated file without re-deployment ?
Under production the most recommendable approach is to have an Apache Httpd or an NGinx server as a front end where you put the static assets. In both cases you will need configure reverse proxy on NGinx or mod_jk (depending of your Java container.).
Inclusive you may think on store large assets in a repository like S3 (if you will run on Internet).
I have an action, that generates a PDF files and save it in the /public/output.pdf.
When I set
config.serve_static_assets = false
this file can't be found.
What's wrong ?
From the documentation:
"config.serve_static_assets configures Rails itself to serve static
assets. Defaults to true, but in the production environment is turned
off as the server software (e.g. Nginx or Apache) used to run the
application should serve static assets instead. Unlike the default
setting set this to true when running (absolutely not recommended!) or
testing your app in production mode using WEBrick. Otherwise you won´t
be able use page caching and requests for files that exist regularly
under the public directory will anyway hit your Rails app."
Which means that if you set that to false Rails will not serve any assets from your public folder as it is assumed that a front-end web server (apache/nginx) will handle it. This lessons the load on Rails as the front-end server is much, much more efficient at serving files directly.
After testing, I came to this conclusion:
1) when using the command
rails s -e production
Rails will only serve the statics files. Any other file created after you compile your assets will not be found.
To handle this, you need to execute your application under a web server like Apache, Nginx or other. These web servers will serve this files for you.
This looks to be obvious, but not for a beginner.