sinatra-outputbuffer 0.1.0
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/.document +5 -0
- data/.gitignore +22 -0
- data/CHANGES +4 -0
- data/LICENSE +20 -0
- data/README.rdoc +220 -0
- data/Rakefile +89 -0
- data/VERSION +1 -0
- data/lib/sinatra/outputbuffer.rb +244 -0
- data/sinatra-outputbuffer.gemspec +62 -0
- data/spec/sinatra/outputbuffer_spec.rb +225 -0
- data/spec/spec.opts +1 -0
- data/spec/spec_helper.rb +57 -0
- metadata +116 -0
data/.document
ADDED
data/.gitignore
ADDED
data/CHANGES
ADDED
data/LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2010 Kematzy, Nathan Esquenazi & Others unknown (for now)
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.rdoc
ADDED
@@ -0,0 +1,220 @@
|
|
1
|
+
= Sinatra::OutputBuffer
|
2
|
+
|
3
|
+
A Sinatra Extension that makes content output buffering easy within your apps or extensions.
|
4
|
+
|
5
|
+
|
6
|
+
== Why was this gem created ?
|
7
|
+
|
8
|
+
To enable the Sinatra community to quickly and easily add this functionality to any
|
9
|
+
app / extension they wish to create. ie: preventing time waste or the 're-invention of the wheel'.
|
10
|
+
|
11
|
+
|
12
|
+
== Installation
|
13
|
+
|
14
|
+
# Add RubyGems.org (former Gemcutter) to your RubyGems sources
|
15
|
+
$ gem sources -a http://rubygems.org
|
16
|
+
|
17
|
+
$ (sudo)? gem install sinatra-outputbuffer
|
18
|
+
|
19
|
+
== Dependencies
|
20
|
+
|
21
|
+
This Gem depends upon the following:
|
22
|
+
|
23
|
+
=== Runtime:
|
24
|
+
|
25
|
+
* sinatra ( >= 1.0.a )
|
26
|
+
|
27
|
+
|
28
|
+
=== Development & Tests:
|
29
|
+
|
30
|
+
* sinatra-tests (>= 0.1.6)
|
31
|
+
* rspec (>= 1.3.0 )
|
32
|
+
* rack-test (>= 0.5.3)
|
33
|
+
* rspec_hpricot_matchers (>= 0.1.0)
|
34
|
+
|
35
|
+
== Getting Started
|
36
|
+
|
37
|
+
Sinatra::OutputBuffer could be very useful in essentially two scenarios:
|
38
|
+
|
39
|
+
* Apps
|
40
|
+
* Sinatra extensions
|
41
|
+
|
42
|
+
|
43
|
+
=== In Apps
|
44
|
+
|
45
|
+
In the App scenario, Sinatra::OutputBuffer provides the following helper methods:
|
46
|
+
|
47
|
+
* <tt>content_for</tt>
|
48
|
+
|
49
|
+
* <tt>yield_content</tt>
|
50
|
+
|
51
|
+
You can access those methods by doing the following:
|
52
|
+
|
53
|
+
class YourApp < Sinatra::Base
|
54
|
+
helpers Sinatra::OutputBuffer::Helpers
|
55
|
+
|
56
|
+
<snip...>
|
57
|
+
|
58
|
+
end
|
59
|
+
|
60
|
+
|
61
|
+
Then you can use them as follows:
|
62
|
+
|
63
|
+
<% content_for :some_key do %>
|
64
|
+
<h1>some HTML content here</h1>
|
65
|
+
<% end %>
|
66
|
+
|
67
|
+
<%= yield_content :some_key %>
|
68
|
+
|
69
|
+
NB! the syntax used for calling these methods.
|
70
|
+
|
71
|
+
Or in Haml
|
72
|
+
|
73
|
+
- content_for :some_key do
|
74
|
+
%h1 some HTML content here
|
75
|
+
|
76
|
+
= yield_content :some_key
|
77
|
+
|
78
|
+
NB! the syntax used for calling these methods.
|
79
|
+
|
80
|
+
|
81
|
+
A more concrete example:
|
82
|
+
|
83
|
+
# in ../views/layout.erb
|
84
|
+
<snip...>
|
85
|
+
<style type="text/css" media="screen">
|
86
|
+
<%= yield_content :custom_css %>
|
87
|
+
</style>
|
88
|
+
</head>
|
89
|
+
|
90
|
+
|
91
|
+
# in ../views/template.erb
|
92
|
+
<% content_for :custom_css do %>
|
93
|
+
body { color: red; }
|
94
|
+
<% end %>
|
95
|
+
|
96
|
+
# in ../views/shared/sidebar.erb
|
97
|
+
|
98
|
+
<% content_for :custom_css do %>
|
99
|
+
#sidebar { background-color: black; }
|
100
|
+
<% end %>
|
101
|
+
|
102
|
+
Which outputs:
|
103
|
+
|
104
|
+
<style type="text/css" media="screen">
|
105
|
+
body { color: red; }
|
106
|
+
#sidebar { background-color: black; }
|
107
|
+
</style>
|
108
|
+
|
109
|
+
|
110
|
+
The methods outlined below are also available in this mode, but not as useful (?) as
|
111
|
+
when used in extensions.
|
112
|
+
|
113
|
+
|
114
|
+
=== In Sinatra Extensions
|
115
|
+
|
116
|
+
When developing a Sinatra Extension, then you just require the gem and include / register
|
117
|
+
it into the extension you are developing, like this:
|
118
|
+
|
119
|
+
require 'sinatra/outputbuffer'
|
120
|
+
|
121
|
+
module Sinatra
|
122
|
+
module YourExtension
|
123
|
+
include Sinatra::OutputBuffer::Helpers
|
124
|
+
|
125
|
+
<snip...>
|
126
|
+
|
127
|
+
end
|
128
|
+
end
|
129
|
+
|
130
|
+
... or if your extension needs to be registered to function...
|
131
|
+
|
132
|
+
module Sinatra
|
133
|
+
module YourExtension
|
134
|
+
|
135
|
+
<snip...>
|
136
|
+
|
137
|
+
def self.registered(app)
|
138
|
+
app.helpers Sinatra::OutputBuffer::Helpers
|
139
|
+
# or
|
140
|
+
app.register Sinatra::OutputBuffer # works too, and leaves a 'trace' of it being loaded
|
141
|
+
<snip...>
|
142
|
+
end
|
143
|
+
|
144
|
+
end
|
145
|
+
end
|
146
|
+
|
147
|
+
|
148
|
+
Once included, Sinatra::OutputBuffer provides the following very useful helper methods:
|
149
|
+
|
150
|
+
* <tt>capture_html</tt>
|
151
|
+
|
152
|
+
* <tt>concat_content</tt>
|
153
|
+
|
154
|
+
* <tt>block_is_template?</tt>
|
155
|
+
|
156
|
+
|
157
|
+
With these three methods you can very easily write something like this:
|
158
|
+
|
159
|
+
##
|
160
|
+
# Creates an html tag with given name, content and options
|
161
|
+
#
|
162
|
+
# ==== Examples
|
163
|
+
#
|
164
|
+
# content_tag(:p, "hello", :class => 'light')
|
165
|
+
#
|
166
|
+
# content_tag(:p, :class => 'dark') do ...
|
167
|
+
# # some output here..
|
168
|
+
# end
|
169
|
+
#
|
170
|
+
# content_tag(name, content=nil, options={}, &block)
|
171
|
+
#
|
172
|
+
def content_tag(*args, &block)
|
173
|
+
name = args.first
|
174
|
+
options = args.extract_options!
|
175
|
+
tag_html = block_given? ? capture_html(&block) : args[1]
|
176
|
+
tag_result = tag(name, options.merge(:content => tag_html))
|
177
|
+
block_is_template?(block) ? concat_content(tag_result) : tag_result
|
178
|
+
end
|
179
|
+
|
180
|
+
# NB! code sample taken from the Padrino framework [http://github.com/padrino/padrino-framework/]
|
181
|
+
|
182
|
+
|
183
|
+
That's more or less it.
|
184
|
+
|
185
|
+
|
186
|
+
|
187
|
+
== RTFM
|
188
|
+
|
189
|
+
If the above is not clear enough, please check the Specs for a better understanding.
|
190
|
+
|
191
|
+
|
192
|
+
== Errors / Bugs
|
193
|
+
|
194
|
+
If something is not behaving intuitively, it is a bug, and should be reported.
|
195
|
+
Report it here: http://github.com/kematzy/sinatra-outputbuffer/issues
|
196
|
+
|
197
|
+
|
198
|
+
== TODOs
|
199
|
+
|
200
|
+
* Keep it up to date with any changes in Sinatra.
|
201
|
+
|
202
|
+
* Any other improvements you can think of.
|
203
|
+
|
204
|
+
|
205
|
+
== Note on Patches/Pull Requests
|
206
|
+
|
207
|
+
* Fork the project.
|
208
|
+
* Make your feature addition or bug fix.
|
209
|
+
* Add tests for it. This is important so I don't break it in a future version unintentionally.
|
210
|
+
* Commit, do not mess with rakefile, version, or history.
|
211
|
+
* (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
|
212
|
+
* Send me a pull request. Bonus points for topic branches.
|
213
|
+
|
214
|
+
== Copyright
|
215
|
+
|
216
|
+
Copyright (c) 2010 Kematzy, Nathan Esquenazi & Others (?)
|
217
|
+
|
218
|
+
Released under the MIT License.
|
219
|
+
|
220
|
+
See LICENSE for further details.
|
data/Rakefile
ADDED
@@ -0,0 +1,89 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'rake'
|
3
|
+
|
4
|
+
begin
|
5
|
+
require 'jeweler'
|
6
|
+
Jeweler::Tasks.new do |gem|
|
7
|
+
gem.name = "sinatra-outputbuffer"
|
8
|
+
gem.summary = %Q{A Sinatra Extension that makes content output buffering easy.}
|
9
|
+
gem.description = %Q{A Sinatra Extension that makes content output buffering easy.}
|
10
|
+
gem.email = "kematzy@gmail.com"
|
11
|
+
gem.homepage = "http://github.com/kematzy/sinatra-outputbuffer"
|
12
|
+
gem.authors = ["kematzy"]
|
13
|
+
gem.add_dependency "sinatra", ">= 1.0.a"
|
14
|
+
gem.add_development_dependency "sinatra-tests", ">= 0.1.6"
|
15
|
+
gem.add_development_dependency "rspec", ">= 1.3.0"
|
16
|
+
# gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
|
17
|
+
end
|
18
|
+
Jeweler::GemcutterTasks.new
|
19
|
+
rescue LoadError
|
20
|
+
puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
|
21
|
+
end
|
22
|
+
|
23
|
+
require 'spec/rake/spectask'
|
24
|
+
Spec::Rake::SpecTask.new(:spec) do |spec|
|
25
|
+
spec.libs << 'lib' << 'spec'
|
26
|
+
spec.spec_opts = ["--color", "--format", "specdoc", "--require", "spec/spec_helper.rb"]
|
27
|
+
spec.spec_files = FileList['spec/**/*_spec.rb']
|
28
|
+
end
|
29
|
+
|
30
|
+
Spec::Rake::SpecTask.new(:rcov) do |spec|
|
31
|
+
spec.libs << 'lib' << 'spec'
|
32
|
+
spec.spec_opts = ["--color", "--format", "specdoc", "--require", "spec/spec_helper.rb"]
|
33
|
+
spec.pattern = 'spec/**/*_spec.rb'
|
34
|
+
spec.rcov = true
|
35
|
+
end
|
36
|
+
|
37
|
+
namespace :spec do
|
38
|
+
|
39
|
+
desc "Run all specifications quietly"
|
40
|
+
Spec::Rake::SpecTask.new(:quiet) do |t|
|
41
|
+
t.libs << "lib"
|
42
|
+
t.spec_opts = ["--color", "--require", "spec/spec_helper.rb"]
|
43
|
+
end
|
44
|
+
|
45
|
+
desc "Run specific spec verbosely (SPEC=/path/2/file)"
|
46
|
+
Spec::Rake::SpecTask.new(:select) do |t|
|
47
|
+
t.libs << "lib"
|
48
|
+
t.spec_files = [ENV["SPEC"]]
|
49
|
+
t.spec_opts = ["--color", "--format", "specdoc", "--require", "spec/spec_helper.rb"]
|
50
|
+
end
|
51
|
+
|
52
|
+
end
|
53
|
+
|
54
|
+
task :spec => :check_dependencies
|
55
|
+
|
56
|
+
task :default => :spec
|
57
|
+
|
58
|
+
require 'rake/rdoctask'
|
59
|
+
Rake::RDocTask.new do |rdoc|
|
60
|
+
version = File.exist?('VERSION') ? File.read('VERSION') : ""
|
61
|
+
|
62
|
+
rdoc.rdoc_dir = 'rdoc'
|
63
|
+
rdoc.title = "Sinatra::OutputBuffer #{version}"
|
64
|
+
rdoc.rdoc_files.include('README*')
|
65
|
+
rdoc.rdoc_files.include('lib/**/*.rb')
|
66
|
+
end
|
67
|
+
|
68
|
+
desc 'Build the rdoc HTML Files'
|
69
|
+
task :docs do
|
70
|
+
version = File.exist?('VERSION') ? IO.read('VERSION').chomp : "[Unknown]"
|
71
|
+
|
72
|
+
sh "sdoc -N --title 'Sinatra::OutputBuffer v#{version}' lib/ README.rdoc"
|
73
|
+
end
|
74
|
+
|
75
|
+
namespace :docs do
|
76
|
+
|
77
|
+
desc 'Remove rdoc products'
|
78
|
+
task :remove => [:clobber_rdoc]
|
79
|
+
|
80
|
+
desc 'Force a rebuild of the RDOC files'
|
81
|
+
task :rebuild => [:rerdoc]
|
82
|
+
|
83
|
+
desc 'Build docs, and open in browser for viewing (specify BROWSER)'
|
84
|
+
task :open => [:docs] do
|
85
|
+
browser = ENV["BROWSER"] || "safari"
|
86
|
+
sh "open -a #{browser} doc/index.html"
|
87
|
+
end
|
88
|
+
|
89
|
+
end
|
data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
0.1.0
|
@@ -0,0 +1,244 @@
|
|
1
|
+
|
2
|
+
# :stopdoc:
|
3
|
+
unless Object.new.respond_to?(:blank?)
|
4
|
+
|
5
|
+
class Object
|
6
|
+
def blank?
|
7
|
+
respond_to?(:empty?) ? empty? : !self
|
8
|
+
end
|
9
|
+
def present?
|
10
|
+
!blank?
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
# :startdoc:
|
15
|
+
|
16
|
+
|
17
|
+
module Sinatra
|
18
|
+
|
19
|
+
# Sinatra::OutputBuffer Extension
|
20
|
+
#
|
21
|
+
#
|
22
|
+
#
|
23
|
+
# The code within this extension is almost in its interity copied from:
|
24
|
+
#
|
25
|
+
# sinatra_more gem [ http://github.com/nesquena/sinatra_more/ ] by Nathan Esquenazi.
|
26
|
+
# The padrino-framework [ http://github.com/padrino/padrino-framework/ ] by Nathan Esquenazi & others.
|
27
|
+
#
|
28
|
+
#
|
29
|
+
# Copyright (c) 2010 Kematzy [kematzy gmail com]
|
30
|
+
# Copyright (c) 2009 Nathan Esquenazi
|
31
|
+
#
|
32
|
+
# Permission is hereby granted, free of charge, to any person obtaining
|
33
|
+
# a copy of this software and associated documentation files (the
|
34
|
+
# "Software"), to deal in the Software without restriction, including
|
35
|
+
# without limitation the rights to use, copy, modify, merge, publish,
|
36
|
+
# distribute, sublicense, and/or sell copies of the Software, and to
|
37
|
+
# permit persons to whom the Software is furnished to do so, subject to
|
38
|
+
# the following conditions:
|
39
|
+
#
|
40
|
+
# The above copyright notice and this permission notice shall be
|
41
|
+
# included in all copies or substantial portions of the Software.
|
42
|
+
#
|
43
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
44
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
45
|
+
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
46
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
47
|
+
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
48
|
+
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
49
|
+
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
50
|
+
#
|
51
|
+
#
|
52
|
+
module OutputBuffer
|
53
|
+
|
54
|
+
VERSION = '0.1.0'
|
55
|
+
##
|
56
|
+
# Returns the version string for this extension
|
57
|
+
#
|
58
|
+
# ==== Examples
|
59
|
+
#
|
60
|
+
# Sinatra::OutputBuffer.version => 'Sinatra::Output v0.9.9'
|
61
|
+
#
|
62
|
+
def self.version; "Sinatra::OutputBuffer v#{VERSION}"; end
|
63
|
+
|
64
|
+
# :stopdoc:
|
65
|
+
# Retaining the Helpers module, just to keep a standard interface
|
66
|
+
# and possibly future proof things ;-)
|
67
|
+
# :startdoc:
|
68
|
+
|
69
|
+
|
70
|
+
module Helpers
|
71
|
+
|
72
|
+
##
|
73
|
+
# Captures the html from a block of template code for erb or haml
|
74
|
+
#
|
75
|
+
# ==== Examples
|
76
|
+
#
|
77
|
+
# capture_html(&block) => "...html..."
|
78
|
+
#
|
79
|
+
# @api public
|
80
|
+
def capture_html(*args, &block)
|
81
|
+
if self.respond_to?(:is_haml?) && is_haml?
|
82
|
+
block_is_haml?(block) ? capture_haml(*args, &block) : block.call
|
83
|
+
elsif has_erb_buffer?
|
84
|
+
result_text = capture_erb(*args, &block)
|
85
|
+
result_text.present? ? result_text : (block_given? && block.call(*args))
|
86
|
+
else # theres no template to capture, invoke the block directly
|
87
|
+
block.call(*args)
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
##
|
92
|
+
# Outputs the given text to the templates buffer directly
|
93
|
+
#
|
94
|
+
# ==== Examples
|
95
|
+
#
|
96
|
+
# concat_content("This will be output to the template buffer in erb or haml")
|
97
|
+
#
|
98
|
+
# @api public
|
99
|
+
def concat_content(text="")
|
100
|
+
if self.respond_to?(:is_haml?) && is_haml?
|
101
|
+
haml_concat(text)
|
102
|
+
elsif has_erb_buffer?
|
103
|
+
erb_concat(text)
|
104
|
+
else # theres no template to concat, return the text directly
|
105
|
+
text
|
106
|
+
end
|
107
|
+
end
|
108
|
+
|
109
|
+
##
|
110
|
+
# Returns true if the block is from an ERB or HAML template; false otherwise.
|
111
|
+
# Used to determine if html should be returned or concatted to view
|
112
|
+
#
|
113
|
+
# ==== Examples
|
114
|
+
#
|
115
|
+
# block_is_template?(block)
|
116
|
+
#
|
117
|
+
# @api public
|
118
|
+
def block_is_template?(block)
|
119
|
+
block && (block_is_erb?(block) || (self.respond_to?(:block_is_haml?) && block_is_haml?(block)))
|
120
|
+
end
|
121
|
+
|
122
|
+
##
|
123
|
+
# Capture a block or text of content to be rendered at a later time.
|
124
|
+
# Your blocks can also receive values, which are passed to them by <tt>yield_content</tt>
|
125
|
+
#
|
126
|
+
# ==== Examples
|
127
|
+
#
|
128
|
+
# content_for(:name) { ...content... }
|
129
|
+
# content_for(:name) { |name| ...content... }
|
130
|
+
# content_for(:name, "I'm Jeff")
|
131
|
+
#
|
132
|
+
# @api public
|
133
|
+
def content_for(key, content = nil, &block)
|
134
|
+
content_blocks[key.to_sym] << (block_given? ? block : Proc.new { content })
|
135
|
+
end
|
136
|
+
|
137
|
+
##
|
138
|
+
# Render the captured content blocks for a given key.
|
139
|
+
# You can also pass values to the content blocks by passing them
|
140
|
+
# as arguments after the key.
|
141
|
+
#
|
142
|
+
# ==== Examples
|
143
|
+
#
|
144
|
+
# yield_content :include
|
145
|
+
# yield_content :head, "param1", "param2"
|
146
|
+
# yield_content(:title) || "My page title"
|
147
|
+
#
|
148
|
+
# @api public
|
149
|
+
def yield_content(key, *args)
|
150
|
+
blocks = content_blocks[key.to_sym]
|
151
|
+
return nil if blocks.empty?
|
152
|
+
blocks.map { |content|
|
153
|
+
capture_html(*args, &content)
|
154
|
+
}.join
|
155
|
+
end
|
156
|
+
|
157
|
+
|
158
|
+
private
|
159
|
+
|
160
|
+
|
161
|
+
##
|
162
|
+
# Retrieves content_blocks stored by content_for or within yield_content
|
163
|
+
#
|
164
|
+
# ==== Examples
|
165
|
+
#
|
166
|
+
# content_blocks[:name] => ['...', '...']
|
167
|
+
#
|
168
|
+
# @api private/public
|
169
|
+
def content_blocks
|
170
|
+
@content_blocks ||= Hash.new {|h,k| h[k] = [] }
|
171
|
+
end
|
172
|
+
|
173
|
+
##
|
174
|
+
# Used to capture the html from a block of erb code
|
175
|
+
#
|
176
|
+
# ==== Examples
|
177
|
+
#
|
178
|
+
# capture_erb(&block) => '...html...'
|
179
|
+
#
|
180
|
+
# @api private/public
|
181
|
+
def capture_erb(*args, &block)
|
182
|
+
erb_with_output_buffer { block_given? && block.call(*args) }
|
183
|
+
end
|
184
|
+
|
185
|
+
##
|
186
|
+
# Concats directly to an erb template
|
187
|
+
#
|
188
|
+
# ==== Examples
|
189
|
+
#
|
190
|
+
# erb_concat("Direct to buffer")
|
191
|
+
#
|
192
|
+
# @api private/public
|
193
|
+
def erb_concat(text)
|
194
|
+
@_out_buf << text if has_erb_buffer?
|
195
|
+
end
|
196
|
+
|
197
|
+
##
|
198
|
+
# Returns true if an erb buffer is detected
|
199
|
+
#
|
200
|
+
# ==== Examples
|
201
|
+
#
|
202
|
+
# has_erb_buffer? => true
|
203
|
+
#
|
204
|
+
# @api private/public
|
205
|
+
def has_erb_buffer?
|
206
|
+
!@_out_buf.nil?
|
207
|
+
end
|
208
|
+
|
209
|
+
if RUBY_VERSION < '1.9.0'
|
210
|
+
# Check whether we're called from an erb template.
|
211
|
+
# We'd return a string in any other case, but erb <%= ... %>
|
212
|
+
# can't take an <% end %> later on, so we have to use <% ... %>
|
213
|
+
# and implicitly concat.
|
214
|
+
def block_is_erb?(block)
|
215
|
+
has_erb_buffer? || block && eval('defined? __in_erb_template', block)
|
216
|
+
end
|
217
|
+
else
|
218
|
+
def block_is_erb?(block)
|
219
|
+
has_erb_buffer? || block && eval('defined? __in_erb_template', block.binding)
|
220
|
+
end
|
221
|
+
end
|
222
|
+
|
223
|
+
##
|
224
|
+
# Used to direct the buffer for the erb capture
|
225
|
+
#
|
226
|
+
def erb_with_output_buffer(buf = '')
|
227
|
+
@_out_buf, old_buffer = buf, @_out_buf
|
228
|
+
yield
|
229
|
+
@_out_buf
|
230
|
+
ensure
|
231
|
+
@_out_buf = old_buffer
|
232
|
+
end
|
233
|
+
|
234
|
+
end #/ Helpers
|
235
|
+
|
236
|
+
def self.registered(app)
|
237
|
+
app.helpers Sinatra::OutputBuffer::Helpers
|
238
|
+
end
|
239
|
+
|
240
|
+
end #/ OutputBuffer
|
241
|
+
|
242
|
+
helpers Sinatra::OutputBuffer::Helpers
|
243
|
+
|
244
|
+
end #/ Sinatra
|
@@ -0,0 +1,62 @@
|
|
1
|
+
# Generated by jeweler
|
2
|
+
# DO NOT EDIT THIS FILE DIRECTLY
|
3
|
+
# Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
|
4
|
+
# -*- encoding: utf-8 -*-
|
5
|
+
|
6
|
+
Gem::Specification.new do |s|
|
7
|
+
s.name = %q{sinatra-outputbuffer}
|
8
|
+
s.version = "0.1.0"
|
9
|
+
|
10
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
|
+
s.authors = ["kematzy"]
|
12
|
+
s.date = %q{2010-03-01}
|
13
|
+
s.description = %q{A Sinatra Extension that makes content output buffering easy.}
|
14
|
+
s.email = %q{kematzy@gmail.com}
|
15
|
+
s.extra_rdoc_files = [
|
16
|
+
"LICENSE",
|
17
|
+
"README.rdoc"
|
18
|
+
]
|
19
|
+
s.files = [
|
20
|
+
".document",
|
21
|
+
".gitignore",
|
22
|
+
"CHANGES",
|
23
|
+
"LICENSE",
|
24
|
+
"README.rdoc",
|
25
|
+
"Rakefile",
|
26
|
+
"VERSION",
|
27
|
+
"lib/sinatra/outputbuffer.rb",
|
28
|
+
"sinatra-outputbuffer.gemspec",
|
29
|
+
"spec/sinatra/outputbuffer_spec.rb",
|
30
|
+
"spec/spec.opts",
|
31
|
+
"spec/spec_helper.rb"
|
32
|
+
]
|
33
|
+
s.homepage = %q{http://github.com/kematzy/sinatra-outputbuffer}
|
34
|
+
s.rdoc_options = ["--charset=UTF-8"]
|
35
|
+
s.require_paths = ["lib"]
|
36
|
+
s.rubygems_version = %q{1.3.6}
|
37
|
+
s.summary = %q{A Sinatra Extension that makes content output buffering easy.}
|
38
|
+
s.test_files = [
|
39
|
+
"spec/sinatra/outputbuffer_spec.rb",
|
40
|
+
"spec/spec_helper.rb"
|
41
|
+
]
|
42
|
+
|
43
|
+
if s.respond_to? :specification_version then
|
44
|
+
current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
|
45
|
+
s.specification_version = 3
|
46
|
+
|
47
|
+
if Gem::Version.new(Gem::RubyGemsVersion) >= Gem::Version.new('1.2.0') then
|
48
|
+
s.add_runtime_dependency(%q<sinatra>, [">= 1.0.a"])
|
49
|
+
s.add_development_dependency(%q<sinatra-tests>, [">= 0.1.6"])
|
50
|
+
s.add_development_dependency(%q<rspec>, [">= 1.3.0"])
|
51
|
+
else
|
52
|
+
s.add_dependency(%q<sinatra>, [">= 1.0.a"])
|
53
|
+
s.add_dependency(%q<sinatra-tests>, [">= 0.1.6"])
|
54
|
+
s.add_dependency(%q<rspec>, [">= 1.3.0"])
|
55
|
+
end
|
56
|
+
else
|
57
|
+
s.add_dependency(%q<sinatra>, [">= 1.0.a"])
|
58
|
+
s.add_dependency(%q<sinatra-tests>, [">= 0.1.6"])
|
59
|
+
s.add_dependency(%q<rspec>, [">= 1.3.0"])
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
@@ -0,0 +1,225 @@
|
|
1
|
+
|
2
|
+
require "#{File.dirname(File.dirname(File.expand_path(__FILE__)))}/spec_helper"
|
3
|
+
|
4
|
+
describe "Sinatra" do
|
5
|
+
|
6
|
+
describe "OutputBuffer" do
|
7
|
+
|
8
|
+
class MyTestApp
|
9
|
+
helpers Sinatra::OutputBuffer::Helpers
|
10
|
+
|
11
|
+
helpers do
|
12
|
+
|
13
|
+
def captured_content(&block)
|
14
|
+
content_html = capture_html(&block)
|
15
|
+
"<p>#{content_html}</p>"
|
16
|
+
end
|
17
|
+
|
18
|
+
def concat_in_p(content_html)
|
19
|
+
concat_content "<p>#{content_html}</p>"
|
20
|
+
end
|
21
|
+
|
22
|
+
def ruby_not_template_block
|
23
|
+
determine_block_is_template('ruby') do
|
24
|
+
content_tag(:span, "This not a template block")
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
def determine_block_is_template(name, &block)
|
29
|
+
concat_content "<p class='is_template'>The #{name} block passed in is a template</p>" if block_is_template?(block)
|
30
|
+
end
|
31
|
+
|
32
|
+
end
|
33
|
+
|
34
|
+
end
|
35
|
+
|
36
|
+
# convenience shared spec that sets up MyTestApp and tests it's OK
|
37
|
+
# without it you will get "stack level too deep" errors
|
38
|
+
it_should_behave_like "MyTestApp"
|
39
|
+
|
40
|
+
|
41
|
+
describe "Helpers" do
|
42
|
+
|
43
|
+
describe "#capture_html" do
|
44
|
+
|
45
|
+
it "should capture the HTML content from ERB templates" do
|
46
|
+
erb_block = %Q[
|
47
|
+
<% @content = captured_content do %>
|
48
|
+
<span>Captured Line 1</span>
|
49
|
+
<span>Captured Line 2</span>
|
50
|
+
<% end %>
|
51
|
+
<%= @content %>
|
52
|
+
]
|
53
|
+
erb_app erb_block
|
54
|
+
body.should have_tag('p > span', 'Captured Line 1')
|
55
|
+
body.should have_tag('p > span', 'Captured Line 2')
|
56
|
+
end
|
57
|
+
|
58
|
+
it "should capture the HTML content from Haml templates" do
|
59
|
+
haml_block = %Q[
|
60
|
+
- @content = captured_content do
|
61
|
+
%span Captured Line 1
|
62
|
+
%span Captured Line 2
|
63
|
+
= @content
|
64
|
+
]
|
65
|
+
haml_app haml_block
|
66
|
+
body.should have_tag('p > span', 'Captured Line 1')
|
67
|
+
body.should have_tag('p > span', 'Captured Line 2')
|
68
|
+
end
|
69
|
+
|
70
|
+
end #/ #capture_html
|
71
|
+
|
72
|
+
describe "#concat_content" do
|
73
|
+
|
74
|
+
it "should concatenate the HTML content from ERB templates" do
|
75
|
+
erb_app '<% concat_in_p("Concat Line 3") %>'
|
76
|
+
body.should have_tag('p', 'Concat Line 3')
|
77
|
+
end
|
78
|
+
|
79
|
+
it "should concatenate the HTML content from Haml templates" do
|
80
|
+
haml_app "- concat_in_p('Concat Line 3')"
|
81
|
+
body.should have_tag('p', 'Concat Line 3')
|
82
|
+
end
|
83
|
+
|
84
|
+
end #/ #concat_content
|
85
|
+
|
86
|
+
describe "#block_is_template?" do
|
87
|
+
|
88
|
+
it "should return true if called from an ERB template" do
|
89
|
+
erb_block = %Q[
|
90
|
+
<% determine_block_is_template('erb') do %>
|
91
|
+
<span>This is erb</span>
|
92
|
+
<span>This is erb</span>
|
93
|
+
<% end %>
|
94
|
+
]
|
95
|
+
erb_app erb_block
|
96
|
+
body.should have_tag('p.is_template', 'The erb block passed in is a template')
|
97
|
+
end
|
98
|
+
|
99
|
+
it "should return false if NOT called from an ERB template" do
|
100
|
+
erb_app '<% ruby_not_template_block %>'
|
101
|
+
# body.should have_tag(:debug)
|
102
|
+
pending "TODO: Get ERB template detection working (fix block_is_erb? method)"
|
103
|
+
body.should_not have_tag('p.is_template', 'The ruby block passed in is a template')
|
104
|
+
|
105
|
+
end
|
106
|
+
|
107
|
+
it "should return true if called from a Haml template" do
|
108
|
+
haml_block = %Q[
|
109
|
+
- determine_block_is_template('haml') do
|
110
|
+
%span This is haml
|
111
|
+
%span This is haml
|
112
|
+
]
|
113
|
+
haml_app haml_block
|
114
|
+
body.should have_tag('p.is_template', 'The haml block passed in is a template')
|
115
|
+
end
|
116
|
+
|
117
|
+
it "should return false if NOT called from a Haml template" do
|
118
|
+
haml_app '- ruby_not_template_block'
|
119
|
+
body.should_not have_tag('p.is_template', 'The haml block passed in is a template')
|
120
|
+
end
|
121
|
+
|
122
|
+
end #/ #block_is_template?
|
123
|
+
|
124
|
+
describe "#content_for" do
|
125
|
+
|
126
|
+
it "should NOT bleed into current ERB template output" do
|
127
|
+
erb_block = %Q[
|
128
|
+
<h1>:content_for</h1>
|
129
|
+
<% content_for :demo do %>
|
130
|
+
<h1>This is content yielded from a content_for</h1>
|
131
|
+
<% end %>
|
132
|
+
]
|
133
|
+
erb_app erb_block
|
134
|
+
# body.should have_tag(:debug)
|
135
|
+
body.should == "\n<h1>:content_for</h1>\n\n"
|
136
|
+
end
|
137
|
+
|
138
|
+
it "should NOT bleed into current Haml template output" do
|
139
|
+
haml_block = %Q[
|
140
|
+
%h1 :content_for
|
141
|
+
- content_for :demo do
|
142
|
+
%h1 This is content yielded from a content_for
|
143
|
+
]
|
144
|
+
haml_app haml_block
|
145
|
+
# body.should have_tag(:debug)
|
146
|
+
body.should == "<h1>:content_for</h1>\n"
|
147
|
+
end
|
148
|
+
|
149
|
+
it "should handle multiple assignments to the same key" do
|
150
|
+
erb_block = %Q[
|
151
|
+
<% content_for :custom_css do %>
|
152
|
+
body{color:red;}
|
153
|
+
<% end %>
|
154
|
+
|
155
|
+
<% content_for :custom_css do %>
|
156
|
+
h1{color:black;}
|
157
|
+
<% end %>
|
158
|
+
|
159
|
+
<style>
|
160
|
+
<%= yield_content :custom_css %>
|
161
|
+
</style>
|
162
|
+
]
|
163
|
+
erb_app erb_block
|
164
|
+
# body.should have_tag(:debug)
|
165
|
+
body.should match(/body\{color:red;\}/)
|
166
|
+
body.should match(/h1\{color:black;\}/)
|
167
|
+
end
|
168
|
+
|
169
|
+
end #/ #content_for
|
170
|
+
|
171
|
+
describe "#yield_content" do
|
172
|
+
|
173
|
+
it "should yield the buffered content from the current ERB template" do
|
174
|
+
erb_block = %Q[
|
175
|
+
<% content_for :demo do %>
|
176
|
+
<h1>This is content yielded from a content_for</h1>
|
177
|
+
<% end %>
|
178
|
+
<div class='demo'><%= yield_content :demo %></div>
|
179
|
+
]
|
180
|
+
erb_app erb_block
|
181
|
+
body.should have_tag('div.demo > h1', 'This is content yielded from a content_for')
|
182
|
+
end
|
183
|
+
|
184
|
+
it "should yield the buffered content from the current Haml template" do
|
185
|
+
haml_block = %Q[
|
186
|
+
- content_for :demo do
|
187
|
+
%h1 This is content yielded from a content_for
|
188
|
+
|
189
|
+
.demo= yield_content :demo
|
190
|
+
]
|
191
|
+
haml_app haml_block
|
192
|
+
body.should have_tag('div.demo > h1', 'This is content yielded from a content_for')
|
193
|
+
end
|
194
|
+
|
195
|
+
it "should yield the buffered content with params from the current ERB template" do
|
196
|
+
erb_block = %Q[
|
197
|
+
<% content_for :demo do |fname, lname| %>
|
198
|
+
<h1>This is content yielded with name <%= fname + " " + lname %></h1>
|
199
|
+
<% end %>
|
200
|
+
<div class='demo'><%= yield_content :demo, 'Joe', 'Blogs' %></div>
|
201
|
+
]
|
202
|
+
erb_app erb_block
|
203
|
+
body.should have_tag('div.demo > h1', 'This is content yielded with name Joe Blogs')
|
204
|
+
end
|
205
|
+
|
206
|
+
it "should yield the buffered content with params from the current Haml template" do
|
207
|
+
# NOTE:: the escaped # => \# in the Haml content below.
|
208
|
+
# Without it the test don't work.s
|
209
|
+
haml_block = %Q[
|
210
|
+
- content_for :demo do |fname, lname|
|
211
|
+
%h1 This is content yielded with name \#{fname + " " + lname}
|
212
|
+
|
213
|
+
.demo= yield_content :demo, 'Joe', 'Blogs'
|
214
|
+
]
|
215
|
+
haml_app haml_block
|
216
|
+
body.should have_tag('div.demo > h1', 'This is content yielded with name Joe Blogs')
|
217
|
+
end
|
218
|
+
|
219
|
+
end #/ #yield_content
|
220
|
+
|
221
|
+
end #/ Helpers
|
222
|
+
|
223
|
+
end #/ OutputBuffer
|
224
|
+
|
225
|
+
end #/ Sinatra
|
data/spec/spec.opts
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
--color
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,57 @@
|
|
1
|
+
|
2
|
+
::APP_ROOT = "#{File.dirname(File.expand_path(__FILE__))}/fixtures"
|
3
|
+
|
4
|
+
$LOAD_PATH.unshift(File.dirname(__FILE__))
|
5
|
+
$LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
|
6
|
+
|
7
|
+
ENV['RACK_ENV'] = 'test'
|
8
|
+
|
9
|
+
#--
|
10
|
+
# DEPENDENCIES
|
11
|
+
#++
|
12
|
+
%w(
|
13
|
+
sinatra/base
|
14
|
+
).each {|lib| require lib }
|
15
|
+
|
16
|
+
#--
|
17
|
+
## SINATRA EXTENSIONS
|
18
|
+
#++
|
19
|
+
%w(
|
20
|
+
sinatra/tests
|
21
|
+
sinatra/outputbuffer
|
22
|
+
).each {|ext| require ext }
|
23
|
+
|
24
|
+
|
25
|
+
Spec::Runner.configure do |config|
|
26
|
+
config.include RspecHpricotMatchers
|
27
|
+
config.include Sinatra::Tests::TestCase
|
28
|
+
config.include Sinatra::Tests::RSpec::SharedSpecs
|
29
|
+
end
|
30
|
+
|
31
|
+
|
32
|
+
# quick convenience methods..
|
33
|
+
|
34
|
+
def fixtures_path
|
35
|
+
"#{File.dirname(File.expand_path(__FILE__))}/fixtures"
|
36
|
+
end
|
37
|
+
|
38
|
+
def public_fixtures_path
|
39
|
+
"#{fixtures_path}/public"
|
40
|
+
end
|
41
|
+
|
42
|
+
class MyTestApp < Sinatra::Base
|
43
|
+
|
44
|
+
set :app_dir, "#{APP_ROOT}/app"
|
45
|
+
set :public, "#{fixtures_path}/public"
|
46
|
+
set :views, "#{app_dir}/views"
|
47
|
+
|
48
|
+
register(Sinatra::Tests)
|
49
|
+
|
50
|
+
enable :raise_errors
|
51
|
+
|
52
|
+
end #/class MyTestApp
|
53
|
+
|
54
|
+
|
55
|
+
class Test::Unit::TestCase
|
56
|
+
Sinatra::Base.set :environment, :test
|
57
|
+
end
|
metadata
ADDED
@@ -0,0 +1,116 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: sinatra-outputbuffer
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
prerelease: false
|
5
|
+
segments:
|
6
|
+
- 0
|
7
|
+
- 1
|
8
|
+
- 0
|
9
|
+
version: 0.1.0
|
10
|
+
platform: ruby
|
11
|
+
authors:
|
12
|
+
- kematzy
|
13
|
+
autorequire:
|
14
|
+
bindir: bin
|
15
|
+
cert_chain: []
|
16
|
+
|
17
|
+
date: 2010-03-01 00:00:00 +08:00
|
18
|
+
default_executable:
|
19
|
+
dependencies:
|
20
|
+
- !ruby/object:Gem::Dependency
|
21
|
+
name: sinatra
|
22
|
+
prerelease: false
|
23
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
24
|
+
requirements:
|
25
|
+
- - ">="
|
26
|
+
- !ruby/object:Gem::Version
|
27
|
+
segments:
|
28
|
+
- 1
|
29
|
+
- 0
|
30
|
+
- a
|
31
|
+
version: 1.0.a
|
32
|
+
type: :runtime
|
33
|
+
version_requirements: *id001
|
34
|
+
- !ruby/object:Gem::Dependency
|
35
|
+
name: sinatra-tests
|
36
|
+
prerelease: false
|
37
|
+
requirement: &id002 !ruby/object:Gem::Requirement
|
38
|
+
requirements:
|
39
|
+
- - ">="
|
40
|
+
- !ruby/object:Gem::Version
|
41
|
+
segments:
|
42
|
+
- 0
|
43
|
+
- 1
|
44
|
+
- 6
|
45
|
+
version: 0.1.6
|
46
|
+
type: :development
|
47
|
+
version_requirements: *id002
|
48
|
+
- !ruby/object:Gem::Dependency
|
49
|
+
name: rspec
|
50
|
+
prerelease: false
|
51
|
+
requirement: &id003 !ruby/object:Gem::Requirement
|
52
|
+
requirements:
|
53
|
+
- - ">="
|
54
|
+
- !ruby/object:Gem::Version
|
55
|
+
segments:
|
56
|
+
- 1
|
57
|
+
- 3
|
58
|
+
- 0
|
59
|
+
version: 1.3.0
|
60
|
+
type: :development
|
61
|
+
version_requirements: *id003
|
62
|
+
description: A Sinatra Extension that makes content output buffering easy.
|
63
|
+
email: kematzy@gmail.com
|
64
|
+
executables: []
|
65
|
+
|
66
|
+
extensions: []
|
67
|
+
|
68
|
+
extra_rdoc_files:
|
69
|
+
- LICENSE
|
70
|
+
- README.rdoc
|
71
|
+
files:
|
72
|
+
- .document
|
73
|
+
- .gitignore
|
74
|
+
- CHANGES
|
75
|
+
- LICENSE
|
76
|
+
- README.rdoc
|
77
|
+
- Rakefile
|
78
|
+
- VERSION
|
79
|
+
- lib/sinatra/outputbuffer.rb
|
80
|
+
- sinatra-outputbuffer.gemspec
|
81
|
+
- spec/sinatra/outputbuffer_spec.rb
|
82
|
+
- spec/spec.opts
|
83
|
+
- spec/spec_helper.rb
|
84
|
+
has_rdoc: true
|
85
|
+
homepage: http://github.com/kematzy/sinatra-outputbuffer
|
86
|
+
licenses: []
|
87
|
+
|
88
|
+
post_install_message:
|
89
|
+
rdoc_options:
|
90
|
+
- --charset=UTF-8
|
91
|
+
require_paths:
|
92
|
+
- lib
|
93
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
94
|
+
requirements:
|
95
|
+
- - ">="
|
96
|
+
- !ruby/object:Gem::Version
|
97
|
+
segments:
|
98
|
+
- 0
|
99
|
+
version: "0"
|
100
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
101
|
+
requirements:
|
102
|
+
- - ">="
|
103
|
+
- !ruby/object:Gem::Version
|
104
|
+
segments:
|
105
|
+
- 0
|
106
|
+
version: "0"
|
107
|
+
requirements: []
|
108
|
+
|
109
|
+
rubyforge_project:
|
110
|
+
rubygems_version: 1.3.6
|
111
|
+
signing_key:
|
112
|
+
specification_version: 3
|
113
|
+
summary: A Sinatra Extension that makes content output buffering easy.
|
114
|
+
test_files:
|
115
|
+
- spec/sinatra/outputbuffer_spec.rb
|
116
|
+
- spec/spec_helper.rb
|