I'm looking for 3 areas to work as dynamic assets:
image_path, javascript_path, and stylesheet_path
When I say dynamic, I mean that they will be dynamic through
controller/models. I have been working through approx. 12 hours of
searches to satisfy my answer to this question but am not finding much
luck.
The closest things I've found enabling this are use of config for assets
(which is normally done for CDNs), or monkey-patching the tag helpers,
which still won't give me what I want.
The reason why I want to do this is to provide for themes. As an
example, if your rails app contained 20 different themes, a theme would
be composed of layouts, images, javascripts, stylesheets, etc. You
wouldn't want to have to change your theme through an initializer and
stop/restart your app for it to work. I've already done a lot of leg
work with getting my themes into the MVC structure.
I just need the ability to change the three paths above using either a
custom call to a module, or through the application controller.
I'm looking for 3 areas to work as dynamic assets:
image_path, javascript_path, and stylesheet_path
When I say dynamic, I mean that they will be dynamic through
controller/models.
That only barely helps clarify. Defining something by repetition
doesn't work.
I have been working through approx. 12 hours of
searches to satisfy my answer to this question but am not finding much
luck.
The closest things I've found enabling this are use of config for assets
(which is normally done for CDNs), or monkey-patching the tag helpers,
which still won't give me what I want.
No, it probably won't unless you monkey-patch to look up the *current
user's* theme each time -- which is doable but potentially costly.
The reason why I want to do this is to provide for themes. As an
example, if your rails app contained 20 different themes, a theme would
be composed of layouts, images, javascripts, stylesheets, etc. You
wouldn't want to have to change your theme through an initializer and
stop/restart your app for it to work. I've already done a lot of leg
work with getting my themes into the MVC structure.
Is there a reason that you didn't use something like Liquid, which seems
to have been designed for exactly this purpose?
I just need the ability to change the three paths above using either a
custom call to a module, or through the application controller.
Can it be done and if so, how?
Of course it can be done by monkeypatching as described above. Whether
it should be done that way is another question.
Another possibility: I recently found out that Haml can use Sass as a
markup filter. This has some interesting potential for dynamically
generated CSS.
Thanks guys - I appreciate both of your responses.
Marnen, I did look at liquid previously and did so again this morning.
However, while I like what the developers are trying to do with certain
features, it's not for me.
And, the nice thing about my system is that there will always be a
default theme in place in a set location, for instance:
public/themes/default
That will be the base default theme.
What I have to really consider are quite a few things. First and
foremost are asset tags. If the asset tags don't include the current
theme, then caching is not going to work properly. There is an
interesting bit in the helper though:
So, my first decision is how to dynamically modify the assets_dir. I
know that assets can be modified through URLs (CDNs), but again, I'm
just now touching into looking through quite a bit of code to make sure
I understand what is going on step by step. Then, I'll create some test
code to play with.
Thanks guys - I appreciate both of your responses.
Marnen, I did look at liquid previously and did so again this morning.
However, while I like what the developers are trying to do with certain
features, it's not for me.
[...]
Why not? I've never used it, but it is a widely used solution to the
exact problem you're trying to solve.
Thanks guys - I appreciate both of your responses.
Marnen, I did look at liquid previously and did so again this morning.
However, while I like what the developers are trying to do with certain
features, it's not for me.
[...]
Why not? I've never used it, but it is a widely used solution to the
exact problem you're trying to solve.
A few reasons. First, I don't like the markup style they are using when
interacting with templates. They also go far above and beyond limiting
what I'm eventually going to do and that is implementing hooks within
templates. In addition, I really do not try to use other people's
plugins (unless it's something very minor). This is mainly because of
how I program, personally. I like to be able to adjust/alter and
understand exactly what is being developed and make alterations as need
be. Going with a plugin on this scale hampers my development as their
ideas and mine might differ and I'd end up monkey patching a plugin.
That's not for me.
I want to develop my own work. I can certainly learn from others and
their work, but that's something entirely different.
Thanks guys - I appreciate both of your responses.
Marnen, I did look at liquid previously and did so again this morning.
However, while I like what the developers are trying to do with certain
features, it's not for me.
As Marnen said you may want to reconsider - mephisto for example uses
liquid for themes and so on and you can change those on the fly
So, my first decision is how to dynamically modify the assets_dir. I
know that assets can be modified through URLs (CDNs), but again, I'm
just now touching into looking through quite a bit of code to make sure
I understand what is going on step by step. Then, I'll create some test
code to play with.
I wonder whether you're overthinking things slightly. If you had a
helper called current_theme_path that returned the path to the current
theme (eg themes/default/ initially, themes/minimalist/ etc...
then you should be able to stuff like style_sheet_tag
(current_theme_path + 'blah.css') or image_tag(current_theme_path +
'heading.png')
link href="/stylesheets/public/themes/default/stylesheets/default.css"
media="screen" rel="stylesheet" type="text/css"
.. which won't work.
The issue here is that /stylesheets is being used as the default
stylesheets_path through rails. In order to utilize such a helper, I
have to first change the stylesheet_path to go to ''.
The same would have to be done for image_path, javascripts_path, etc.
However, looking through all of the code I just don't see a way to tie
into changing those default paths unless I monkey patch. I was hoping
there would be another way which is why I opened the topic.
I am able to get it to work by doing the following:
Monkey Patching :: asset_tag_helper.rb
def javascript_path(source)
compute_public_path(source, 'themes', 'js')
end
def stylesheet_path(source)
compute_public_path(source, 'themes', 'css')
end
def image_path(source)
compute_public_path(source, 'themes')
end
...
And adding a helper: (this will of course change)
def current_theme_path(type)
path = @opt_default_theme + "/images/" if type == 'img'
path = @opt_default_theme + "/stylesheets/" if type == 'css'
path = @opt_default_theme + "/javascripts/" if type == 'js'
path = @opt_default_theme + "/swfs/" if type == 'swf'
return path
end
I don't understand why you can't use a stylesheet like:
application.css
that handles the general case or "default theme", as you refer to it, and then simply serve up a second stylesheet after that based on preference, as:
<%= stylesheet_link_tag :application %>
<%= stylesheet_link_tag @user_theme_stylesheet if @user_theme_stylesheet %>
You can then simply implement a before filter in your controller that sets @user_theme_stylesheet based on user preference and relies on the CSS proximity rule disambiguation to decide what CSS rule to apply.
I don't understand why you can't use a stylesheet like:
application.css
that handles the general case or "default theme", as you refer to it,
and then simply serve up a second stylesheet after that based on
preference, as:
<%= stylesheet_link_tag :application %>
<%= stylesheet_link_tag @user_theme_stylesheet if @user_theme_stylesheet
%>
You can then simply implement a before filter in your controller that
sets @user_theme_stylesheet based on user preference and relies on the
CSS proximity rule disambiguation to decide what CSS rule to apply.
Have I misunderstood your problem?
Yes, it's not that simple. My problem isn't with CSS directly. My
problem lays simply in delivering up the paths to the css files, and the
js files, and the swf files, and the image files, and the layout files -
depending on what theme is set as the default theme for the site.
I no longer have these issues thanks to Fred.
I already have a layouts system implemented where based on any given
theme, a user can decide on exactly what layout to use for every single
page or grouped by controller type. It's very detailed but it works
great.
The only issues I had that were remaining were handling of images, css,
js, and swfs, relative to the path of the theme and still have the
ability for rails to manage these assets.
I've tested out the new code and it works great. The assets and
timestamps are working properly for root path and for the theme path.
+1 for LIQUID and/or Haml and Sass. Interestingly enough there are
some changes in the Sass 2.4 source code that might be exactly what
you're looking for:
So, here is the output code and what's displayed. As you can see, I
simplified the helper calls and am able to call multiple stylesheets and
javascripts and am able to feed image tags with options.