A Day in the Life

2008-06-12

#1 特定のアクションだけJS/CSS を読み込んで欲しい

とあるコントローラの、とあるアクションだけJS/CSS等を読み込んで欲しい。そんなときは ApplicationController に

def self.javascript_dependency(arg, options = {})
    dependency 'javascripts', arg,  options
  end
  def self.stylesheet_dependency(arg, options = {})
    dependency 'stylesheets', arg, options
  end
  def self.dependency(name, arg, options = {})
    before_filter Proc.new {
      a = read_inheritable_attribute(name) || []
      a.concat [arg].flatten
      write_inheritable_attribute(name, a)
    }, options
  end

を書くと、コントローラで

javascript_dependency ['ui.datepicker', 'ui.datepicker-ja', 'jquery.autocomplete'], :only => [:new, :edit]
  javascript_dependency 'foobar', :only => [:index]
  stylesheet_dependency ['ui.datepicker', 'jquery.autocomplete'], :only => [:new, :edit]

と DSL で書ける。んで layout の head に

<%= javascript_include_tag controller.class.read_inheritable_attribute('javascripts') || [] %>
 <%= stylesheet_link_tag controller.class.read_inheritable_attribute('stylesheets') || []  %>

書けば使える。また別に JS/CSS 以外にもいろいろ使える(なんに使うかは思いつかない…)。

これぐらいのコードの断片だとプラギンにするよりコピペで張った方が便利な気がする。

http://d.hatena.ne.jp/kusakari/20080613/1213336544 のやり方の方が格好いいし view で完全に分離できる

rails とクラス変数と production

production ではクラスの再ロードは基本されない。のでコントローラ等で内部DSL るため

@@class_var ||= []
@@class_var << obj

等の事をしてると、毎回呼び出されて増えていく。毎回コントローラ呼びだしでクラス変数初期化でもいいんだけど、rails 的には

read_inheritable_attribute name
write_inheritable_attribute name, val

を使う(ARのclass拡張)のがいいっぽいな。filter 周りでこいつつかってた。

記事の一覧 >