yell0wgh0st
yell0wgh0st

Reputation: 33

How to get Liquid template partials (includes) working with Sinatra?

I am new to ruby and I am trying to get template partials working in my Sinatra + Liquid project.

I have several template partials in my /includes directory.

How can I get all of these templates working as liquid partials so I can use them with liquid include tag?

What I actually have done:

# Sinatra First App
require 'sinatra'
require 'sinatra/config_file'
require 'liquid'

config_file 'config.yml'

# WebRick
set :run, true
set :server, %w[webrick]

# App Paths
set :root, File.dirname(__FILE__)
set :views, File.dirname(__FILE__) + '/views'
set :controlers, File.dirname(__FILE__) + '/controlers'
set :public_folder, Proc.new { File.join(root, "static") }

# Includes Folder
includes = File.dirname(__FILE__) + '/includes'

get '/' do
    Liquid::Template.file_system = Liquid::LocalFileSystem.new(includes)
    Liquid::Template.parse(includes).render
    liquid :index, :locals => { :title => "My Sinatra App"}
end

get '/test' do
    "This is the test page."
end

But I am still getting: Liquid error: Illegal template name ''.

Here is my index template:

<html>
    {% include 'header' %}
    <body>
        <h1>{{ title }}</h1>

        {{content}}
    </body>
</html>

and here is the header part template:

<head>
    <title>{{ title }}</title>
</head>

How can I fix it? Thanks for every response.

Upvotes: 3

Views: 3067

Answers (1)

ian
ian

Reputation: 12251

Of the get '/' route, it seems to me that the first line should be in a configuration block, and the second line shouldn't be needed at all as Tilt/Sinatra should take care of calling render, e.g.

configure do
  set :views, File.join(File.dirname(__FILE__),'/includes')
  # or just put these in the views dir
end

get '/' do
  liquid :index, :locals => { :title => "My Sinatra App"}
end

or, if you want a views directory with sub-directories for partials/includes etc, something like "./views/includes", you could pass the view folder as an option, e.g.

get '/' do
  liquid :index, :locals => { :title => "My Sinatra App"}, :views => File.join(File.dirname(__FILE__),'views/includes') 
end

or you could try Sinatra Partial (I'm the maintainer).


Since the above didn't work (see comments), I looked at the Sinatra tests for Liquid and played around with the OP's code. I found that the following worked for me:

# ./app.rb
# Sinatra First App
require 'sinatra'
require 'sinatra/config_file'
require 'liquid'

config_file 'config.yml'

configure do
  # WebRick
  set :run, true
  set :server, %w[webrick]

  # App Paths
  set :root, File.dirname(__FILE__)
  set :views, File.dirname(__FILE__) + '/views'
  set :controlers, File.dirname(__FILE__) + '/controlers'
  set :public_folder, Proc.new { File.join(root, "static") }
  Liquid::Template.file_system = Liquid::LocalFileSystem.new(File.join(File.dirname(__FILE__),'views/includes'))
end


get '/' do
  liquid :index, :locals => { :title => "My Sinatra App" }
end

get '/test' do
  "This is the test page."
end


#./Gemfile
source "https://rubygems.org"

gem "sinatra"
gem "liquid"
gem "sinatra-contrib"


#./views/includes/_header.liquid
<head>
    <title>{{ title }}</title>
</head>


#./views/index.liquid
<h1>{{ title }}</h1>

{{content}}


#./views/layout.liquid
<html>
    {% include "header" %}
    <body>
      {{ yield }}
    </body>
</html>

Upvotes: 2

Related Questions