lib/hyperloop/application.rb in hyperloop-0.0.2 vs lib/hyperloop/application.rb in hyperloop-0.0.3
- old
+ new
@@ -1,45 +1,85 @@
-require 'rack'
+require "rack"
+require "sprockets"
+require "yui/compressor"
module Hyperloop
class Application
include Rack::Utils
def initialize(root=nil)
- @root = root
- @views_path = File.join([@root, 'app/views'].compact)
+ @root = root
+ @view_registry = View::Registry.new(@root)
end
# Rack call interface.
def call(env)
request = Rack::Request.new(env)
response = Response.new
- path = view_path(request)
- if File.exist?(path)
- # If there's a file at the view path, use its data as the response body.
- data = File.read(path)
+ if self.class.asset_path?(request.path) && asset = assets[normalized_asset_path(request.path)]
+ # If the path is for an asset, find the specified asset and use its data
+ # as the response body.
+ response["Content-Type"] = asset.content_type
+ response.write(asset.source)
+ elsif view = @view_registry.find_template_view(normalized_request_path(request.path))
+ # If there's a view at the path, use its data as the response body.
+ data = view.render(request)
response.write(data)
else
- # If there's no file at the view path, 404.
+ # If there's no view at the path, 404.
response.status = 404
end
response.finish
end
private
- # Internal: Get the view path for the specified request.
+ # Internal: Is the specified path for assets?
#
- # request - Rack::Request to get the view path for.
+ # path - Path to check.
#
- # Returns a String.
- def view_path(request)
- path = File.join(@views_path, request.path).chomp('/')
+ # Returns a boolean.
+ def self.asset_path?(path)
+ path =~ /^\/assets\/(images|javascripts|stylesheets)\//
+ end
- # If we're currently pointing to a directory, get index in it.
- path = File.join(path, 'index') if Dir.exist?(path)
- path + '.html'
+ # Internal: The sprockets environment for the app.
+ #
+ # Returns a Sprockets::Environment.
+ def assets
+ @assets ||= Sprockets::Environment.new do |env|
+ env.append_path(File.join(@root, "app", "assets"))
+ env.append_path(File.join(@root, "vendor", "assets"))
+
+ # compress everything in production
+ if ENV["RACK_ENV"] == "production"
+ env.js_compressor = YUI::JavaScriptCompressor.new(:munge => true)
+ env.css_compressor = YUI::CssCompressor.new
+ end
+ end
+ end
+
+ # Internal: Get a normalized version of the specified asset path.
+ #
+ # path - Asset path to normalize
+ #
+ # Returns a string.
+ def normalized_asset_path(path)
+ path.sub(/^\/assets\//, "")
+ end
+
+ # Internal: Get a normalized version of the specified request path.
+ #
+ # path - Request path to normalize
+ #
+ # Returns a string.
+ def normalized_request_path(path)
+ if path == "/"
+ path
+ else
+ path.chomp("/")
+ end
end
end
end