Reputation: 666
I have a Rails 5.2.0 api app with a limited set of middleware. From the app I want to serve a css file to browsers requesting it.
The content of the css file depends on the request params, so I'd like to be able serve the file from a controller. I already do this successfully with a script. Here is my implementation:
Rails.application.routes.draw do
get "assets/script" => "assets#script"
get "assets/stylesheet" => "assets#stylesheet", :format => :css
end
class AssetsController < ApplicationController
## This action works
def script
js = ActionController::Base.render(
"assets/script", assigns: {foo: params[:foo]}
)
render :js => js
end
## This action doesn't work
def stylesheet
css = ActionController::Base.render(
"assets/stylesheet", assigns: {foo: params[:foo]}
)
render :plain => css
end
end
When a browser requests the script it becomes available in the browser:
<script>$.getScript("https://example.com/assets/script");</script>
However that is not the case with my stylesheet:
$('<link/>', {
rel: 'stylesheet',
href: "https://example.com/assets/stylesheet.css"
}).appendTo('head');
The stylesheet is returned and added in the browser, but it isn't put to use. I can serve the exact same content from the /public
folder of a regular Rails app, and it will be put to use.
I must be missing something, maybe some response headers. Any idea what I'm missing?
Upvotes: 4
Views: 1339
Reputation: 18464
Browsers expect css to be served with corresponding content type:
render body: css, content_type: 'text/css'
Rails has default mime type for this: render css: css
Also you can render in one step:
render template: "assets/stylesheet", formats: [:css], assigns: {foo: params[:foo]}
Upvotes: 3