Rails: Separating Asset Folders by Module

Posted by acts_as_flinn Tue, 24 Apr 2007 23:37:00 GMT

Like a lot of people writing apps with a public frontend and a private admin section I like to separate public and private controllers. This makes it easy to do a number of things, like authentication and keeping code clean. In order to do this, you can use or generate modules like so:

$ ./script/generate scaffold admin::frobnicator

This will generate (among other things)

  • app/controllers/admin/frobnicators_controller.rb
  • app/views/admin/frobnicators/

It becomes a pain when your frontend images and admin images start to intermingle. One approach for example is to put assets into their own subfolders like so

  • public/images/admin
  • public/javascripts/admin
  • public/stylesheets/admin

This works to keep your asset folders from looking like a clusterfuck getting to mixed up.

The Problem

The problem really comes when you start mucking around in views. You’ve now got to prefix every resource like so:

stylesheet_link_tag(‘admin/frobnicators’)
image_tag(‘admin/frobnicators.png’)

Then do this in your stylesheets like so:

  background: url(/images/admin/frobnicators-background.png);

Ok, so here’s it’s not so bad, do this with a half a dozen controllers and the views (and every link_to) and stylesheets that come along and it starts to become a pain in the ass to prefix everything with admin.

Solution

Fortunately there is a simple solution, overflow compute_public_path. By overflowing compute_pubic_path you can create folders for modules, then reference them as usual.

In my module controllers, I will usually extend them like so:

class Admin::FrobnicatorsController < AdminController

This allows me to do fun stuff like specify an admin layout for all the admin controllers

class AdminController < ApplicationController
  layout ‘admin’
...

This has the nice side effect of looking for the admin helper ( helpers/admin_helper.rb ) with all of the module controllers. You can now overflow compute_public_path to your hearts content.

module AdminHelper
  def compute_public_path(source, dir, ext)
    dir = "admin/#{dir}"
    super
  end
...

Results

Use a subfolder for your module and keep it clean.

  • public/admin/images
  • public/admin/javascripts
  • public/admin/stylesheets

Your stylesheets get a little cleaner and…

  background: url(../images/frobnicators-background.png);

And so do your views…

image_tag(‘frobnicators.png’)

You can almost go on thinking the module is a separate app. No more intermingled assets.


ss_blog_claim=746d258dc975cb7923cc57154dbf1d71