garterbelt 0.0.9 → 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- data/TODO +10 -11
- data/VERSION +1 -1
- data/garterbelt.gemspec +2 -2
- data/lib/renderers/content_rendering.rb +3 -3
- data/lib/renderers/renderer.rb +1 -1
- data/lib/renderers/text.rb +1 -1
- data/lib/view.rb +64 -49
- data/spec/integration/templates/form.rb +1 -1
- data/spec/page_spec.rb +1 -1
- data/spec/performance/profiling.rb +2 -2
- data/spec/renderers/closed_tag_spec.rb +1 -1
- data/spec/renderers/content_tag_spec.rb +2 -2
- data/spec/renderers/text_spec.rb +1 -1
- data/spec/support/mock_view.rb +4 -4
- data/spec/view/view_basics_spec.rb +34 -34
- data/spec/view/view_caching_spec.rb +2 -2
- data/spec/view/view_partial_spec.rb +63 -12
- data/spec/view/view_render_spec.rb +45 -29
- data/spec/view/view_variables_spec.rb +4 -0
- metadata +4 -4
data/TODO
CHANGED
@@ -3,15 +3,16 @@ increase performance ~10%
|
|
3
3
|
anonymous views
|
4
4
|
|
5
5
|
view
|
6
|
-
class level view required defaults to [] not nil
|
7
|
-
join on widgets?
|
8
|
-
pass block to render method so you can yield!
|
9
6
|
better error messaging when rendering buffer, which line in content is causing the problem?
|
10
|
-
|
7
|
+
join on widgets?
|
8
|
+
caching of full views
|
9
|
+
|
10
|
+
partial
|
11
|
+
--
|
11
12
|
|
12
|
-
|
13
|
-
|
14
|
-
|
13
|
+
renderers
|
14
|
+
switch from erb to direct escaping of text
|
15
|
+
make quotes not escape
|
15
16
|
|
16
17
|
page
|
17
18
|
embed_js, embed_css file content, string content
|
@@ -19,10 +20,8 @@ page
|
|
19
20
|
|
20
21
|
|
21
22
|
name changes (for less name collision):
|
22
|
-
|
23
|
-
curator to _curator
|
24
|
-
look at other names for possible issues
|
25
|
-
|
23
|
+
--
|
26
24
|
|
25
|
+
-----------------------------------------
|
27
26
|
# CoverGirl
|
28
27
|
rails style helpers
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.0
|
1
|
+
0.1.0
|
data/garterbelt.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{garterbelt}
|
8
|
-
s.version = "0.0
|
8
|
+
s.version = "0.1.0"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Kane Baccigalupi"]
|
12
|
-
s.date = %q{2011-04-
|
12
|
+
s.date = %q{2011-04-19}
|
13
13
|
s.description = %q{Garterbelt is a Ruby HTML/XML markup framework inspired by Erector and Markaby. Garterbelt maps html tags to methods allowing the intuitive construction of HTML pages using nothing but Ruby. And because it is all Ruby all the time, views benefit from the dryness of inheritance, modules and all the meta magic that Ruby can imagine. Stockings not included.}
|
14
14
|
s.email = %q{baccigalupi@gmail.com}
|
15
15
|
s.extra_rdoc_files = [
|
@@ -17,18 +17,18 @@ module Garterbelt
|
|
17
17
|
end
|
18
18
|
|
19
19
|
def head
|
20
|
-
view.
|
20
|
+
view._level += 1
|
21
21
|
end
|
22
22
|
|
23
23
|
def foot
|
24
|
-
view.
|
24
|
+
view._level -= 1
|
25
25
|
end
|
26
26
|
|
27
27
|
def render_content
|
28
28
|
if content.is_a?(Proc)
|
29
29
|
content.call
|
30
30
|
else
|
31
|
-
view.
|
31
|
+
view._buffer << Text.new(:view => view, :content => content) if content
|
32
32
|
end
|
33
33
|
view.render_buffer
|
34
34
|
end
|
data/lib/renderers/renderer.rb
CHANGED
data/lib/renderers/text.rb
CHANGED
data/lib/view.rb
CHANGED
@@ -1,25 +1,23 @@
|
|
1
1
|
module Garterbelt
|
2
2
|
class View
|
3
|
-
|
4
|
-
|
5
|
-
attr_accessor :output, :buffer, :level, :escape, :block, :options, :render_style
|
6
|
-
attr_reader :curator
|
3
|
+
attr_accessor :output, :_buffer, :_level, :_escape, :block, :initialization_options, :render_style
|
4
|
+
attr_reader :_curator
|
7
5
|
|
8
6
|
def initialize(opts={}, &block)
|
9
|
-
self.
|
10
|
-
self.
|
11
|
-
self.
|
12
|
-
self.render_style =
|
7
|
+
self.initialization_options = opts
|
8
|
+
self._buffer = []
|
9
|
+
self._level = initialization_options.delete(:_level) || 0
|
10
|
+
self.render_style = initialization_options.delete(:style) || :pretty
|
13
11
|
self.output = ""
|
14
|
-
self.
|
12
|
+
self._escape = true
|
15
13
|
self.block = block if block_given?
|
16
14
|
|
17
|
-
self.
|
15
|
+
self._curator = initialization_options.delete(:_curator) || self
|
18
16
|
|
19
17
|
params = self.class.default_variables.merge(opts)
|
20
18
|
keys = params.keys
|
21
19
|
|
22
|
-
unless (
|
20
|
+
unless (self.class.required - keys).empty?
|
23
21
|
raise ArgumentError, "#{(self.class.required - keys).inspect} required as an initialization option"
|
24
22
|
end
|
25
23
|
|
@@ -33,24 +31,29 @@ module Garterbelt
|
|
33
31
|
end
|
34
32
|
end
|
35
33
|
|
36
|
-
def
|
37
|
-
@
|
34
|
+
def _curator=(parent_view)
|
35
|
+
@_curator = parent_view
|
38
36
|
if parent_view != self
|
39
|
-
self.
|
40
|
-
self.
|
37
|
+
self._buffer = parent_view._buffer
|
38
|
+
self._level = parent_view._level
|
41
39
|
self.output = parent_view.output
|
42
|
-
self.
|
40
|
+
self._escape = parent_view._escape
|
43
41
|
self.render_style = parent_view.render_style
|
44
42
|
end
|
45
43
|
end
|
46
44
|
|
47
45
|
def curated?
|
48
|
-
|
46
|
+
_curator === self
|
49
47
|
end
|
50
48
|
|
51
49
|
# VARIABLE ACCESS -----------------------------
|
52
50
|
class << self
|
53
|
-
|
51
|
+
attr_writer :required
|
52
|
+
attr_accessor :selective_require
|
53
|
+
end
|
54
|
+
|
55
|
+
def self.required
|
56
|
+
@required ||= []
|
54
57
|
end
|
55
58
|
|
56
59
|
def self.add_accessor key
|
@@ -73,7 +76,7 @@ module Garterbelt
|
|
73
76
|
end
|
74
77
|
|
75
78
|
def self.super_required
|
76
|
-
superclass? ? superclass.required
|
79
|
+
superclass? ? superclass.required : []
|
77
80
|
end
|
78
81
|
|
79
82
|
def self.default_variables
|
@@ -87,7 +90,7 @@ module Garterbelt
|
|
87
90
|
end
|
88
91
|
|
89
92
|
args = super_required + args
|
90
|
-
self.required
|
93
|
+
self.required += args.uniq
|
91
94
|
build_accessors
|
92
95
|
required
|
93
96
|
end
|
@@ -111,7 +114,7 @@ module Garterbelt
|
|
111
114
|
# TAG HELPERS -----------------------
|
112
115
|
|
113
116
|
def add_to_buffer(renderer)
|
114
|
-
|
117
|
+
_buffer << renderer
|
115
118
|
renderer
|
116
119
|
end
|
117
120
|
|
@@ -129,10 +132,10 @@ module Garterbelt
|
|
129
132
|
end
|
130
133
|
|
131
134
|
def non_escape_tag(*args, &block)
|
132
|
-
if
|
133
|
-
|
135
|
+
if _escape
|
136
|
+
_curator._escape = false
|
134
137
|
t = block_given? ? tag(*args, &block) : tag(*args)
|
135
|
-
|
138
|
+
_curator._escape = true
|
136
139
|
t
|
137
140
|
else
|
138
141
|
block_given? ? tag(*args, &block) : tag(*args)
|
@@ -140,16 +143,16 @@ module Garterbelt
|
|
140
143
|
end
|
141
144
|
|
142
145
|
def text(content)
|
143
|
-
add_to_buffer Text.new(:view =>
|
146
|
+
add_to_buffer Text.new(:view => _curator, :content => content)
|
144
147
|
end
|
145
148
|
|
146
149
|
alias :h :text
|
147
150
|
|
148
151
|
def raw_text(content)
|
149
|
-
if
|
150
|
-
|
152
|
+
if _escape
|
153
|
+
_curator._escape = false
|
151
154
|
t = text(content)
|
152
|
-
|
155
|
+
_curator._escape = true
|
153
156
|
t
|
154
157
|
else
|
155
158
|
text(content)
|
@@ -159,11 +162,11 @@ module Garterbelt
|
|
159
162
|
alias :rawtext :raw_text
|
160
163
|
|
161
164
|
def comment_tag(content)
|
162
|
-
add_to_buffer Comment.new(:view =>
|
165
|
+
add_to_buffer Comment.new(:view => _curator, :content => content)
|
163
166
|
end
|
164
167
|
|
165
168
|
def doctype(type=:transitional)
|
166
|
-
add_to_buffer Doctype.new(:view =>
|
169
|
+
add_to_buffer Doctype.new(:view => _curator, :type => type)
|
167
170
|
end
|
168
171
|
|
169
172
|
def xml(opts={})
|
@@ -172,7 +175,7 @@ module Garterbelt
|
|
172
175
|
end
|
173
176
|
|
174
177
|
def parse_tag_arguments(type, args)
|
175
|
-
opts = {:type => type, :view =>
|
178
|
+
opts = {:type => type, :view => _curator}
|
176
179
|
if args.size == 2
|
177
180
|
opts[:content] = args.shift
|
178
181
|
opts[:attributes] = args.first
|
@@ -198,8 +201,8 @@ module Garterbelt
|
|
198
201
|
'noframes', 'noscript',
|
199
202
|
'object', 'ol', 'optgroup', 'option', 'p', 'param',
|
200
203
|
'q', 's',
|
201
|
-
'samp', '
|
202
|
-
'strong', '
|
204
|
+
'samp', 'select', 'small', 'span',
|
205
|
+
'strong', 'sub', 'sup',
|
203
206
|
'table', 'tbody', 'td', 'textarea', 'tfoot',
|
204
207
|
'th', 'thead', 'tr', 'tt', 'u', 'ul', 'var'
|
205
208
|
]
|
@@ -211,7 +214,7 @@ module Garterbelt
|
|
211
214
|
RUBY
|
212
215
|
end
|
213
216
|
|
214
|
-
NON_ESCAPE_TAGS = ['code', 'pre']
|
217
|
+
NON_ESCAPE_TAGS = ['code', 'pre', 'script', 'style']
|
215
218
|
NON_ESCAPE_TAGS.each do |type|
|
216
219
|
class_eval <<-RUBY
|
217
220
|
def #{type}(*args, &block)
|
@@ -270,18 +273,23 @@ module Garterbelt
|
|
270
273
|
|
271
274
|
def render(*args)
|
272
275
|
if args.first.is_a?(Hash)
|
273
|
-
|
274
|
-
content_method =
|
276
|
+
initialization_options = args.shift
|
277
|
+
content_method = initialization_options[:method]
|
275
278
|
else
|
276
279
|
content_method = args.shift
|
277
|
-
|
280
|
+
initialization_options = args.shift || {}
|
278
281
|
end
|
279
282
|
|
280
283
|
content_method ||= self.class.default_content_method
|
281
|
-
self.render_style =
|
284
|
+
self.render_style = initialization_options[:style] || self.class.default_render_style
|
282
285
|
|
283
286
|
self.output = "" if curated?
|
284
|
-
|
287
|
+
|
288
|
+
if block
|
289
|
+
send(content_method, &block)
|
290
|
+
else
|
291
|
+
send(content_method)
|
292
|
+
end
|
285
293
|
|
286
294
|
render_buffer
|
287
295
|
output
|
@@ -302,8 +310,8 @@ module Garterbelt
|
|
302
310
|
end
|
303
311
|
|
304
312
|
def render_buffer
|
305
|
-
array =
|
306
|
-
|
313
|
+
array = _buffer.dup
|
314
|
+
_buffer.clear
|
307
315
|
array.each do |item|
|
308
316
|
if item.respond_to?(:render)
|
309
317
|
item.render
|
@@ -321,18 +329,25 @@ module Garterbelt
|
|
321
329
|
end
|
322
330
|
|
323
331
|
def partial(*args, &block)
|
324
|
-
if (klass = args.first).is_a?(Class)
|
332
|
+
view = if (klass = args.first).is_a?(Class)
|
325
333
|
args.shift
|
326
|
-
|
327
|
-
|
334
|
+
partial_opts = args.shift || {}
|
335
|
+
available_opts = self.class.default_variables.merge(initialization_options)
|
336
|
+
opts = if klass.selective_require
|
337
|
+
klass.required.each do |key|
|
338
|
+
partial_opts[key] ||= available_opts[key]
|
339
|
+
end
|
340
|
+
partial_opts
|
328
341
|
else
|
329
|
-
|
342
|
+
available_opts.merge(partial_opts)
|
330
343
|
end
|
344
|
+
klass.new(opts)
|
331
345
|
else
|
332
|
-
|
346
|
+
args.first
|
333
347
|
end
|
334
|
-
view.
|
335
|
-
|
348
|
+
view.block = block if block
|
349
|
+
view._curator = _curator
|
350
|
+
self._buffer << view
|
336
351
|
view
|
337
352
|
end
|
338
353
|
|
@@ -375,7 +390,7 @@ module Garterbelt
|
|
375
390
|
end
|
376
391
|
|
377
392
|
def cache(key, opts={}, &block)
|
378
|
-
opts = opts.merge(:key => cache_key(key), :view =>
|
393
|
+
opts = opts.merge(:key => cache_key(key), :view => _curator)
|
379
394
|
add_to_buffer Cache.new(opts, &block)
|
380
395
|
end
|
381
396
|
end
|
data/spec/page_spec.rb
CHANGED
@@ -14,8 +14,8 @@ require 'ruby-prof'
|
|
14
14
|
# Profile the code
|
15
15
|
@view = Garterbelt::View.new
|
16
16
|
@tag = Garterbelt::ContentTag.new(:type => :p, :view => @view) do
|
17
|
-
@view.
|
18
|
-
@view.
|
17
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :span, :view => @view, :content => 'spanning')
|
18
|
+
@view._buffer << Garterbelt::Text.new(:content => ' so much time here', :view => @view)
|
19
19
|
end
|
20
20
|
|
21
21
|
result = RubyProf.profile do
|
@@ -171,13 +171,13 @@ describe Garterbelt::ContentTag do
|
|
171
171
|
before do
|
172
172
|
@b = Garterbelt::ClosedTag.new(:view => @view, :type => :hr, :attributes => {:class => :linear})
|
173
173
|
@tag.id(:foo) do
|
174
|
-
@view.
|
174
|
+
@view._buffer << @b
|
175
175
|
end
|
176
176
|
end
|
177
177
|
|
178
178
|
it 'should add the tag to the buffer' do
|
179
179
|
@tag.render
|
180
|
-
@view.
|
180
|
+
@view._buffer.should include @b
|
181
181
|
end
|
182
182
|
|
183
183
|
it 'calls render buffer on the view' do
|
data/spec/renderers/text_spec.rb
CHANGED
@@ -44,7 +44,7 @@ describe Garterbelt::Text do
|
|
44
44
|
|
45
45
|
it 'does not escape if the view is set to not escape' do
|
46
46
|
str = "<a href='/foo.com'>Foo it!</a>"
|
47
|
-
@view.
|
47
|
+
@view._escape = false
|
48
48
|
text = Garterbelt::Text.new(:view => @view, :content => str)
|
49
49
|
text.render.should include str
|
50
50
|
end
|
data/spec/support/mock_view.rb
CHANGED
@@ -1,11 +1,11 @@
|
|
1
1
|
class MockView
|
2
|
-
attr_accessor :output, :
|
2
|
+
attr_accessor :output, :_buffer, :_level, :_escape, :cache_store, :render_style
|
3
3
|
|
4
4
|
def initialize
|
5
|
-
self.
|
5
|
+
self._buffer = []
|
6
6
|
self.output = ""
|
7
|
-
self.
|
8
|
-
self.
|
7
|
+
self._level ||= 2
|
8
|
+
self._escape = true
|
9
9
|
self.render_style = :pretty
|
10
10
|
self.cache_store = Moneta::Memory.new
|
11
11
|
end
|
@@ -15,10 +15,10 @@ describe Garterbelt::View do
|
|
15
15
|
|
16
16
|
describe 'attributes' do
|
17
17
|
it 'has a tag buffer' do
|
18
|
-
@view.
|
18
|
+
@view._buffer.should == []
|
19
19
|
@tag = Garterbelt::ContentTag.new(:view => @view, :type => :hr)
|
20
|
-
@view.
|
21
|
-
@view.
|
20
|
+
@view._buffer << @tag
|
21
|
+
@view._buffer.should == [@tag]
|
22
22
|
end
|
23
23
|
|
24
24
|
describe 'output' do
|
@@ -26,30 +26,30 @@ describe Garterbelt::View do
|
|
26
26
|
@view.output.should == ""
|
27
27
|
end
|
28
28
|
|
29
|
-
it 'its output is that of the
|
30
|
-
BasicView.new(:
|
29
|
+
it 'its output is that of the _curator if the _curator is not self' do
|
30
|
+
BasicView.new(:_curator => @view).output.should === @view.output
|
31
31
|
end
|
32
32
|
end
|
33
33
|
|
34
|
-
describe '
|
35
|
-
it 'has
|
36
|
-
@view.
|
34
|
+
describe '_escape' do
|
35
|
+
it 'has _escape set to true by default' do
|
36
|
+
@view._escape.should == true
|
37
37
|
end
|
38
38
|
|
39
39
|
it 'can be set' do
|
40
|
-
@view.
|
41
|
-
@view.
|
42
|
-
BasicView.new(:
|
40
|
+
@view._escape = false
|
41
|
+
@view._escape.should == false
|
42
|
+
BasicView.new(:_escape => false)._escape.should == false
|
43
43
|
end
|
44
44
|
end
|
45
45
|
|
46
|
-
describe '
|
46
|
+
describe '_level' do
|
47
47
|
it 'is 0 by default' do
|
48
|
-
@view.
|
48
|
+
@view._level.should == 0
|
49
49
|
end
|
50
50
|
|
51
51
|
it 'can be set via initialization' do
|
52
|
-
BasicView.new(:
|
52
|
+
BasicView.new(:_level => 42)._level.should == 42
|
53
53
|
end
|
54
54
|
end
|
55
55
|
|
@@ -60,9 +60,9 @@ describe Garterbelt::View do
|
|
60
60
|
view.block.is_a?(Proc).should be_true
|
61
61
|
end
|
62
62
|
|
63
|
-
it 'saves the options' do
|
63
|
+
it 'saves the initialization options' do
|
64
64
|
view = BasicView.new(:foo => 'foo', :bar => 'bar')
|
65
|
-
view.
|
65
|
+
view.initialization_options.should == {:foo => 'foo', :bar => 'bar'}
|
66
66
|
end
|
67
67
|
|
68
68
|
it 'render_style defaults to :pretty' do
|
@@ -70,48 +70,48 @@ describe Garterbelt::View do
|
|
70
70
|
view.render_style.should == :pretty
|
71
71
|
end
|
72
72
|
|
73
|
-
describe 'setting the
|
73
|
+
describe 'setting the _curator: view responsible for displaying the rendered content' do
|
74
74
|
before do
|
75
|
-
@view.
|
75
|
+
@view._level = 42
|
76
76
|
@view.output = "foo"
|
77
|
-
@view.
|
78
|
-
@view.
|
77
|
+
@view._buffer = ["bar"]
|
78
|
+
@view._escape = false
|
79
79
|
@view.render_style = :text
|
80
|
-
@child = BasicView.new(:
|
80
|
+
@child = BasicView.new(:_curator => @view)
|
81
81
|
end
|
82
82
|
|
83
83
|
it 'is self by default' do
|
84
|
-
@view.
|
84
|
+
@view._curator.should == @view
|
85
85
|
end
|
86
86
|
|
87
87
|
it 'can be set' do
|
88
|
-
@view.
|
89
|
-
@view.
|
88
|
+
@view._curator = BasicView.new
|
89
|
+
@view._curator.should_not == @view
|
90
90
|
end
|
91
91
|
|
92
92
|
it 'can be intialized in' do
|
93
|
-
BasicView.new(:
|
93
|
+
BasicView.new(:_curator => @view)._curator.should == @view
|
94
94
|
end
|
95
95
|
|
96
96
|
describe 'resets other attributes' do
|
97
|
-
it 'sets the output to the
|
97
|
+
it 'sets the output to the _curator\'s' do
|
98
98
|
@child.output.should === @view.output
|
99
99
|
end
|
100
100
|
|
101
|
-
it 'sets the
|
102
|
-
@child.
|
103
|
-
@child.
|
101
|
+
it 'sets the _level to the _curator\'s' do
|
102
|
+
@child._level.should == @view._level
|
103
|
+
@child._level.should == 42
|
104
104
|
end
|
105
105
|
|
106
|
-
it 'sets the buffer to the
|
107
|
-
@child.
|
106
|
+
it 'sets the buffer to the _curator\'s' do
|
107
|
+
@child._buffer.should === @view._buffer
|
108
108
|
end
|
109
109
|
|
110
|
-
it 'sets the
|
111
|
-
@child.
|
110
|
+
it 'sets the _escape to the _curator\'s' do
|
111
|
+
@child._escape.should == @view._escape
|
112
112
|
end
|
113
113
|
|
114
|
-
it 'sets the render_style to the
|
114
|
+
it 'sets the render_style to the _curator\'s' do
|
115
115
|
@child.render_style.should == @view.render_style
|
116
116
|
end
|
117
117
|
end
|
@@ -124,7 +124,7 @@ describe Garterbelt::View, "Caching" do
|
|
124
124
|
@view.cache("foo_you") do
|
125
125
|
puts "bar"
|
126
126
|
end
|
127
|
-
cache = @view.
|
127
|
+
cache = @view._buffer.last
|
128
128
|
cache.is_a?(Garterbelt::Cache).should be_true
|
129
129
|
cache.key.should == 'cached_foo_you'
|
130
130
|
end
|
@@ -133,7 +133,7 @@ describe Garterbelt::View, "Caching" do
|
|
133
133
|
@view.cache("my_key", :expires_in => 24*3600) do
|
134
134
|
puts "foo"
|
135
135
|
end
|
136
|
-
cache = @view.
|
136
|
+
cache = @view._buffer.last
|
137
137
|
cache.expires_in.should == 24*3600
|
138
138
|
end
|
139
139
|
end
|
@@ -5,8 +5,8 @@ describe Garterbelt::View, 'Partials' do
|
|
5
5
|
before do
|
6
6
|
@view = Garterbelt::View.new
|
7
7
|
@view.output = "Foo You!\n"
|
8
|
-
@view.
|
9
|
-
@view.
|
8
|
+
@view._level = 3
|
9
|
+
@view._buffer = ['foo', 'bar']
|
10
10
|
end
|
11
11
|
|
12
12
|
describe 'with an instance' do
|
@@ -14,14 +14,21 @@ describe Garterbelt::View, 'Partials' do
|
|
14
14
|
@child_instance = Garterbelt::View.new
|
15
15
|
end
|
16
16
|
|
17
|
-
it 'sets the
|
18
|
-
@child_instance.should_receive(:
|
17
|
+
it 'sets the _curator of the instance to the current view' do
|
18
|
+
@child_instance.should_receive(:_curator=).with(@view)
|
19
19
|
@view.partial(@child_instance)
|
20
20
|
end
|
21
21
|
|
22
|
-
it 'adds the instance to the
|
22
|
+
it 'adds the instance to the _curator view buffer' do
|
23
23
|
@view.partial(@child_instance)
|
24
|
-
@view.
|
24
|
+
@view._buffer.should include @child_instance
|
25
|
+
end
|
26
|
+
|
27
|
+
it 'passes down the block' do
|
28
|
+
@view.partial(@child_instance) do
|
29
|
+
puts {'partial to the block'}
|
30
|
+
end
|
31
|
+
@view._buffer.last.block.is_a?(Proc).should be_true
|
25
32
|
end
|
26
33
|
end
|
27
34
|
|
@@ -41,20 +48,20 @@ describe Garterbelt::View, 'Partials' do
|
|
41
48
|
|
42
49
|
it 'adds the instance to the buffer' do
|
43
50
|
@view.partial(PartedOut, :x => '!= y?')
|
44
|
-
partial = @view.
|
51
|
+
partial = @view._buffer.last
|
45
52
|
partial.is_a?(PartedOut).should be_true
|
46
53
|
end
|
47
54
|
|
48
55
|
|
49
|
-
it 'has the
|
56
|
+
it 'has the _curator as the current view' do
|
50
57
|
@view.partial(PartedOut, :x => 'what about z?')
|
51
|
-
partial = @view.
|
52
|
-
partial.
|
58
|
+
partial = @view._buffer.last
|
59
|
+
partial._curator.should == @view
|
53
60
|
end
|
54
61
|
|
55
62
|
it 'has the correct initalization options' do
|
56
63
|
@view.partial(PartedOut, :x => '= foo')
|
57
|
-
partial = @view.
|
64
|
+
partial = @view._buffer.last
|
58
65
|
partial.x.should == '= foo'
|
59
66
|
end
|
60
67
|
|
@@ -62,9 +69,53 @@ describe Garterbelt::View, 'Partials' do
|
|
62
69
|
@view.partial(PartedOut, :x => 'not x') do
|
63
70
|
puts { 'maybe x; i don\'t know '}
|
64
71
|
end
|
65
|
-
partial = @view.
|
72
|
+
partial = @view._buffer.last
|
66
73
|
partial.block.is_a?(Proc).should be_true
|
67
74
|
end
|
75
|
+
|
76
|
+
describe 'passing down arguments' do
|
77
|
+
class Containment < Garterbelt::View
|
78
|
+
needs :x => 'find me'
|
79
|
+
def content
|
80
|
+
partial PartedOut
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
84
|
+
it 'works with defaults' do
|
85
|
+
view = Containment.new
|
86
|
+
view.content
|
87
|
+
|
88
|
+
parted = view._buffer.last
|
89
|
+
parted.is_a?(PartedOut).should be_true
|
90
|
+
parted.x.should == 'find me'
|
91
|
+
end
|
92
|
+
|
93
|
+
it 'should recieved initailialized options' do
|
94
|
+
view = Containment.new(:x => 'newer x')
|
95
|
+
view.content
|
96
|
+
|
97
|
+
parted = view._buffer.last
|
98
|
+
parted.x.should == 'newer x'
|
99
|
+
end
|
100
|
+
|
101
|
+
it 'should pass all the initialization options along' do
|
102
|
+
view = Containment.new(:y => 'two dimensions, yo!')
|
103
|
+
view.content
|
104
|
+
|
105
|
+
parted = view._buffer.last
|
106
|
+
parted.y.should == 'two dimensions, yo!'
|
107
|
+
end
|
108
|
+
|
109
|
+
it 'only passes required arguments if partial is selective' do
|
110
|
+
PartedOut.selective_require = true
|
111
|
+
view = Containment.new(:z => 'two dimensions, again')
|
112
|
+
view.content
|
113
|
+
|
114
|
+
parted = view._buffer.last
|
115
|
+
parted.x.should == 'find me'
|
116
|
+
parted.should_not respond_to :z
|
117
|
+
end
|
118
|
+
end
|
68
119
|
end
|
69
120
|
end
|
70
121
|
end
|
@@ -72,13 +72,13 @@ describe Garterbelt::View do
|
|
72
72
|
end
|
73
73
|
|
74
74
|
it 'will clear the buffer' do
|
75
|
-
@view.
|
75
|
+
@view._buffer = [:foo]
|
76
76
|
@view.render_buffer
|
77
|
-
@view.
|
77
|
+
@view._buffer.should == []
|
78
78
|
end
|
79
79
|
|
80
80
|
it 'will call render on each tag in the buffer' do
|
81
|
-
@view.
|
81
|
+
@view._buffer << @hr << @input << @img
|
82
82
|
@hr.should_receive(:render)
|
83
83
|
@input.should_receive(:render)
|
84
84
|
@img.should_receive(:render)
|
@@ -87,7 +87,7 @@ describe Garterbelt::View do
|
|
87
87
|
end
|
88
88
|
|
89
89
|
it 'will add non renderable items to the output as strings' do
|
90
|
-
@view.
|
90
|
+
@view._buffer << "foo " << :bar
|
91
91
|
@view.render_buffer
|
92
92
|
@view.output.should include 'foo bar'
|
93
93
|
end
|
@@ -95,20 +95,20 @@ describe Garterbelt::View do
|
|
95
95
|
|
96
96
|
describe 'tag nesting' do
|
97
97
|
it 'should render correctly at one layer deep' do
|
98
|
-
@view.
|
98
|
+
@view._buffer << Garterbelt::ClosedTag.new(:type => :hr, :view => @view)
|
99
99
|
@view.render.should == "<hr>\n"
|
100
100
|
end
|
101
101
|
|
102
102
|
describe 'second level' do
|
103
103
|
before do
|
104
|
-
@view.
|
105
|
-
@view.
|
104
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :p, :view => @view) do
|
105
|
+
@view._buffer << Garterbelt::ClosedTag.new(:type => :hr, :view => @view)
|
106
106
|
end
|
107
107
|
@view.render
|
108
108
|
end
|
109
109
|
|
110
110
|
it 'should leave an empty buffer' do
|
111
|
-
@view.
|
111
|
+
@view._buffer.should be_empty
|
112
112
|
end
|
113
113
|
|
114
114
|
it 'should include the content' do
|
@@ -122,12 +122,12 @@ describe Garterbelt::View do
|
|
122
122
|
|
123
123
|
describe 'multi level' do
|
124
124
|
before do
|
125
|
-
@view.
|
126
|
-
@view.
|
127
|
-
@view.
|
128
|
-
@view.
|
125
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :form, :view => @view) do
|
126
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :fieldset, :view => @view) do
|
127
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :label, :view => @view, :attributes => {:for => 'email'}) do
|
128
|
+
@view._buffer << Garterbelt::ClosedTag.new(:type => :input, :view => @view, :attributes => {:name => 'email', :type => 'text'})
|
129
129
|
end
|
130
|
-
@view.
|
130
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :input, :view => @view, :attributes => {:type => 'submit', :value => 'Login or whatever'})
|
131
131
|
end
|
132
132
|
end
|
133
133
|
@view.render
|
@@ -186,10 +186,26 @@ describe Garterbelt::View do
|
|
186
186
|
describe 'block initalized content' do
|
187
187
|
it 'has a #render_block method that renders that content' do
|
188
188
|
@view = BasicView.new do
|
189
|
-
@view.
|
189
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :p, :view => @view, :content => 'Block level p tag')
|
190
190
|
end
|
191
191
|
@view.render_block.should include "Block level p tag"
|
192
192
|
end
|
193
|
+
|
194
|
+
it 'passes the block to the content method' do
|
195
|
+
class PassItOn < Garterbelt::View
|
196
|
+
def content
|
197
|
+
p do
|
198
|
+
yield
|
199
|
+
end
|
200
|
+
end
|
201
|
+
end
|
202
|
+
|
203
|
+
@view = PassItOn.new do
|
204
|
+
@view._buffer << Garterbelt::ContentTag.new(:type => :span, :view => @view, :content => 'spanning it up!')
|
205
|
+
end
|
206
|
+
|
207
|
+
@view.render.should include "spanning it up!"
|
208
|
+
end
|
193
209
|
end
|
194
210
|
end
|
195
211
|
|
@@ -208,12 +224,12 @@ describe Garterbelt::View do
|
|
208
224
|
|
209
225
|
it 'adds it to the buffer' do
|
210
226
|
tag = @view.tag(:p, "content", {:class => 'classy'})
|
211
|
-
@view.
|
227
|
+
@view._buffer.should include tag
|
212
228
|
end
|
213
229
|
|
214
230
|
it 'works with block content' do
|
215
231
|
tag = @view.tag(:p, "content", {:class => 'classy'}) do
|
216
|
-
@view.
|
232
|
+
@view._buffer << "foo"
|
217
233
|
end
|
218
234
|
tag.content.is_a?(Proc).should be_true
|
219
235
|
end
|
@@ -233,7 +249,7 @@ describe Garterbelt::View do
|
|
233
249
|
|
234
250
|
it 'adds it to the buffer' do
|
235
251
|
tag = @view.closed_tag(:hr, :class => 'linear')
|
236
|
-
@view.
|
252
|
+
@view._buffer.should include tag
|
237
253
|
end
|
238
254
|
end
|
239
255
|
|
@@ -244,15 +260,15 @@ describe Garterbelt::View do
|
|
244
260
|
end
|
245
261
|
|
246
262
|
it 'sets and resets the escape when escape is originally set to true' do
|
247
|
-
@view.should_receive(:
|
263
|
+
@view.should_receive(:_escape=).with(false).ordered
|
248
264
|
@view.should_receive(:tag).ordered
|
249
|
-
@view.should_receive(:
|
265
|
+
@view.should_receive(:_escape=).with(true).ordered
|
250
266
|
@view.non_escape_tag(:pre, "<div>content</div>", {:class => 'classy'})
|
251
267
|
end
|
252
268
|
|
253
269
|
it 'does not set the escape when set to false' do
|
254
|
-
@view.
|
255
|
-
@view.should_not_receive(:
|
270
|
+
@view._escape = false
|
271
|
+
@view.should_not_receive(:_escape=)
|
256
272
|
@view.non_escape_tag(:pre, "<div>content</div>", {:class => 'classy'})
|
257
273
|
end
|
258
274
|
end
|
@@ -272,7 +288,7 @@ describe Garterbelt::View do
|
|
272
288
|
|
273
289
|
it 'adds the Text object to the buffer' do
|
274
290
|
@view.text("content")
|
275
|
-
text = @view.
|
291
|
+
text = @view._buffer.last
|
276
292
|
text.is_a?(Garterbelt::Text).should be_true
|
277
293
|
text.content.should == 'content'
|
278
294
|
end
|
@@ -285,15 +301,15 @@ describe Garterbelt::View do
|
|
285
301
|
end
|
286
302
|
|
287
303
|
it 'sets escape before and after for a view that is set to escape' do
|
288
|
-
@view.should_receive(:
|
304
|
+
@view.should_receive(:_escape=).with(false).ordered
|
289
305
|
@view.should_receive(:text).and_return('text')
|
290
|
-
@view.should_receive(:
|
306
|
+
@view.should_receive(:_escape=).with(true).ordered
|
291
307
|
@view.raw_text("<div>foo</div>")
|
292
308
|
end
|
293
309
|
|
294
310
|
it 'does not set escape if the view is not escaping' do
|
295
|
-
@view.
|
296
|
-
@view.should_not_receive(:
|
311
|
+
@view._escape = false
|
312
|
+
@view.should_not_receive(:_escape=)
|
297
313
|
@view.raw_text("<div>foo</div>")
|
298
314
|
end
|
299
315
|
end
|
@@ -352,7 +368,7 @@ describe Garterbelt::View do
|
|
352
368
|
|
353
369
|
it 'puts it on the buffer' do
|
354
370
|
comment = @view.comment_tag("new comment now")
|
355
|
-
@view.
|
371
|
+
@view._buffer.last.should == comment
|
356
372
|
end
|
357
373
|
end
|
358
374
|
|
@@ -363,7 +379,7 @@ describe Garterbelt::View do
|
|
363
379
|
|
364
380
|
it 'puts it on the buffer' do
|
365
381
|
doctype = @view.doctype
|
366
|
-
@view.
|
382
|
+
@view._buffer.last.should == doctype
|
367
383
|
end
|
368
384
|
end
|
369
385
|
|
@@ -371,7 +387,7 @@ describe Garterbelt::View do
|
|
371
387
|
it 'adds an xml to the buffer' do
|
372
388
|
xml = @view.xml
|
373
389
|
xml.is_a?(Garterbelt::Xml).should be_true
|
374
|
-
@view.
|
390
|
+
@view._buffer.last.should == xml
|
375
391
|
end
|
376
392
|
|
377
393
|
it 'makes a closed tag with default options' do
|
@@ -18,6 +18,10 @@ describe Garterbelt::View, 'Variables' do
|
|
18
18
|
end
|
19
19
|
|
20
20
|
describe 'class level requirements' do
|
21
|
+
it 'is an empty array by default' do
|
22
|
+
Garterbelt::View.required.should == []
|
23
|
+
end
|
24
|
+
|
21
25
|
it 'the class should store a list of required variables' do
|
22
26
|
NeedyView.required.should == [:x, :y]
|
23
27
|
SelectiveView.required.should == [:x, :y]
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: garterbelt
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 27
|
5
5
|
prerelease: false
|
6
6
|
segments:
|
7
7
|
- 0
|
8
|
+
- 1
|
8
9
|
- 0
|
9
|
-
|
10
|
-
version: 0.0.9
|
10
|
+
version: 0.1.0
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Kane Baccigalupi
|
@@ -15,7 +15,7 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date: 2011-04-
|
18
|
+
date: 2011-04-19 00:00:00 -07:00
|
19
19
|
default_executable:
|
20
20
|
dependencies:
|
21
21
|
- !ruby/object:Gem::Dependency
|