Mounting a Cell to a Route with Cells 3.8.

Those of you “having asked for mountable cells”: will be happy with the recent “3.8.0 release”:! We entirely removed the ActionController dependency. That essentially means you can have cells outside of the standard Rails stack. Cool, heh?

h3. Cells 3.8.0 Released

Two little things in 3.8 changed. @Cell::Base@ and @Cell::Rails@ are now different classes with different semantics. Don’t panic – if you still derive your cells from @Cell::Rails@ and use the @#render_cell@ interface, only, nothing will change for you.

However, we had to tweak the API of some semi-public methods, here’s the new signatures.

Cell::Rails.create_cell_for(name, controller)
Cell::Rails.render_cell_for(name, state, controller, *args)

Well, nothing serious, it’s just the controller sliding to the end. If you use this anywhere, be sure to change it.

h3. What’s new?

What is new is that @Cell::Base@ is now decoupled from the ActionController. There simply is no AC-reference in @Base@ anymore. However, this reference is still managed in @Cell::Rails@ on purpose:

  • Calls to @#url_for@ and friends automatically query the parent controller for host and action name. This makes it easy to embedd cells into a controller view and still having correct links in the cell.
  • Having the AC reference, people can still use request, params and session – if they need it. We strongly discourage accessing HTTP properties from a view component, though.

Let’s see what the new decoupled @Base@ brings us.

h3. Cells on Routes.

Deriving your cell from @Base@ makes it _routeable_.

class PostsCell < Cell::Base
  def show
    @posts = Post.find(:all)

Routeable? Mountable? Well, let’s look at @config/routes.rb@ to understand this.

match "/posts" => proc { |env|
  content = 
    Cell::Base.render_cell_for(:posts, :show)
  [ 200, {}, [ content ]]

How cool is that? You can mount a cell to a route without the ActionController overhead and still use the rendering, the caching and testing you all love from Cells. And, hey, *it’s super super fast now.*

The lack of the AC dependency makes cells even more versatile.

h3. More on Routing

Since we got rid of the AC instance we have to take care of our URLs ourself. The cell still has access to all the URL helpers. Nevertheless, those helpers usually query the controller for host name portions, etc. That’s actually very simple with cells, too.

class PostsCell  ""}

Just override the @#default_url_options@ method as used from AC. This allows using the URL helpers as usual.
#=> ""

Let me know how these changes work for you! I’m eager to see new cases of applications in the next weeks.


8 thoughts on “Mounting a Cell to a Route with Cells 3.8.

  1. Hi,

    since I’m pretty new to cells and reading your rack example I was wondering if it would make sense to get a rack compatible object from cells directly.

    thus your example above could be something link:

    match “/posts” =>, :show)


  2. Sie regieren!!

    Thanks, Nick — I can see where this is heading with Apotomo.

    So if we wanted to create an app that used ONLY cells and no AC whatsoever, then we need a cell that creates the layout? Is that right? So instead of AC automatically choosing the layout template, we write a cell that creates the HTML header, body, etc and then plugs in the cells that render the specific body (or header/whatever) content?


  3. @bumi: Love the Cell::Rack idea!

    @Kevin: Yeah, you could either go and have two cells, or use the :layout option in render.

    @sasuke: For Apotomo, I need a couple of more hours to think about it, I will blog when it’s ready.


  4. Why not using the cell higher in the middleware? using it on routing is already after the whole rackstack is loaded (as I understand) so its not performant enough.


Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s