This extension is part of the Sinatra::Contrib project. Run gem install sinatra-contrib to have it available.
Sinatra::ContentFor is a set of helpers that allows you to
capture blocks inside views to be rendered later during the request. The
most common use is to populate different parts of your layout from your
The currently supported engines are: Erb, Erubi, Erubis, Haml and Slim.
content_for, generally from a view, to capture a
block of markup giving it an identifier:
# index.erb <% content_for :some_key do %> <chunk of="html">...</chunk> <% end %>
Then, you call
yield_content with that identifier, generally
from a layout, to render the captured block:
# layout.erb <%= yield_content :some_key %>
If you have provided
yield_content with a block and no content
for the specified key is found, it will render the results of the block
provided to yield_content.
# layout.erb <% yield_content :some_key_with_no_content do %> <chunk of="default html">...</chunk> <% end %>
To use the helpers in a classic application all you need to do is require them:
require "sinatra" require "sinatra/content_for" # Your classic application code goes here...
To use the helpers in a modular application you need to require them, and then, tell the application you will use them:
require "sinatra/base" require "sinatra/content_for" class MyApp < Sinatra::Base helpers Sinatra::ContentFor # The rest of your modular application code goes here... end
And How Is This Useful?
stylesheets, but you don't want to force this files in all your pages.
Then you can put
<%= yield_content :scripts_and_styles
%> on your layout, inside the <head> tag, and each view can
content_for setting the appropriate set of tags that
should be added to the layout.
Due to the rendering process limitation using
%> from within nested templates do not work above the
<tt><%= yield %> statement. For more details github.com/sinatra/sinatra-contrib/issues/140#issuecomment-48831668
# app.rb get '/' do erb :body, :layout => :layout do erb :foobar end end # foobar.erb <% content_for :one do %> <script> alert('one'); </script> <% end %> <% content_for :two do %> <script> alert('two'); </script> <% end %>
<%= yield_content %> before
%> will cause only the second alert to display:
# body.erb # Display only second alert <%= yield_content :one %> <%= yield %> <%= yield_content :two %> # body.erb # Display both alerts <%= yield %> <%= yield_content :one %> <%= yield_content :two %>