zafu 0.7.9 → 0.8.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/History.txt +8 -0
- data/lib/zafu/info.rb +1 -1
- data/lib/zafu/node_context.rb +27 -11
- data/lib/zafu/ordered_hash.rb +6 -0
- data/lib/zafu/parsing_rules.rb +19 -3
- data/lib/zafu/process/ajax.rb +29 -21
- data/lib/zafu/process/conditional.rb +24 -14
- data/lib/zafu/process/forms.rb +2 -0
- data/lib/zafu/process/html.rb +8 -1
- data/lib/zafu/process/ruby_less_processing.rb +2 -3
- data/test/mock/params.rb +5 -0
- data/test/zafu/basic.yml +16 -0
- data/zafu.gemspec +2 -2
- metadata +5 -5
data/History.txt
CHANGED
@@ -1,3 +1,11 @@
|
|
1
|
+
== 0.8.0 2011-06-15
|
2
|
+
|
3
|
+
* Enhancements
|
4
|
+
* Include with 'part' can now replace method.
|
5
|
+
* Fixed 'merge' for OrderedHash.
|
6
|
+
* Fixed dom_scope from block in each (was not using propagated dom scope).
|
7
|
+
* Added support for comments (started with '//!').
|
8
|
+
|
1
9
|
== 0.7.9 2011-05-26
|
2
10
|
|
3
11
|
* Enhancements
|
data/lib/zafu/info.rb
CHANGED
data/lib/zafu/node_context.rb
CHANGED
@@ -13,6 +13,9 @@ module Zafu
|
|
13
13
|
# it has a name or dom id defined ('main', 'related', 'list', etc).
|
14
14
|
attr_writer :dom_prefix
|
15
15
|
|
16
|
+
# This is used to force a given dom_id (in saved templates for example).
|
17
|
+
attr_accessor :saved_dom_id
|
18
|
+
|
16
19
|
# Any kind of information that the compiler might need to use (QueryBuilder query used
|
17
20
|
# to fetch the node for example).
|
18
21
|
attr_reader :opts
|
@@ -48,7 +51,9 @@ module Zafu
|
|
48
51
|
# ivar name (see #master_class).
|
49
52
|
def as_main(after_class = nil)
|
50
53
|
klass = after_class ? master_class(after_class) : single_class
|
51
|
-
self.class.new("@#{klass.to_s.underscore}", single_class)
|
54
|
+
res = self.class.new("@#{klass.to_s.underscore}", single_class, nil, :new_record => @opts[:new_record])
|
55
|
+
res.dom_prefix = self.dom_prefix
|
56
|
+
res
|
52
57
|
end
|
53
58
|
|
54
59
|
# Find the class just afer 'after_class' in the class hierarchy.
|
@@ -64,25 +69,36 @@ module Zafu
|
|
64
69
|
end
|
65
70
|
|
66
71
|
# Generate a unique DOM id for this element based on dom_scopes defined in parent contexts.
|
72
|
+
# :code option returns ruby
|
73
|
+
# :erb option returns either string content or "<%= ... %>"
|
74
|
+
# default returns something to insert in interpolated string such as '#{xxx}'
|
67
75
|
def dom_id(opts = {})
|
68
76
|
dom_prefix = opts[:dom_prefix] || self.dom_prefix
|
69
77
|
options = {:list => true, :erb => true}.merge(opts)
|
70
78
|
|
71
|
-
if options[:erb]
|
72
|
-
dom = dom_id(options.merge(:erb => false))
|
79
|
+
if options[:erb] || options[:code]
|
80
|
+
dom = dom_id(options.merge(:erb => false, :code => false))
|
81
|
+
|
73
82
|
if dom =~ /^#\{([^\{]+)\}$/
|
74
|
-
|
83
|
+
code = $1
|
75
84
|
elsif dom =~ /#\{/
|
76
|
-
"
|
85
|
+
code = "%Q{#{dom}}"
|
77
86
|
else
|
78
|
-
dom
|
87
|
+
str = dom
|
88
|
+
code = dom.inspect
|
79
89
|
end
|
80
|
-
|
81
|
-
if
|
82
|
-
|
90
|
+
|
91
|
+
if options[:code]
|
92
|
+
code
|
83
93
|
else
|
84
|
-
|
85
|
-
end
|
94
|
+
str || "<%= #{code} %>"
|
95
|
+
end
|
96
|
+
else
|
97
|
+
@saved_dom_id || (
|
98
|
+
[dom_prefix] +
|
99
|
+
dom_scopes +
|
100
|
+
(options[:list] ? [make_scope_id] : [])
|
101
|
+
).compact.uniq.join('_')
|
86
102
|
end
|
87
103
|
end
|
88
104
|
|
data/lib/zafu/ordered_hash.rb
CHANGED
data/lib/zafu/parsing_rules.rb
CHANGED
@@ -93,9 +93,10 @@ module Zafu
|
|
93
93
|
end
|
94
94
|
|
95
95
|
def extract_name
|
96
|
-
|
96
|
+
@options[:name] ||
|
97
97
|
(%w{input select textarea}.include?(@method) ? nil : @params[:name]) ||
|
98
|
-
@markup.params[:id]
|
98
|
+
@markup.params[:id] ||
|
99
|
+
@params[:id]
|
99
100
|
end
|
100
101
|
|
101
102
|
def remove_erb(text)
|
@@ -125,7 +126,12 @@ module Zafu
|
|
125
126
|
# scan rules
|
126
127
|
def scan
|
127
128
|
# puts "SCAN(#{@method}): [#{@text}]"
|
128
|
-
if @text =~
|
129
|
+
if @text =~ %r{\A([^<]*?)(\s*)//!}m
|
130
|
+
# comment
|
131
|
+
flush $1
|
132
|
+
eat $2
|
133
|
+
scan_comment
|
134
|
+
elsif @text =~ /\A([^<]*?)(^ *|)</m
|
129
135
|
flush $1
|
130
136
|
eat $2
|
131
137
|
if @text[1..1] == '/'
|
@@ -191,6 +197,16 @@ module Zafu
|
|
191
197
|
end
|
192
198
|
end
|
193
199
|
|
200
|
+
def scan_comment
|
201
|
+
if @text =~ %r{\A//!.*(\n|\Z)}
|
202
|
+
# zafu html escaped
|
203
|
+
eat $&
|
204
|
+
else
|
205
|
+
# error
|
206
|
+
flush
|
207
|
+
end
|
208
|
+
end
|
209
|
+
|
194
210
|
def scan_tag(opts={})
|
195
211
|
#puts "TAG(#{@method}): [#{@text}]"
|
196
212
|
if @text =~ /\A<r:([\w_]+\??)([^>]*?)(\/?)>/
|
data/lib/zafu/process/ajax.rb
CHANGED
@@ -8,6 +8,7 @@ module Zafu
|
|
8
8
|
|
9
9
|
# This method process a list and handles building the necessary templates for ajax 'add'.
|
10
10
|
def expand_with_finder(finder)
|
11
|
+
@context.delete(:make_form) # Do not propagate.
|
11
12
|
return super unless finder[:class].kind_of?(Array)
|
12
13
|
|
13
14
|
# reset scope
|
@@ -25,8 +26,14 @@ module Zafu
|
|
25
26
|
(edit_block && edit_block.params[:publish])
|
26
27
|
|
27
28
|
# class name for create form
|
28
|
-
|
29
|
-
|
29
|
+
if class_name = (add_block && add_block.params[:klass]) ||
|
30
|
+
(form_block && form_block.params[:klass])
|
31
|
+
unless klass = get_class(class_name)
|
32
|
+
return parser_error("Invalid class '#{class_name}'")
|
33
|
+
end
|
34
|
+
else
|
35
|
+
klass = finder[:class].first
|
36
|
+
end
|
30
37
|
|
31
38
|
if need_ajax?(each_block)
|
32
39
|
# We need to build the templates for ajax rendering.
|
@@ -35,6 +42,7 @@ module Zafu
|
|
35
42
|
# assign [] to var
|
36
43
|
out "<% if (#{var} = #{finder[:method]}) || (#{node}.#{finder[:class].first <= Comment ? "can_comment?" : "can_write?"} && #{var}=[]) %>"
|
37
44
|
# The list is not empty or we have enough rights to add new elements.
|
45
|
+
|
38
46
|
node.dom_prefix = dom_name
|
39
47
|
|
40
48
|
# New node context.
|
@@ -71,7 +79,10 @@ module Zafu
|
|
71
79
|
:saved_template => form_url(node.dom_prefix),
|
72
80
|
:klass => klass,
|
73
81
|
:make_form => each_block == form_block,
|
82
|
+
# Used to get parameters like 'publish', 'done', 'after'
|
83
|
+
:add => add_block,
|
74
84
|
:publish_after_save => publish_after_save,
|
85
|
+
:node => node.move_to("@node", klass, :new_record => true)
|
75
86
|
}
|
76
87
|
|
77
88
|
store_block(form_block, cont)
|
@@ -174,10 +185,11 @@ module Zafu
|
|
174
185
|
# TODO: show 'reply' instead of 'edit' in comments if visitor != author
|
175
186
|
block = ancestor(%w{each block})
|
176
187
|
|
177
|
-
#
|
178
|
-
# removed so
|
179
|
-
@params.delete(
|
180
|
-
@params.delete(
|
188
|
+
# These parameters are detected by r_block and set in form.
|
189
|
+
# removed so they do not polute link
|
190
|
+
@params.delete(:publish)
|
191
|
+
@params.delete(:cancel)
|
192
|
+
@params.delete(:tcancel)
|
181
193
|
|
182
194
|
link = wrap(make_link(:default_text => _('edit'), :update => block, :action => 'edit'))
|
183
195
|
|
@@ -223,16 +235,7 @@ module Zafu
|
|
223
235
|
# Expand 'add' block
|
224
236
|
out wrap("#{expand_with(:onclick=>"[\"#{node.dom_prefix}_add\", \"#{node.dom_prefix}_form\"].each(Element.toggle);#{focus}return false;")}")
|
225
237
|
|
226
|
-
|
227
|
-
unless klass = get_class(klass)
|
228
|
-
out parser_error("Invalid class '#{@context[:klass]}'")
|
229
|
-
# Clean close ERB
|
230
|
-
out "<% end -%>"
|
231
|
-
return
|
232
|
-
end
|
233
|
-
else
|
234
|
-
klass = Array(node.klass).first
|
235
|
-
end
|
238
|
+
klass = @context[:klass] || node.single_class
|
236
239
|
|
237
240
|
# New object to render form.
|
238
241
|
new_node = node.move_to("#{var}_new", klass, :new_record => true)
|
@@ -252,7 +255,10 @@ module Zafu
|
|
252
255
|
out expand_block(form_block,
|
253
256
|
# Needed in form to be able to return the result
|
254
257
|
:template_url => template_url(node.dom_prefix),
|
255
|
-
#
|
258
|
+
# Used to avoid wrong dom_id in hidden form. Should not be
|
259
|
+
# necessary but it's hard to fix when node changes a lot (drop in add).
|
260
|
+
:dom_prefix => node.dom_prefix,
|
261
|
+
# Used to add needed hidden fields in form
|
256
262
|
:in_add => true,
|
257
263
|
# Used to get parameters like 'publish' or 'klass'
|
258
264
|
:add => self,
|
@@ -279,9 +285,11 @@ module Zafu
|
|
279
285
|
def r_each
|
280
286
|
if @context[:saved_template]
|
281
287
|
# render to start a saved template
|
288
|
+
node.saved_dom_id = "\#{ndom_id(#{node})}"
|
282
289
|
node.propagate_dom_scope!
|
290
|
+
@markup.set_id(node.dom_id)
|
291
|
+
|
283
292
|
options = form_options
|
284
|
-
@markup.set_id(options[:id]) if options[:id]
|
285
293
|
@markup.set_param(:style, options[:style]) if options[:style]
|
286
294
|
|
287
295
|
out wrap(expand_with)
|
@@ -384,12 +392,12 @@ module Zafu
|
|
384
392
|
|
385
393
|
def store_block(block, cont = {})
|
386
394
|
cont, prefix = context_for_partial(cont)
|
387
|
-
# Keep dom prefix
|
388
|
-
dom_prefix = node.dom_prefix
|
389
395
|
|
390
396
|
# Create new node context
|
391
397
|
node = cont[:node].as_main(ActiveRecord::Base)
|
392
|
-
|
398
|
+
|
399
|
+
# The dom_id will be calculated from the Ajax params in the view.
|
400
|
+
node.saved_dom_id = "\#{ndom_id(#{node})}"
|
393
401
|
|
394
402
|
cont[:template_url] = template_url(node.dom_prefix)
|
395
403
|
cont[:node] = node
|
@@ -29,22 +29,28 @@ module Zafu
|
|
29
29
|
|
30
30
|
# We use 'elsif' just in case there are more then one 'else' clause
|
31
31
|
if markup = @context[:markup]
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
32
|
+
if @markup.tag.blank?
|
33
|
+
# Copy markup tag
|
34
|
+
@markup.tag = markup.tag
|
35
|
+
@markup.steal_html_params_from(@params)
|
36
|
+
markup.params.each do |k, v|
|
37
|
+
next if @markup.params[k]
|
38
|
+
@markup.set_param(k, v)
|
39
|
+
end
|
39
40
|
|
40
|
-
|
41
|
-
|
42
|
-
|
41
|
+
markup.dyn_params.each do |k, v|
|
42
|
+
next if @markup.params[k] || @markup.dyn_params[k]
|
43
|
+
@markup.set_dyn_param(k, v)
|
44
|
+
end
|
45
|
+
inner = wrap(res)
|
46
|
+
else
|
47
|
+
markup.done = false
|
48
|
+
# Wrap with both markup (ours and the else/elsif clause).
|
49
|
+
inner = markup.wrap(wrap(res))
|
43
50
|
end
|
44
|
-
|
45
|
-
out "<% elsif #{cond} %>#{wrap(res)}" # do not propagate
|
51
|
+
out "<% elsif #{cond} %>#{inner}" # do not propagate
|
46
52
|
else
|
47
|
-
|
53
|
+
#@markup.done = true # never wrap else/elsif clause
|
48
54
|
out "<% elsif #{cond} %>#{res}" # do not propagate
|
49
55
|
end
|
50
56
|
end
|
@@ -72,7 +78,11 @@ module Zafu
|
|
72
78
|
private
|
73
79
|
def get_condition
|
74
80
|
if in_tag = @params[:in]
|
75
|
-
|
81
|
+
if in_tag == 'form' && @context[:make_form]
|
82
|
+
'true'
|
83
|
+
else
|
84
|
+
ancestor(in_tag) ? 'true' : 'false'
|
85
|
+
end
|
76
86
|
else
|
77
87
|
get_attribute_or_eval(false)
|
78
88
|
end
|
data/lib/zafu/process/forms.rb
CHANGED
data/lib/zafu/process/html.rb
CHANGED
@@ -34,6 +34,13 @@ module Zafu
|
|
34
34
|
obj.markup = @markup.dup
|
35
35
|
end
|
36
36
|
@markup.tag = nil
|
37
|
+
|
38
|
+
if sub_do
|
39
|
+
obj.method = @blocks.first.method
|
40
|
+
obj.params = @blocks.first.params
|
41
|
+
elsif params[:method]
|
42
|
+
obj.method = params[:method]
|
43
|
+
end
|
37
44
|
super(obj)
|
38
45
|
end
|
39
46
|
|
@@ -111,7 +118,7 @@ module Zafu
|
|
111
118
|
end
|
112
119
|
|
113
120
|
src = @params.delete(key)
|
114
|
-
if src && src[0..
|
121
|
+
if src && src[0..7] != 'http://'
|
115
122
|
new_value = helper.send(:template_url_for_asset, :src => src, :base_path => @options[:base_path], :type => type)
|
116
123
|
@markup.params[key] = new_value.blank? ? src : new_value
|
117
124
|
end
|
@@ -33,7 +33,7 @@ module Zafu
|
|
33
33
|
|
34
34
|
rubyless_render(@method, params)
|
35
35
|
rescue RubyLess::NoMethodError => err
|
36
|
-
parser_continue("#{err.error_message} <span class='type'>#{err.method_with_arguments}</span>
|
36
|
+
parser_continue("#{err.error_message} <span class='type'>#{err.method_with_arguments}</span> (#{node.klass} context)")
|
37
37
|
rescue RubyLess::Error => err
|
38
38
|
parser_continue(err.message)
|
39
39
|
end
|
@@ -133,7 +133,7 @@ module Zafu
|
|
133
133
|
end
|
134
134
|
|
135
135
|
private
|
136
|
-
# Extract arguments from params
|
136
|
+
# Extract arguments from params (evaluates params as RubyLess strings).
|
137
137
|
def extract_from_params(*keys)
|
138
138
|
res = []
|
139
139
|
|
@@ -272,7 +272,6 @@ module Zafu
|
|
272
272
|
# Find a class or behavior based on a name. The returned class should implement
|
273
273
|
# 'safe_method_type'.
|
274
274
|
def get_class(class_name)
|
275
|
-
deb class_name
|
276
275
|
Module.const_get(class_name)
|
277
276
|
rescue
|
278
277
|
nil
|
data/test/mock/params.rb
CHANGED
data/test/zafu/basic.yml
CHANGED
@@ -13,3 +13,19 @@ empty_do:
|
|
13
13
|
do_with_escaped_quote:
|
14
14
|
src: "<li do='raw(\'blah\')'>blah</li>"
|
15
15
|
tem: "<li><%= raw(\"blah\") %></li>"
|
16
|
+
|
17
|
+
quotes_in_quotes:
|
18
|
+
src: "<r:inspect line_numbers='true' text=\"<code lang='lua'>function foo(a); print(a); end</code>\"/>"
|
19
|
+
tem: "/:text=>\"<code lang='lua'>function foo\(a\); print\(a\); end</code>\"/"
|
20
|
+
|
21
|
+
comment:
|
22
|
+
src: "<r:raw>hello</r:raw> //! This is a comment that will be removed"
|
23
|
+
tem: "<%= raw(\"hello\") %>"
|
24
|
+
|
25
|
+
line_comment:
|
26
|
+
src: "<r:raw>hello</r:raw>\n//! This is a comment that will be removed\nabc"
|
27
|
+
tem: "<%= raw(\"hello\") %>\nabc"
|
28
|
+
|
29
|
+
do_not_touch_js_comment:
|
30
|
+
src: "<r:raw>hello</r:raw> // This is a comment that will not be removed"
|
31
|
+
tem: "<%= raw(\"hello\") %> // This is a comment that will not be removed"
|
data/zafu.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{zafu}
|
8
|
-
s.version = "0.
|
8
|
+
s.version = "0.8.0"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Gaspard Bucher"]
|
12
|
-
s.date = %q{2011-
|
12
|
+
s.date = %q{2011-06-15}
|
13
13
|
s.description = %q{Provides a powerful templating language based on xhtml for rails}
|
14
14
|
s.email = %q{gaspard@teti.ch}
|
15
15
|
s.extra_rdoc_files = [
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: zafu
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 63
|
5
5
|
prerelease:
|
6
6
|
segments:
|
7
7
|
- 0
|
8
|
-
-
|
9
|
-
-
|
10
|
-
version: 0.
|
8
|
+
- 8
|
9
|
+
- 0
|
10
|
+
version: 0.8.0
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Gaspard Bucher
|
@@ -15,7 +15,7 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date: 2011-
|
18
|
+
date: 2011-06-15 00:00:00 +02:00
|
19
19
|
default_executable:
|
20
20
|
dependencies:
|
21
21
|
- !ruby/object:Gem::Dependency
|