rjspotter-innate 2009.06.29
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/AUTHORS +10 -0
- data/CHANGELOG +3261 -0
- data/COPYING +18 -0
- data/MANIFEST +127 -0
- data/README.md +563 -0
- data/Rakefile +39 -0
- data/example/app/retro_games.rb +60 -0
- data/example/app/todo/layout/default.xhtml +11 -0
- data/example/app/todo/spec/todo.rb +63 -0
- data/example/app/todo/start.rb +51 -0
- data/example/app/todo/view/index.xhtml +39 -0
- data/example/app/whywiki_erb/layout/wiki.html.erb +15 -0
- data/example/app/whywiki_erb/spec/wiki.rb +19 -0
- data/example/app/whywiki_erb/start.rb +42 -0
- data/example/app/whywiki_erb/view/edit.erb +6 -0
- data/example/app/whywiki_erb/view/index.erb +12 -0
- data/example/custom_middleware.rb +35 -0
- data/example/hello.rb +11 -0
- data/example/howto_spec.rb +35 -0
- data/example/link.rb +27 -0
- data/example/provides.rb +31 -0
- data/example/session.rb +38 -0
- data/innate.gemspec +41 -0
- data/lib/innate.rb +269 -0
- data/lib/innate/action.rb +137 -0
- data/lib/innate/adapter.rb +76 -0
- data/lib/innate/cache.rb +134 -0
- data/lib/innate/cache/api.rb +128 -0
- data/lib/innate/cache/drb.rb +58 -0
- data/lib/innate/cache/file_based.rb +44 -0
- data/lib/innate/cache/marshal.rb +20 -0
- data/lib/innate/cache/memory.rb +21 -0
- data/lib/innate/cache/yaml.rb +20 -0
- data/lib/innate/current.rb +35 -0
- data/lib/innate/dynamap.rb +96 -0
- data/lib/innate/helper.rb +185 -0
- data/lib/innate/helper/aspect.rb +124 -0
- data/lib/innate/helper/cgi.rb +54 -0
- data/lib/innate/helper/flash.rb +36 -0
- data/lib/innate/helper/link.rb +94 -0
- data/lib/innate/helper/redirect.rb +85 -0
- data/lib/innate/helper/render.rb +152 -0
- data/lib/innate/helper/send_file.rb +26 -0
- data/lib/innate/log.rb +20 -0
- data/lib/innate/log/color_formatter.rb +49 -0
- data/lib/innate/log/hub.rb +77 -0
- data/lib/innate/middleware_compiler.rb +65 -0
- data/lib/innate/mock.rb +49 -0
- data/lib/innate/node.rb +1029 -0
- data/lib/innate/options.rb +37 -0
- data/lib/innate/options/dsl.rb +205 -0
- data/lib/innate/options/stub.rb +7 -0
- data/lib/innate/request.rb +141 -0
- data/lib/innate/response.rb +24 -0
- data/lib/innate/route.rb +114 -0
- data/lib/innate/session.rb +133 -0
- data/lib/innate/session/flash.rb +94 -0
- data/lib/innate/spec.rb +1 -0
- data/lib/innate/spec/bacon.rb +28 -0
- data/lib/innate/state.rb +26 -0
- data/lib/innate/state/accessor.rb +130 -0
- data/lib/innate/traited.rb +90 -0
- data/lib/innate/trinity.rb +18 -0
- data/lib/innate/version.rb +3 -0
- data/lib/innate/view.rb +97 -0
- data/lib/innate/view/erb.rb +14 -0
- data/lib/innate/view/etanni.rb +33 -0
- data/lib/innate/view/none.rb +9 -0
- data/spec/example/app/retro_games.rb +30 -0
- data/spec/example/hello.rb +13 -0
- data/spec/example/link.rb +25 -0
- data/spec/example/provides.rb +16 -0
- data/spec/example/session.rb +22 -0
- data/spec/helper.rb +10 -0
- data/spec/innate/action/layout.rb +121 -0
- data/spec/innate/action/layout/file_layout.xhtml +1 -0
- data/spec/innate/cache/common.rb +47 -0
- data/spec/innate/cache/marshal.rb +5 -0
- data/spec/innate/cache/memory.rb +5 -0
- data/spec/innate/cache/yaml.rb +5 -0
- data/spec/innate/dynamap.rb +22 -0
- data/spec/innate/helper.rb +86 -0
- data/spec/innate/helper/aspect.rb +75 -0
- data/spec/innate/helper/cgi.rb +37 -0
- data/spec/innate/helper/flash.rb +115 -0
- data/spec/innate/helper/link.rb +139 -0
- data/spec/innate/helper/redirect.rb +171 -0
- data/spec/innate/helper/render.rb +165 -0
- data/spec/innate/helper/send_file.rb +21 -0
- data/spec/innate/helper/view/aspect_hello.xhtml +1 -0
- data/spec/innate/helper/view/locals.xhtml +1 -0
- data/spec/innate/helper/view/loop.xhtml +4 -0
- data/spec/innate/helper/view/num.xhtml +1 -0
- data/spec/innate/helper/view/partial.xhtml +1 -0
- data/spec/innate/helper/view/recursive.xhtml +7 -0
- data/spec/innate/mock.rb +84 -0
- data/spec/innate/modes.rb +61 -0
- data/spec/innate/node/mapping.rb +37 -0
- data/spec/innate/node/node.rb +135 -0
- data/spec/innate/node/resolve.rb +82 -0
- data/spec/innate/node/view/another_layout/another_layout.xhtml +3 -0
- data/spec/innate/node/view/bar.xhtml +1 -0
- data/spec/innate/node/view/foo.html.xhtml +1 -0
- data/spec/innate/node/view/only_view.xhtml +1 -0
- data/spec/innate/node/view/with_layout.xhtml +1 -0
- data/spec/innate/node/wrap_action_call.rb +83 -0
- data/spec/innate/options.rb +123 -0
- data/spec/innate/parameter.rb +154 -0
- data/spec/innate/provides.rb +99 -0
- data/spec/innate/provides/list.html.xhtml +1 -0
- data/spec/innate/provides/list.txt.xhtml +1 -0
- data/spec/innate/request.rb +79 -0
- data/spec/innate/route.rb +135 -0
- data/spec/innate/session.rb +58 -0
- data/spec/innate/traited.rb +55 -0
- data/tasks/authors.rake +30 -0
- data/tasks/bacon.rake +66 -0
- data/tasks/changelog.rake +18 -0
- data/tasks/gem.rake +22 -0
- data/tasks/gem_setup.rake +99 -0
- data/tasks/grancher.rake +12 -0
- data/tasks/manifest.rake +4 -0
- data/tasks/rcov.rake +19 -0
- data/tasks/release.rake +53 -0
- data/tasks/reversion.rake +8 -0
- data/tasks/setup.rake +6 -0
- data/tasks/ycov.rake +84 -0
- metadata +218 -0
@@ -0,0 +1,54 @@
|
|
1
|
+
autoload(:CGI, 'cgi') # in case you want to use html_unescape
|
2
|
+
|
3
|
+
module Innate
|
4
|
+
|
5
|
+
# Shortcuts to some CGI methods
|
6
|
+
|
7
|
+
module Helper
|
8
|
+
module CGI
|
9
|
+
module_function
|
10
|
+
|
11
|
+
# Shortcut for Rack::Utils.escape
|
12
|
+
#
|
13
|
+
# @param [#to_s] input
|
14
|
+
# @return [String] URI-encoded representation of +input+
|
15
|
+
def url_encode(input)
|
16
|
+
Rack::Utils.escape(input.to_s)
|
17
|
+
end
|
18
|
+
alias u url_encode
|
19
|
+
|
20
|
+
# Shortcut for Rack::Utils.unescape
|
21
|
+
#
|
22
|
+
# @param [#to_s] input
|
23
|
+
# @return [String] URI-decoded representation of +input+
|
24
|
+
def url_decode(input)
|
25
|
+
Rack::Utils.unescape(input.to_s)
|
26
|
+
end
|
27
|
+
|
28
|
+
# Shortcut for Rack::Utils.escape_html
|
29
|
+
#
|
30
|
+
# @param [#to_s] input
|
31
|
+
# @return [String]
|
32
|
+
def html_escape(input)
|
33
|
+
Rack::Utils.escape_html(input.to_s)
|
34
|
+
end
|
35
|
+
|
36
|
+
# Shortcut for CGI.unescapeHTML
|
37
|
+
#
|
38
|
+
# @param [#to_s] input
|
39
|
+
# @return [String]
|
40
|
+
def html_unescape(input)
|
41
|
+
::CGI.unescapeHTML(input.to_s)
|
42
|
+
end
|
43
|
+
|
44
|
+
# safely escape all HTML and code
|
45
|
+
def html_and_code_escape(input)
|
46
|
+
Rack::Utils.escape_html(input.to_s).gsub(/#([{@$]@?)/, '#\1')
|
47
|
+
end
|
48
|
+
alias h html_and_code_escape
|
49
|
+
|
50
|
+
# aliases are ignored by module_function...
|
51
|
+
module_function :u, :h
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
module Innate
|
2
|
+
module Helper
|
3
|
+
# Simple access to session.flash.
|
4
|
+
#
|
5
|
+
# Flash is a mechanism using sessions to provide a rotating holder of
|
6
|
+
# key/value pairs.
|
7
|
+
#
|
8
|
+
# Every request that is made will rotate one step, dropping contents stored
|
9
|
+
# two requests ago.
|
10
|
+
#
|
11
|
+
# The purpose of this class is to provide an easy way of setting/retrieving
|
12
|
+
# from the current flash.
|
13
|
+
#
|
14
|
+
# Flash is a way to keep a temporary pairs of keys and values for the duration
|
15
|
+
# of two requests, the current and following.
|
16
|
+
#
|
17
|
+
# Very vague Example:
|
18
|
+
#
|
19
|
+
# On the first request, for example on registering:
|
20
|
+
#
|
21
|
+
# flash[:error] = "You should reconsider your username, it's taken already"
|
22
|
+
# redirect R(self, :register)
|
23
|
+
#
|
24
|
+
# This is the request from the redirect:
|
25
|
+
#
|
26
|
+
# do_stuff if flash[:error]
|
27
|
+
#
|
28
|
+
# On the request after this, flash[:error] is gone.
|
29
|
+
module Flash
|
30
|
+
# Just for convenience
|
31
|
+
def flash
|
32
|
+
session.flash
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,94 @@
|
|
1
|
+
module Innate
|
2
|
+
module Helper
|
3
|
+
module Link
|
4
|
+
def self.included(into)
|
5
|
+
into.extend(self)
|
6
|
+
end
|
7
|
+
|
8
|
+
# Provide the path to given Node and actions.
|
9
|
+
# Escapes GET parameters.
|
10
|
+
#
|
11
|
+
# Usage, mapping is Pages => '/', Users => '/users':
|
12
|
+
#
|
13
|
+
# Pages.r # => URI('/')
|
14
|
+
# Pages.r(:foo) # => URI('/foo')
|
15
|
+
# Pages.r(:foo, :bar) # => URI('/foo/bar')
|
16
|
+
# Pages.r(:foo, :a => :b) # => URI('/foo?a=b')
|
17
|
+
# Pages.r(:foo, :bar, :a => :b) # => URI('/foo/bar?a=b')
|
18
|
+
#
|
19
|
+
# Users.r # => URI('/users/')
|
20
|
+
# Users.r(:foo) # => URI('/users/foo')
|
21
|
+
# Users.r(:foo, :bar) # => URI('/users/foo/bar')
|
22
|
+
# Users.r(:foo, :a => :b) # => URI('/users/foo?a=b')
|
23
|
+
# Users.r(:foo, :bar, :a => :b) # => URI('/users/foo/bar?a=b')
|
24
|
+
#
|
25
|
+
# @return [URI] to the location
|
26
|
+
def route(name = '/', *args)
|
27
|
+
hash = {}
|
28
|
+
hashes, names = args.partition{|arg| arg.respond_to?(:merge!) }
|
29
|
+
hashes.each{|to_merge| hash.merge!(to_merge) }
|
30
|
+
|
31
|
+
escape = Rack::Utils.method(:escape)
|
32
|
+
location = route_location(self)
|
33
|
+
front = Array[location, name, *names.map{|n| escape[n]}].join('/').squeeze('/')
|
34
|
+
|
35
|
+
return URI(front) if hash.empty?
|
36
|
+
|
37
|
+
query = hash.map{|k, v| "#{escape[k]}=#{escape[v]}" }.join(';')
|
38
|
+
URI("#{front}?#{query}")
|
39
|
+
end
|
40
|
+
alias r route
|
41
|
+
|
42
|
+
def route_location(klass)
|
43
|
+
prefix = Innate.options.prefix
|
44
|
+
location = Innate.to(klass) || Innate.to(klass.class)
|
45
|
+
[prefix, location].join('/')
|
46
|
+
end
|
47
|
+
|
48
|
+
# Create a route to the currently active Node.
|
49
|
+
#
|
50
|
+
# This method is mostly here in case you include this helper elsewhere
|
51
|
+
# and don't want (or can't) type SomeNode.r all the time.
|
52
|
+
#
|
53
|
+
# The usage is identical with {route}.
|
54
|
+
#
|
55
|
+
# @param [#to_s] name
|
56
|
+
# @return [URI] to the location
|
57
|
+
# @see Ramaze::Helper::Link#route
|
58
|
+
# @author manveru
|
59
|
+
def route_self(name = '/', *args)
|
60
|
+
Current.action.node.route(name, *args)
|
61
|
+
end
|
62
|
+
alias rs route_self
|
63
|
+
|
64
|
+
# Create a link tag
|
65
|
+
#
|
66
|
+
# Usage, given Wiki is mapped to `/wiki`:
|
67
|
+
#
|
68
|
+
# Wiki.a(:home) # => '<a href="/wiki/home">home</a>'
|
69
|
+
# Wiki.a('home', :home) # => '<a href="/wiki/home">home</a>'
|
70
|
+
# Wiki.a('home', :/) # => '<a href="/wiki/">home</a>'
|
71
|
+
# Wiki.a('foo', :/, :foo => :bar) # => '<a href="/wiki/?foo=bar">foo</a>'
|
72
|
+
# Wiki.a('example', 'http://example.com')
|
73
|
+
# # => '<a href="http://example.com">example</a>'
|
74
|
+
#
|
75
|
+
# @return [String]
|
76
|
+
def anchor(text, *args)
|
77
|
+
case first = (args.first || text)
|
78
|
+
when URI
|
79
|
+
href = first.to_s
|
80
|
+
when /^\w+:\/\//
|
81
|
+
uri = URI(first)
|
82
|
+
uri.query = Rack::Utils.escape_html(uri.query)
|
83
|
+
href = uri.to_s
|
84
|
+
else
|
85
|
+
href = args.empty? ? r(text) : r(*args)
|
86
|
+
end
|
87
|
+
|
88
|
+
text = Rack::Utils.escape_html(text)
|
89
|
+
%(<a href="#{href}">#{text}</a>)
|
90
|
+
end
|
91
|
+
alias a anchor
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
@@ -0,0 +1,85 @@
|
|
1
|
+
module Innate
|
2
|
+
module Helper
|
3
|
+
module Redirect
|
4
|
+
def respond(body, status = 200, header = {})
|
5
|
+
response.write body
|
6
|
+
response.status = status
|
7
|
+
header['Content-Type'] ||= 'text/html'
|
8
|
+
header.each{|k,v| response[k] = v }
|
9
|
+
|
10
|
+
throw(:respond, response)
|
11
|
+
end
|
12
|
+
|
13
|
+
def respond!(body, status = 200, header = {})
|
14
|
+
header['Content-Type'] ||= 'text/html'
|
15
|
+
throw(:respond, Response.new(body, status, header))
|
16
|
+
end
|
17
|
+
|
18
|
+
# +target+ should be anything responding to #to_s.
|
19
|
+
# To check or modify the URI the redirect will go to you may pass a
|
20
|
+
# block, the result value of the block is ignored:
|
21
|
+
#
|
22
|
+
# redirect("/"){|uri| uri.scheme = 'http' }
|
23
|
+
# redirect("/"){|uri| uri.host = 'secure.com' if uri.scheme =~ /s/ }
|
24
|
+
#
|
25
|
+
# +options+ may contain:
|
26
|
+
#
|
27
|
+
# :scheme => "http" | "https" | "ftp" | ...
|
28
|
+
# :host => "localhost" | "foo.com" | "123.123.123.123" | ...
|
29
|
+
# :port => 7000 | "80" | 80 | ...
|
30
|
+
#
|
31
|
+
# :status => 302 | 300 | 303 | ...
|
32
|
+
# :body => "This is a redirect, hold on while we teleport" | ...
|
33
|
+
#
|
34
|
+
# :raw! => true | false | nil | ...
|
35
|
+
#
|
36
|
+
# Note that all options are optional and you may just pass a +target+.
|
37
|
+
|
38
|
+
def redirect(target, options = {})
|
39
|
+
target = target.to_s
|
40
|
+
|
41
|
+
case target
|
42
|
+
when /^http/, /^\//
|
43
|
+
uri = URI(target)
|
44
|
+
else
|
45
|
+
uri = URI("/#{target}")
|
46
|
+
end
|
47
|
+
|
48
|
+
uri.scheme ||= options[:scheme] || request.scheme
|
49
|
+
uri.host ||= options[:host] || request.host
|
50
|
+
uri.port ||= options[:port] || request.port
|
51
|
+
|
52
|
+
uri = URI(uri.to_s)
|
53
|
+
|
54
|
+
yield(uri) if block_given?
|
55
|
+
|
56
|
+
raw_redirect(uri, options)
|
57
|
+
end
|
58
|
+
|
59
|
+
def raw_redirect(target, options = {}, &block)
|
60
|
+
header = response.header.merge('Location' => target.to_s)
|
61
|
+
status = options[:status] || 302
|
62
|
+
body = options[:body] || redirect_body(target)
|
63
|
+
|
64
|
+
Log.debug "Redirect to: #{target}"
|
65
|
+
throw(:redirect, Response.new(body, status, header, &block))
|
66
|
+
end
|
67
|
+
|
68
|
+
def redirect_body(target)
|
69
|
+
"You are being redirected, please follow this link to: " +
|
70
|
+
"<a href='#{target}'>#{h target}</a>!"
|
71
|
+
end
|
72
|
+
|
73
|
+
def redirect_referrer(fallback = '/')
|
74
|
+
if referer = request.referer and url = request.url
|
75
|
+
referer_uri, request_uri = URI(referer), URI(url)
|
76
|
+
|
77
|
+
redirect(referer) unless referer_uri == request_uri
|
78
|
+
end
|
79
|
+
|
80
|
+
redirect(fallback)
|
81
|
+
end
|
82
|
+
alias redirect_referer redirect_referrer
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
@@ -0,0 +1,152 @@
|
|
1
|
+
module Innate
|
2
|
+
module Helper
|
3
|
+
module Render
|
4
|
+
# Enables you to simply call:
|
5
|
+
#
|
6
|
+
# @example of added functionality
|
7
|
+
# YourController.render_partial(:foo, :x => 42)
|
8
|
+
def self.included(into)
|
9
|
+
into.extend(self)
|
10
|
+
end
|
11
|
+
|
12
|
+
# Renders the full action in the way a real request would.
|
13
|
+
#
|
14
|
+
# Please be aware that, if this is the first request from a client, you
|
15
|
+
# will not have access to the session in the action being rendered, as no
|
16
|
+
# actual session has been put into place yet.
|
17
|
+
#
|
18
|
+
# It should work as expected on any subsequent requests.
|
19
|
+
#
|
20
|
+
# As usual, patches welcome.
|
21
|
+
#
|
22
|
+
# @example usage
|
23
|
+
#
|
24
|
+
# render_full('/blog/article/1')
|
25
|
+
# render_full('/blog/article/1', :lang => :de)
|
26
|
+
#
|
27
|
+
# Please note that you have to give the full path in the same way you'd
|
28
|
+
# do in a direct request with curl or a browser.
|
29
|
+
#
|
30
|
+
# @api external
|
31
|
+
# @see Mock.session
|
32
|
+
# @author manveru
|
33
|
+
def render_full(path, query = {})
|
34
|
+
uri = URI(path.to_s)
|
35
|
+
uri.query = Rack::Utils.build_query(query)
|
36
|
+
|
37
|
+
if cookie = request.env['HTTP_COOKIE']
|
38
|
+
Mock.session do |mock|
|
39
|
+
mock.cookie = cookie
|
40
|
+
return mock.get(uri.to_s).body
|
41
|
+
end
|
42
|
+
else
|
43
|
+
Mock.get(uri.to_s).body
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
# Renders an action without any layout.
|
48
|
+
# You can further tweak the action to be rendered by passing a block.
|
49
|
+
#
|
50
|
+
# @example usage
|
51
|
+
#
|
52
|
+
# render_partial(:index)
|
53
|
+
# render_partial(:index, :title => :foo)
|
54
|
+
#
|
55
|
+
# Please note that you only have to supply the action name, if your
|
56
|
+
# action requires arguments then you have to pass a name suitable for
|
57
|
+
# that.
|
58
|
+
#
|
59
|
+
# @example usage with action that requires arguments
|
60
|
+
#
|
61
|
+
# # requires two arguments
|
62
|
+
# def foo(a, b)
|
63
|
+
# end
|
64
|
+
#
|
65
|
+
# # pass two suitable arguments
|
66
|
+
# render_partial('foo/1/2')
|
67
|
+
#
|
68
|
+
# @api external
|
69
|
+
# @see render_custom
|
70
|
+
# @author manveru
|
71
|
+
def render_partial(action_name, variables = {})
|
72
|
+
render_custom(action_name, variables) do |action|
|
73
|
+
action.layout = nil
|
74
|
+
yield(action) if block_given?
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
# Renders an action view, doesn't execute any methods and won't wrap it
|
79
|
+
# into a layout.
|
80
|
+
# You can further tweak the action to be rendered by passing a block.
|
81
|
+
#
|
82
|
+
# @example usage
|
83
|
+
#
|
84
|
+
# render_view(:index)
|
85
|
+
# render_view(:index, :title => :foo)
|
86
|
+
#
|
87
|
+
# @api external
|
88
|
+
# @see render_custom
|
89
|
+
# @author manveru
|
90
|
+
def render_view(action_name, variables = {})
|
91
|
+
render_custom(action_name, variables) do |action|
|
92
|
+
action.layout = nil
|
93
|
+
action.method = nil
|
94
|
+
yield(action) if block_given?
|
95
|
+
end
|
96
|
+
end
|
97
|
+
|
98
|
+
# Use the given file as a template and render it in the same scope as
|
99
|
+
# the current action.
|
100
|
+
# The +filename+ may be an absolute path or relative to the process
|
101
|
+
# working directory.
|
102
|
+
#
|
103
|
+
# @example usage
|
104
|
+
#
|
105
|
+
# path = '/home/manveru/example/app/todo/view/index.xhtml'
|
106
|
+
# render_file(path)
|
107
|
+
# render_file(path, :title => :foo)
|
108
|
+
#
|
109
|
+
# Ramaze will emit a warning if you try to render an Action without a
|
110
|
+
# method or view template, but will still try to render it.
|
111
|
+
# The usual {Action#valid?} doesn't apply here, as sometimes you just
|
112
|
+
# cannot have a method associated with a template.
|
113
|
+
#
|
114
|
+
# @api external
|
115
|
+
# @see render_custom
|
116
|
+
# @author manveru
|
117
|
+
def render_file(filename, variables = {})
|
118
|
+
action = Action.create(:view => filename)
|
119
|
+
action.sync_variables(self.action)
|
120
|
+
|
121
|
+
action.node = self.class
|
122
|
+
action.engine = self.action.engine
|
123
|
+
action.instance = action.node.new
|
124
|
+
action.variables = variables.dup
|
125
|
+
|
126
|
+
yield(action) if block_given?
|
127
|
+
|
128
|
+
valid_action = action.view || action.method
|
129
|
+
Log.warn("Empty action: %p" % [action]) unless valid_action
|
130
|
+
action.render
|
131
|
+
end
|
132
|
+
|
133
|
+
# @api internal
|
134
|
+
# @author manveru
|
135
|
+
def render_custom(action_name, variables = {})
|
136
|
+
unless action = resolve(action_name.to_s)
|
137
|
+
raise(ArgumentError, "No Action %p on #{self}" % [action_name])
|
138
|
+
end
|
139
|
+
|
140
|
+
action.sync_variables(self.action)
|
141
|
+
action.instance = action.node.new
|
142
|
+
action.variables = action.variables.merge(variables)
|
143
|
+
|
144
|
+
yield(action) if block_given?
|
145
|
+
|
146
|
+
valid_action = action.view || action.method
|
147
|
+
Log.warn("Empty action: %p" % [action]) unless valid_action
|
148
|
+
action.render
|
149
|
+
end
|
150
|
+
end
|
151
|
+
end
|
152
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module Innate
|
2
|
+
module Helper
|
3
|
+
module SendFile
|
4
|
+
# Not optimally performing but convenient way to send files by their
|
5
|
+
# filename.
|
6
|
+
#
|
7
|
+
# I think we should remove this from the default helpers and move it into
|
8
|
+
# Ramaze, the functionality is almost never used, the naming is ambigous,
|
9
|
+
# and it doesn't use the send_file capabilities of frontend servers.
|
10
|
+
#
|
11
|
+
# So for now, I'll mark it for deprecation
|
12
|
+
def send_file(filename, content_type = nil, content_disposition = nil)
|
13
|
+
content_type ||= Rack::Mime.mime_type(::File.extname(filename))
|
14
|
+
content_disposition ||= File.basename(filename)
|
15
|
+
|
16
|
+
response.body = ::File.readlines(filename, 'rb')
|
17
|
+
response['Content-Length'] = ::File.size(filename).to_s
|
18
|
+
response['Content-Type'] = content_type
|
19
|
+
response['Content-Disposition'] = content_disposition
|
20
|
+
response.status = 200
|
21
|
+
|
22
|
+
throw(:respond, response)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|