Middleman is a great tool for creating static websites. Recently I’ve been using it to redesign my own website and a scenario I encountered was wanting to pass variables between my layout and my template file. Specifically, I wanted to pass information local data (a yaml file) to my layout file. Here’s how I went about doing this:

# in your layout file (inside layout/ folder):
<% myvar = yield_content :myvar %>
 
# in your template file (e.g., mypage.html.erb):
<% content_for :myvar, data.somefile %>
 
# this examples assumes there's a somefile.yml in your data/ folder:
name: hello world
tag: the quick brown jumps over the lazy dog

After this setup, you’d expect to be able to call <%= myvar['name'] %> in your layout file and be able to access what’s in your local data file. However, it won’t work (when I did this, it just print out the name of the key, which in this case meant it print out ‘name’ and not ‘hello world’).

The reason ended up being that myvar is actually not an instance of Hash, it’s actually an instance of ActiveSupport::SafeBuffer. To convert it into a hash, you need to call something like this:

# in your layout file (inside layout/ folder):
&lt;% myvar = yield_content :myvar %&gt;
&lt;% myvar = eval(myvar.to_str) %&gt;

Calling to_str converts the SafeBuffer to a string and calling eval converts the string to a Hash. Now you can call myvar['name'] and it will work as expected!

To make things easier, you could also make this a helper function inside config.rb:

# in config.rb:
helpers do
  def hashify(safebuffer)
    eval(safebuffer.to_str)
  end
end
 
# in your layout file:
&lt;% myvar = hashify yield_content :myvar %&gt;
# this should print out 'hello world'
&lt;%= myvar['name'] %&gt;

This article has 1 comments

  1. David Reply

    This is exactly what I’ve been looking for, but in my testing it doesn’t seem to work. I’m getting a

    no implicit conversion of nil into String

    error. Any thoughts?

Leave a Comment

Your email address will not be published. Required fields are marked *