2009-10-22 20:25:15 -04:00
|
|
|
# We're riding on Sinatra, so let's include it
|
|
|
|
require 'sinatra/base'
|
|
|
|
|
2009-11-16 14:32:55 -05:00
|
|
|
class Sinatra::Request
|
|
|
|
attr_accessor :layout
|
|
|
|
end
|
|
|
|
|
2009-10-22 20:25:15 -04:00
|
|
|
module Middleman
|
|
|
|
class Base < Sinatra::Base
|
|
|
|
set :app_file, __FILE__
|
|
|
|
set :root, Dir.pwd
|
|
|
|
set :reload, false
|
|
|
|
set :logging, false
|
|
|
|
set :environment, ENV['MM_ENV'] || :development
|
|
|
|
set :supported_formats, %w(erb)
|
|
|
|
set :index_file, "index.html"
|
|
|
|
set :js_dir, "javascripts"
|
|
|
|
set :css_dir, "stylesheets"
|
|
|
|
set :images_dir, "images"
|
|
|
|
set :build_dir, "build"
|
2009-11-06 19:23:33 -05:00
|
|
|
set :http_prefix, nil
|
2009-10-22 20:25:15 -04:00
|
|
|
|
|
|
|
use Rack::ConditionalGet if environment == :development
|
|
|
|
|
|
|
|
@@features = []
|
|
|
|
|
|
|
|
def self.enable(*opts)
|
|
|
|
@@features << opts
|
|
|
|
super
|
|
|
|
end
|
|
|
|
|
|
|
|
def self.disable(*opts)
|
|
|
|
@@features -= opts
|
|
|
|
super
|
|
|
|
end
|
|
|
|
|
2009-10-26 18:42:06 -04:00
|
|
|
@@afters = []
|
2009-10-29 12:43:08 -04:00
|
|
|
def self.after_feature_init(&block)
|
2009-10-26 18:42:06 -04:00
|
|
|
@@afters << block
|
|
|
|
end
|
|
|
|
|
2009-10-22 20:25:15 -04:00
|
|
|
# Rack helper for adding mime-types during local preview
|
|
|
|
def self.mime(ext, type)
|
|
|
|
ext = ".#{ext}" unless ext.to_s[0] == ?.
|
|
|
|
::Rack::Mime::MIME_TYPES[ext.to_s] = type
|
|
|
|
end
|
|
|
|
|
|
|
|
# Convenience function to discover if a tempalte exists for the requested renderer (haml, sass, etc)
|
|
|
|
def template_exists?(path, renderer=nil)
|
|
|
|
template_path = path.dup
|
|
|
|
template_path << ".#{renderer}" if renderer
|
|
|
|
File.exists? File.join(options.views, template_path)
|
|
|
|
end
|
|
|
|
|
|
|
|
# Base case renderer (do nothing), Should be over-ridden
|
|
|
|
module StaticRender
|
2009-11-16 14:32:55 -05:00
|
|
|
def render_path(path, layout)
|
2009-10-22 20:25:15 -04:00
|
|
|
if template_exists?(path, :erb)
|
2009-11-16 14:32:55 -05:00
|
|
|
erb(path.to_sym, :layout => layout)
|
2009-10-22 20:25:15 -04:00
|
|
|
else
|
|
|
|
false
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
include StaticRender
|
|
|
|
|
2009-11-16 14:32:55 -05:00
|
|
|
def process_request
|
2009-10-22 20:25:15 -04:00
|
|
|
# Normalize the path and add index if we're looking at a directory
|
|
|
|
path = request.path
|
|
|
|
path << options.index_file if path.match(%r{/$})
|
|
|
|
path.gsub!(%r{^/}, '')
|
|
|
|
|
2009-11-02 19:11:24 -05:00
|
|
|
# layout(:"layout.html") # Insert the .html into the layout name like the rest of the templates
|
|
|
|
|
2009-10-22 20:25:15 -04:00
|
|
|
# If the enabled renderers succeed, return the content, mime-type and an HTTP 200
|
2009-11-16 14:32:55 -05:00
|
|
|
if content = render_path(path, (request.layout || :layout))
|
2009-10-22 20:25:15 -04:00
|
|
|
content_type media_type(File.extname(path)), :charset => 'utf-8'
|
|
|
|
status 200
|
|
|
|
content
|
|
|
|
else
|
|
|
|
status 404
|
|
|
|
end
|
|
|
|
end
|
2009-11-16 14:32:55 -05:00
|
|
|
|
|
|
|
def self.page(url, options={}, &block)
|
|
|
|
get(url) do
|
|
|
|
request.layout = @@layout if (@@layout ||= nil)
|
|
|
|
request.layout = options[:layout] if options[:layout]
|
|
|
|
|
|
|
|
if block_given?
|
|
|
|
yield
|
|
|
|
else
|
|
|
|
process_request
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
def self.with_layout(layout, &block)
|
|
|
|
@@layout = layout
|
|
|
|
class_eval(&block)
|
|
|
|
ensure
|
|
|
|
@@layout = nil
|
|
|
|
end
|
|
|
|
|
|
|
|
# This will match all requests not overridden in the project's init.rb
|
|
|
|
not_found do
|
|
|
|
process_request
|
|
|
|
end
|
2009-10-22 20:25:15 -04:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
# Haml is required & includes helpers
|
|
|
|
require "middleman/haml"
|
|
|
|
require "middleman/sass"
|
2009-10-26 18:42:06 -04:00
|
|
|
require "sinatra/content_for"
|
|
|
|
require "middleman/helpers"
|
|
|
|
require "middleman/rack/static"
|
|
|
|
require "middleman/rack/sprockets"
|
2009-10-22 20:25:15 -04:00
|
|
|
|
|
|
|
class Middleman::Base
|
|
|
|
helpers Sinatra::ContentFor
|
|
|
|
helpers Middleman::Helpers
|
|
|
|
|
|
|
|
use Middleman::Rack::Static
|
|
|
|
use Middleman::Rack::Sprockets
|
|
|
|
|
|
|
|
# Features disabled by default
|
|
|
|
disable :slickmap
|
|
|
|
disable :cache_buster
|
|
|
|
disable :minify_css
|
|
|
|
disable :minify_javascript
|
|
|
|
disable :relative_assets
|
|
|
|
disable :maruku
|
|
|
|
disable :smush_pngs
|
2009-10-26 18:07:21 -04:00
|
|
|
disable :automatic_image_sizes
|
2009-11-16 14:32:55 -05:00
|
|
|
disable :relative_assets
|
|
|
|
disable :cache_buster
|
2009-10-22 20:25:15 -04:00
|
|
|
|
|
|
|
# Default build features
|
|
|
|
configure :build do
|
|
|
|
end
|
|
|
|
|
|
|
|
def self.new(*args, &bk)
|
|
|
|
# Check for and evaluate local configuration
|
|
|
|
local_config = File.join(self.root, "init.rb")
|
|
|
|
if File.exists? local_config
|
|
|
|
puts "== Reading: Local config" if logging?
|
|
|
|
class_eval File.read(local_config)
|
2009-10-27 21:13:19 -04:00
|
|
|
set :app_file, File.expand_path(local_config)
|
2009-10-22 20:25:15 -04:00
|
|
|
end
|
|
|
|
|
|
|
|
# loop over enabled feature
|
|
|
|
@@features.flatten.each do |feature_name|
|
|
|
|
next unless send(:"#{feature_name}?")
|
2009-10-27 21:13:19 -04:00
|
|
|
|
|
|
|
feature_path = "features/#{feature_name}"
|
|
|
|
if File.exists? File.join(File.dirname(__FILE__), "#{feature_path}.rb")
|
|
|
|
puts "== Enabling: #{feature_name.to_s.capitalize}" if logging?
|
|
|
|
require "middleman/#{feature_path}"
|
|
|
|
end
|
2009-10-22 20:25:15 -04:00
|
|
|
end
|
|
|
|
|
2009-10-26 18:42:06 -04:00
|
|
|
@@afters.each { |block| class_eval(&block) }
|
2009-10-22 20:25:15 -04:00
|
|
|
|
|
|
|
super
|
|
|
|
end
|
|
|
|
end
|