diff --git a/lib/cell.rb b/lib/cell.rb index 65e1bb02..d01ca341 100644 --- a/lib/cell.rb +++ b/lib/cell.rb @@ -1,6 +1,6 @@ module Cell autoload :Caching, 'cell/caching' - + extend ActiveSupport::Concern DEFAULT_VIEW_PATHS = [File.join('app', 'cells')] @@ -18,63 +18,5 @@ def render_cell_for(controller, name, state, *args) cell.render_state(state, *args) end - - # Creates a cell instance. Note that this method calls builders which were attached to the - # class with Cell::Base.build - this might lead to a different cell being returned. - def create_cell_for(controller, name, *args) - class_from_cell_name(name).build_for(controller, *args) - end - - def build_for(controller, *args) - build_class_for(controller, *args). - new(controller) - end - - # Adds a builder to the cell class. Builders are used in #render_cell to find out the concrete - # class for rendering. This is helpful if you frequently want to render subclasses according - # to different circumstances (e.g. login situations) and you don't want to place these deciders in - # your view code. - # - # Passes the opts hash from #render_cell into the block. The block is executed in controller context. - # Multiple build blocks are ORed, if no builder matches the building cell is used. - # - # Example: - # - # Consider two different user box cells in your app. - # - # class AuthorizedUserBox < UserInfoBox - # end - # - # class AdminUserBox < UserInfoBox - # end - # - # Now you don't want to have deciders all over your views - use a declarative builder. - # - # UserInfoBox.build do |opts| - # AuthorizedUserBox if user_signed_in? - # AdminUserBox if admin_signed_in? - # end - # - # In your view #render_cell will instantiate the right cell for you now. - def build(&block) - builders << block - end - - # The cell class constant for +cell_name+. - def class_from_cell_name(cell_name) - "#{cell_name}_cell".classify.constantize - end - - protected - def build_class_for(controller, *args) - builders.each do |blk| - klass = controller.instance_exec(*args, &blk) and return klass - end - self - end - - def builders - @builders ||= [] - end end end diff --git a/lib/cell/base.rb b/lib/cell/base.rb index ca0ebb92..ca14e17c 100644 --- a/lib/cell/base.rb +++ b/lib/cell/base.rb @@ -1,9 +1,11 @@ require 'abstract_controller' require 'cell' +require 'cell/builder' module Cell class Base < AbstractController::Base include Cell + extend Builder include AbstractController include Rendering, Layouts, Helpers, Callbacks, Translation, Logger diff --git a/lib/cell/builder.rb b/lib/cell/builder.rb new file mode 100644 index 00000000..552e1359 --- /dev/null +++ b/lib/cell/builder.rb @@ -0,0 +1,65 @@ +module Cell + module Builder + # Creates a cell instance. Note that this method calls builders which were attached to the + # class with Cell::Base.build - this might lead to a different cell being returned. + def create_cell_for(controller, name, *args) + class_from_cell_name(name).build_for(controller, *args) + end + + def build_for(controller, *args) + build_class_for(controller, *args). + new(controller) + end + + # Adds a builder to the cell class. Builders are used in #render_cell to find out the concrete + # class for rendering. This is helpful if you frequently want to render subclasses according + # to different circumstances (e.g. login situations) and you don't want to place these deciders in + # your view code. + # + # Passes the opts hash from #render_cell into the block. The block is executed in controller context. + # Multiple build blocks are ORed, if no builder matches the building cell is used. + # + # Example: + # + # Consider two different user box cells in your app. + # + # class AuthorizedUserBox < UserInfoBox + # end + # + # class AdminUserBox < UserInfoBox + # end + # + # Now you don't want to have deciders all over your views - use a declarative builder. + # + # UserInfoBox.build do |opts| + # AuthorizedUserBox if user_signed_in? + # AdminUserBox if admin_signed_in? + # end + # + # In your view #render_cell will instantiate the right cell for you now. + def build(&block) + builders << block + end + + # The cell class constant for +cell_name+. + def class_from_cell_name(cell_name) + "#{cell_name}_cell".classify.constantize + end + + protected + def build_class_for(controller, *args) + builders.each do |blk| + klass = run_builder_block(blk, controller, *args) and return klass + end + self + end + + def run_builder_block(blk, controller, *args) + controller.instance_exec(*args, &blk) + end + + def builders + @builders ||= [] + end + end +end