rango 0.1.1.1 → 0.1.1.2
Sign up to get free protection for your applications and to get access to all the features.
- data/README.textile +17 -0
- data/Rakefile +11 -1
- data/lib/rango.rb +0 -2
- data/lib/rango/controller.rb +22 -19
- data/lib/rango/gv.rb +0 -3
- data/lib/rango/gv/static.rb +3 -0
- data/lib/rango/mixins/message.rb +25 -6
- data/lib/rango/mixins/render.rb +6 -69
- data/lib/rango/mixins/rendering.rb +7 -2
- data/lib/rango/rack/request.rb +7 -5
- data/lib/rango/templates/exts/haml.rb +1 -1
- data/lib/rango/version.rb +7 -0
- data/spec/rango/mixins/message_spec.rb +85 -0
- data/spec/rango/mixins/render_spec.rb +49 -0
- data/spec/rango_spec.rb +0 -5
- data/spec/stubs/templates/context_id.html.haml +1 -0
- data/spec/stubs/templates/index.html.haml +1 -0
- metadata +5 -2
data/README.textile
CHANGED
@@ -11,6 +11,23 @@ h1. Installation via "Rip":http://hellorip.com
|
|
11
11
|
* Install edge version: @rip install git://github.com/botanicus/rango.git@
|
12
12
|
* Install tagged version: @rip install git://github.com/botanicus/rango.git 0.1@
|
13
13
|
|
14
|
+
h1. How to Contribute To Rango
|
15
|
+
|
16
|
+
Contributions to Rango is easy, you don't have to create a ticket or something, the only thing you really have to do is write good code. Before you send a pull request, please ensure that you:
|
17
|
+
* Wrote YARD documentation
|
18
|
+
* Wrote specs and run them under at least under Ruby 1.9.1, ideally under all the supported Ruby platforms:
|
19
|
+
|
20
|
+
<pre>
|
21
|
+
# run all the specs under Ruby 1.9.1 and Ruby 1.9.2
|
22
|
+
rvm specs 1.9.1,1.9.2
|
23
|
+
|
24
|
+
# run given spec under all installed Ruby implementations
|
25
|
+
rvm ruby ./script/spec spec/rango/mixins/message_spec.rb
|
26
|
+
|
27
|
+
# run given spec under Ruby 1.9.1
|
28
|
+
rvm 1.9.1 ruby ./script/spec spec/rango/mixins/message_spec.rb
|
29
|
+
</pre>
|
30
|
+
|
14
31
|
h1. Documentation
|
15
32
|
|
16
33
|
* "Wiki":http://wiki.github.com/botanicus/rango
|
data/Rakefile
CHANGED
@@ -1,5 +1,11 @@
|
|
1
1
|
# encoding: utf-8
|
2
2
|
|
3
|
+
require_relative "lib/rango/version"
|
4
|
+
|
5
|
+
# ENV setup for external commands
|
6
|
+
ENV["RUBYLIB"] = Dir["vendor/*/lib"].join(":")
|
7
|
+
$LOAD_PATH.clear.push(*Dir["vendor/*/lib"])
|
8
|
+
|
3
9
|
# http://support.runcoderun.com/faqs/builds/how-do-i-run-rake-with-trace-enabled
|
4
10
|
Rake.application.options.trace = true
|
5
11
|
|
@@ -8,5 +14,9 @@ task :default => ["submodules:init", :spec]
|
|
8
14
|
|
9
15
|
# load tasks
|
10
16
|
Dir["tasks/*.rake"].each do |taskfile|
|
11
|
-
|
17
|
+
begin
|
18
|
+
load File.join(Dir.pwd, taskfile)
|
19
|
+
rescue Exception => exception
|
20
|
+
puts exception
|
21
|
+
end
|
12
22
|
end
|
data/lib/rango.rb
CHANGED
data/lib/rango/controller.rb
CHANGED
@@ -8,33 +8,36 @@ require "rango/rack/request"
|
|
8
8
|
|
9
9
|
module Rango
|
10
10
|
class Controller
|
11
|
+
include Rango::UrlHelper
|
11
12
|
# [master] Change Merb::Controller to respond to #call and return a Rack Array. (wycats)http://rubyurl.com/BhoY
|
12
13
|
# @since 0.0.2
|
13
14
|
def self.call(env)
|
14
15
|
Rango::Router.set_rack_env(env)
|
15
16
|
request = Rango::Request.new(env)
|
16
17
|
options = env["rango.router.params"] || raise("rango.router.params property has to be setup at least to empty hash")
|
17
|
-
method = env["rango.controller.action"].to_sym
|
18
18
|
controller = self.new(env, options.merge(request.params))
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
controller.
|
34
|
-
|
35
|
-
|
36
|
-
controller.rescue_http_error(exception)
|
19
|
+
controller.to_response
|
20
|
+
end
|
21
|
+
|
22
|
+
def to_response
|
23
|
+
method = env["rango.controller.action"].to_sym
|
24
|
+
unless controller.respond_to?(method) # TODO: what about method_missing?
|
25
|
+
raise NotFound, "Controller #{self.name} doesn't have method #{method}"
|
26
|
+
end
|
27
|
+
controller.run_filters(:before, method.to_sym)
|
28
|
+
# If you don't care about arguments or if you prefer usage of params.
|
29
|
+
if controller.method(method).arity.eql?(0)
|
30
|
+
Rango.logger.debug("Calling method #{self.name}##{method} without arguments")
|
31
|
+
controller.response.body = controller.method(method).call
|
32
|
+
else
|
33
|
+
args = controller.params.values
|
34
|
+
Rango.logger.debug("Calling method #{self.name}##{method} with arguments #{args.inspect}")
|
35
|
+
controller.response.body = controller.method(method).call(*args)
|
37
36
|
end
|
37
|
+
controller.run_filters(:after, method)
|
38
|
+
return controller.response.finish
|
39
|
+
rescue HttpError => exception
|
40
|
+
controller.rescue_http_error(exception)
|
38
41
|
end
|
39
42
|
|
40
43
|
# for routers
|
data/lib/rango/gv.rb
CHANGED
@@ -4,12 +4,9 @@
|
|
4
4
|
# Use directly or include into a controller if you want to use filters or customize them
|
5
5
|
# http://wiki.github.com/botanicus/rango/generic-views
|
6
6
|
|
7
|
-
require "rango/mini"
|
8
7
|
require "rango/router"
|
9
|
-
require "rango/mixins/render"
|
10
8
|
|
11
9
|
module Rango
|
12
10
|
module GV
|
13
|
-
extend Rango::RenderMixin
|
14
11
|
end
|
15
12
|
end
|
data/lib/rango/gv/static.rb
CHANGED
data/lib/rango/mixins/message.rb
CHANGED
@@ -4,21 +4,40 @@ module Rango
|
|
4
4
|
module MessageMixin
|
5
5
|
# The rails-style flash messages
|
6
6
|
# @since 0.0.2
|
7
|
+
# NOTE: it's important to include this mixin after ImplicitRendering mixin
|
8
|
+
def self.included(controller)
|
9
|
+
# How to determine
|
10
|
+
# respond to not, it's a class
|
11
|
+
# if controller.instance_methods.include?(:locals)
|
12
|
+
controller.class_eval do
|
13
|
+
def locals
|
14
|
+
@locals ||= super.merge!(message: self.message)
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
7
19
|
def message
|
8
20
|
@message ||= (request.GET[:msg] || Hash.new)
|
9
21
|
end
|
10
|
-
|
22
|
+
|
11
23
|
# @since 0.0.2
|
12
24
|
def redirect(url, options = Hash.new)
|
13
|
-
self.
|
25
|
+
url = [self.request.base_url.chomp("/"), url].join("/").chomp("/") unless url.match(/^http/)
|
14
26
|
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
27
|
+
if options.respond_to?(:inject)
|
28
|
+
# redirect "/post", error: "Try again"
|
29
|
+
# ?msg[error]="Try again"
|
30
|
+
url = options.inject(url) do |url, pair|
|
31
|
+
type, message = pair
|
32
|
+
url + "?msg[#{type}]=#{message}"
|
19
33
|
end
|
34
|
+
else
|
35
|
+
# redirect "/post", "Try again"
|
36
|
+
# ?msg="Try again"
|
37
|
+
url.concat("?msg=#{options}")
|
20
38
|
end
|
21
39
|
|
40
|
+
self.status = 302
|
22
41
|
self.headers["Location"] = URI.escape(url)
|
23
42
|
return String.new
|
24
43
|
end
|
data/lib/rango/mixins/render.rb
CHANGED
@@ -1,81 +1,18 @@
|
|
1
1
|
# encoding: utf-8
|
2
2
|
|
3
|
-
require "rango
|
4
|
-
require "rango/router"
|
3
|
+
require "rango" # logger
|
5
4
|
require "rango/templates/template"
|
6
5
|
|
7
|
-
# This mixin should be included to the all objects which are supposed to return response for Rack, so not just ControllerStrategy, but also CallableStrategy
|
8
6
|
module Rango
|
9
7
|
module RenderMixin
|
10
|
-
include Rango::UrlHelper
|
11
8
|
extend self # so you can use Rango::RenderMixin.render
|
12
9
|
|
13
|
-
# class Posts < Rango::Controller
|
14
|
-
# def context
|
15
|
-
# Object.new
|
16
|
-
# end
|
17
|
-
#
|
18
|
-
# def show
|
19
|
-
# # you can't use @explicit
|
20
|
-
# post = Post.get(params[:id])
|
21
|
-
# render "post.html", post: post
|
22
|
-
# end
|
23
|
-
# end
|
24
|
-
#
|
25
|
-
# Context for rendering templates
|
26
|
-
# This context will be extended by same crucial methods from template mixin
|
27
|
-
# We are in context of current controller by default
|
28
|
-
def context
|
29
|
-
Object.new.extend(Rango::Helpers)
|
30
|
-
end
|
31
|
-
|
32
|
-
# def show
|
33
|
-
# locals[:post] = Post.get(params[:id])
|
34
|
-
# render "show.html", locals
|
35
|
-
# end
|
36
|
-
def locals
|
37
|
-
@locals ||= {message: self.message}
|
38
|
-
end
|
39
|
-
|
40
|
-
# TODO: extensions handling
|
41
10
|
# @since 0.0.2
|
42
|
-
def render(
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
end
|
48
|
-
template, locals = self.template_location, template if template.is_a?(Hash) && locals.empty?
|
49
|
-
template2 = Rango::Templates::Template.new(template, self.context)
|
50
|
-
if self.class.respond_to?(:after_render_filters)
|
51
|
-
run_filters2 self.class.after_render_filters, template2
|
52
|
-
end
|
53
|
-
return template2.render(locals)
|
54
|
-
end
|
55
|
-
|
56
|
-
# @since 0.0.2
|
57
|
-
def display(object, template, locals = Hash.new)
|
58
|
-
if self.class.respond_to?(:before_display_filters)
|
59
|
-
run_filters2 self.class.before_display_filters, object, template, locals
|
60
|
-
end
|
61
|
-
result = render(template)
|
62
|
-
if self.class.respond_to?(:after_display_filters)
|
63
|
-
run_filters2 self.class.after_display_filters, object, result
|
64
|
-
end
|
65
|
-
return result
|
66
|
-
rescue Error406
|
67
|
-
# TODO: provides API
|
68
|
-
format = Project.settings.mime_formats.find do |format|
|
69
|
-
object.respond_to?("to_#{format}")
|
70
|
-
end
|
71
|
-
format ? object.send("to_#{format}") : raise(Error406.new(self.params))
|
72
|
-
end
|
73
|
-
|
74
|
-
def run_filters2(array, *args)
|
75
|
-
array.each do |filter|
|
76
|
-
Rango.logger.debug("Calling filter #{filter.inspect}")
|
77
|
-
filter.call(*args)
|
78
|
-
end
|
11
|
+
def render(path, context = Object.new, locals = Hash.new)
|
12
|
+
context, locals = Object.new, context if locals.empty? && context.is_a?(Hash)
|
13
|
+
Rango.logger.inspect(locals: locals)
|
14
|
+
template = Rango::Templates::Template.new(path, context)
|
15
|
+
return template.render(locals)
|
79
16
|
end
|
80
17
|
end
|
81
18
|
end
|
@@ -5,7 +5,12 @@ module Rango
|
|
5
5
|
def render(template, locals = Hash.new)
|
6
6
|
super(template, self.locals.merge!(locals))
|
7
7
|
end
|
8
|
-
|
8
|
+
|
9
|
+
# class Posts < Rango::Controller
|
10
|
+
# def context
|
11
|
+
# Object.new
|
12
|
+
# end
|
13
|
+
#
|
9
14
|
# def show
|
10
15
|
# # you can't use @explicit
|
11
16
|
# post = Post.get(params[:id])
|
@@ -25,7 +30,7 @@ module Rango
|
|
25
30
|
# render "show.html", locals
|
26
31
|
# end
|
27
32
|
def locals
|
28
|
-
@locals ||= {
|
33
|
+
@locals ||= {request: self.request}
|
29
34
|
end
|
30
35
|
end
|
31
36
|
|
data/lib/rango/rack/request.rb
CHANGED
@@ -160,11 +160,13 @@ module Rango
|
|
160
160
|
end
|
161
161
|
|
162
162
|
def base_url
|
163
|
-
|
164
|
-
|
165
|
-
|
166
|
-
|
167
|
-
|
163
|
+
url = scheme + "://"
|
164
|
+
url << host
|
165
|
+
if scheme == "https" && port != 443 ||
|
166
|
+
scheme == "http" && port != 80
|
167
|
+
url << ":#{port}"
|
168
|
+
end
|
169
|
+
url
|
168
170
|
end
|
169
171
|
end
|
170
172
|
end
|
@@ -1,7 +1,7 @@
|
|
1
1
|
# encoding: utf-8
|
2
2
|
|
3
3
|
# Option default_attributes
|
4
|
-
#
|
4
|
+
#
|
5
5
|
# A hash of default attributes for tags (`{tag => {attribute => default_value}}`).
|
6
6
|
# Attributes of each tag will reverse merged with his default attributes, so you
|
7
7
|
# don't have to write over and over that script tag has attribute `type` with value
|
@@ -0,0 +1,85 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require_relative "../../spec_helper"
|
4
|
+
|
5
|
+
require "rack/mock"
|
6
|
+
require "rango/controller"
|
7
|
+
require "rango/mixins/message"
|
8
|
+
require "rango/mixins/rendering"
|
9
|
+
|
10
|
+
class TestController < Rango::Controller
|
11
|
+
include Rango::MessageMixin
|
12
|
+
end
|
13
|
+
|
14
|
+
describe Rango::MessageMixin do
|
15
|
+
before(:each) do
|
16
|
+
@env = Rack::MockRequest.env_for("/?msg")
|
17
|
+
@controller = TestController.new(@env)
|
18
|
+
end
|
19
|
+
|
20
|
+
describe ".included" do
|
21
|
+
it "should not do anything if method locals isn't defined" do
|
22
|
+
pending "How to implement it?"
|
23
|
+
@controller.should_not respond_to(:locals)
|
24
|
+
end
|
25
|
+
|
26
|
+
class ExplicitRenderingController < Rango::Controller
|
27
|
+
include Rango::ExplicitRendering
|
28
|
+
include Rango::MessageMixin
|
29
|
+
end
|
30
|
+
|
31
|
+
it "should add message to locals if method locals is defined" do
|
32
|
+
controller = ExplicitRenderingController.new(@env)
|
33
|
+
controller.locals.should have_key(:message)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
describe "#message" do
|
38
|
+
before(:each) do
|
39
|
+
@env = Rack::MockRequest.env_for("/")
|
40
|
+
end
|
41
|
+
|
42
|
+
it "should" do
|
43
|
+
@env["QUERY_STRING"] = "msg=Hello%20There%21"
|
44
|
+
controller = TestController.new(@env)
|
45
|
+
controller.message.should eql("Hello There!")
|
46
|
+
end
|
47
|
+
|
48
|
+
it "should" do
|
49
|
+
@env["QUERY_STRING"] = "msg%5Berror%5D%3DHello%20There%21"
|
50
|
+
controller = TestController.new(@env)
|
51
|
+
controller.message[:error].should eql("Hello There!")
|
52
|
+
end
|
53
|
+
|
54
|
+
it "should" do
|
55
|
+
@env["QUERY_STRING"] = "msg%5Berror%5D=Hello%20There%21&msg%5Bnotice%5D=Welcome%21"
|
56
|
+
controller = TestController.new(@env)
|
57
|
+
controller.message[:error].should eql("Hello There!")
|
58
|
+
controller.message[:notice].should eql("Welcome!")
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
describe "#redirect" do
|
63
|
+
before(:each) do
|
64
|
+
@env = Rack::MockRequest.env_for("/")
|
65
|
+
Posts = Class.new(Rango::Controller) { include Rango::MessageMixin }
|
66
|
+
@controller = Posts.new(@env)
|
67
|
+
end
|
68
|
+
|
69
|
+
it "should be satisfied just with url" do
|
70
|
+
@controller.redirect("/")
|
71
|
+
@controller.status.should eql(302)
|
72
|
+
@controller.headers["Location"].should eql("http://example.org/")
|
73
|
+
end
|
74
|
+
|
75
|
+
it "should be satisfied just with url" do
|
76
|
+
@controller.redirect("/", "Try again")
|
77
|
+
@controller.headers["Location"].should eql("http://example.org/?msg=Try%20again")
|
78
|
+
end
|
79
|
+
|
80
|
+
it "should be satisfied just with url" do
|
81
|
+
@controller.redirect("/", error: "Try again")
|
82
|
+
@controller.headers["Location"].should eql("http://example.org/?msg[error]=Try%20again")
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
@@ -0,0 +1,49 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
|
3
|
+
require_relative "../../spec_helper"
|
4
|
+
|
5
|
+
require "rango/project"
|
6
|
+
require "rango/mixins/render"
|
7
|
+
|
8
|
+
Project.settings.template_dirs = [File.join(STUBS_ROOT, "templates")]
|
9
|
+
|
10
|
+
describe Rango::RenderMixin do
|
11
|
+
it "should work standalone" do
|
12
|
+
Rango::RenderMixin.should respond_to(:render)
|
13
|
+
end
|
14
|
+
|
15
|
+
it "should work as a mixin" do
|
16
|
+
controller = Class.new { include Rango::RenderMixin }
|
17
|
+
controller.new.should respond_to(:render)
|
18
|
+
end
|
19
|
+
|
20
|
+
describe "#render" do
|
21
|
+
include Rango::RenderMixin
|
22
|
+
it "should take a path as the first argument" do
|
23
|
+
body = render "test.html"
|
24
|
+
body.should be_kind_of(String)
|
25
|
+
end
|
26
|
+
|
27
|
+
it "should take a context as the second argument" do
|
28
|
+
context = Object.new
|
29
|
+
body = render "context_id.html", context
|
30
|
+
context_id = body.chomp.to_i
|
31
|
+
context_id.should eql(context.object_id)
|
32
|
+
end
|
33
|
+
|
34
|
+
it "should take locals as the third argument" do
|
35
|
+
context = Object.new
|
36
|
+
body = render "index.html", context, title: "Hi!"
|
37
|
+
body.should match(/Hi\!/)
|
38
|
+
end
|
39
|
+
|
40
|
+
it "should take the second arguments as a locals if it's a hash and there is no third argument" do
|
41
|
+
body = render "index.html", title: "Hi!"
|
42
|
+
body.should match(/Hi\!/)
|
43
|
+
end
|
44
|
+
|
45
|
+
it "should raise TemplateNotFound if template wasn't found" do
|
46
|
+
-> { render "idonotexist.html" }.should raise_error(Rango::Errors::TemplateNotFound)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
data/spec/rango_spec.rb
CHANGED
@@ -4,11 +4,6 @@ require_relative "spec_helper"
|
|
4
4
|
require "rango"
|
5
5
|
|
6
6
|
describe Rango do
|
7
|
-
it "should have version" do
|
8
|
-
Rango::VERSION.should be_kind_of(String)
|
9
|
-
Rango::VERSION.should match(/^\d+\.\d+\.\d+$/)
|
10
|
-
end
|
11
|
-
|
12
7
|
it "should has logger" do
|
13
8
|
Rango.logger.should be_kind_of(RubyExts::Logger)
|
14
9
|
end
|
@@ -0,0 +1 @@
|
|
1
|
+
= self.object_id
|
@@ -0,0 +1 @@
|
|
1
|
+
= title
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rango
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.1.
|
4
|
+
version: 0.1.1.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- "Jakub \xC5\xA0\xC5\xA5astn\xC3\xBD aka Botanicus"
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain:
|
11
|
-
date: 2009-12-
|
11
|
+
date: 2009-12-07 00:00:00 +00:00
|
12
12
|
default_executable: rango
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
@@ -143,6 +143,7 @@ files:
|
|
143
143
|
- lib/rango/templates/helpers.rb
|
144
144
|
- lib/rango/templates/template.rb
|
145
145
|
- lib/rango/utils.rb
|
146
|
+
- lib/rango/version.rb
|
146
147
|
- lib/rango.rb
|
147
148
|
- spec/rango/contrib/pagination/adapters/datamapper_spec.rb
|
148
149
|
- spec/rango/contrib/pagination/helpers_spec.rb
|
@@ -211,8 +212,10 @@ files:
|
|
211
212
|
- spec/stubs/templates/basic.html.erb
|
212
213
|
- spec/stubs/templates/capture.html.erb
|
213
214
|
- spec/stubs/templates/context.html.erb
|
215
|
+
- spec/stubs/templates/context_id.html.haml
|
214
216
|
- spec/stubs/templates/erubis.html.erubis
|
215
217
|
- spec/stubs/templates/exception.html.erb
|
218
|
+
- spec/stubs/templates/index.html.haml
|
216
219
|
- spec/stubs/templates/inheritance/basic/base.html.haml
|
217
220
|
- spec/stubs/templates/inheritance/basic/index.html.haml
|
218
221
|
- spec/stubs/templates/inheritance/capture/erb/base.html.erb
|