hobo 0.7.2 → 0.7.3
Sign up to get free protection for your applications and to get access to all the features.
- data/bin/hobo +24 -7
- data/hobo_files/plugin/CHANGES.txt +501 -0
- data/hobo_files/plugin/generators/hobo/hobo_generator.rb +8 -6
- data/hobo_files/plugin/generators/hobo/templates/application.dryml +3 -0
- data/hobo_files/plugin/generators/hobo/templates/dryml-support.js +132 -0
- data/hobo_files/plugin/generators/hobo_front_controller/hobo_front_controller_generator.rb +4 -5
- data/hobo_files/plugin/generators/hobo_model_resource/hobo_model_resource_generator.rb +75 -0
- data/hobo_files/plugin/generators/hobo_model_resource/templates/controller.rb +7 -0
- data/hobo_files/plugin/generators/hobo_model_resource/templates/functional_test.rb +8 -0
- data/hobo_files/plugin/generators/hobo_model_resource/templates/helper.rb +2 -0
- data/hobo_files/plugin/generators/hobo_rapid/templates/hobo-rapid.js +30 -11
- data/hobo_files/plugin/generators/hobo_rapid/templates/themes/clean/public/stylesheets/application.css +149 -92
- data/hobo_files/plugin/generators/hobo_rapid/templates/themes/clean/public/stylesheets/rapid-ui.css +0 -48
- data/hobo_files/plugin/init.rb +45 -13
- data/hobo_files/plugin/lib/action_view_extensions/base.rb +4 -3
- data/hobo_files/plugin/lib/active_record/association_proxy.rb +18 -0
- data/hobo_files/plugin/lib/active_record/association_reflection.rb +5 -0
- data/hobo_files/plugin/lib/active_record/has_many_association.rb +7 -11
- data/hobo_files/plugin/lib/active_record/has_many_through_association.rb +8 -0
- data/hobo_files/plugin/lib/extensions/test_case.rb +1 -1
- data/hobo_files/plugin/lib/hobo.rb +38 -60
- data/hobo_files/plugin/lib/hobo/authentication_support.rb +1 -1
- data/hobo_files/plugin/lib/hobo/bundle.rb +131 -34
- data/hobo_files/plugin/lib/hobo/composite_model.rb +1 -1
- data/hobo_files/plugin/lib/hobo/controller.rb +7 -8
- data/hobo_files/plugin/lib/hobo/dev_controller.rb +21 -0
- data/hobo_files/plugin/lib/hobo/dryml/dryml_builder.rb +14 -8
- data/hobo_files/plugin/lib/hobo/dryml/dryml_support_controller.rb +13 -0
- data/hobo_files/plugin/lib/hobo/dryml/taglib.rb +6 -7
- data/hobo_files/plugin/lib/hobo/dryml/template.rb +207 -73
- data/hobo_files/plugin/lib/hobo/dryml/template_environment.rb +67 -55
- data/hobo_files/plugin/lib/hobo/dryml/template_handler.rb +53 -3
- data/hobo_files/plugin/lib/hobo/hobo_helper.rb +75 -107
- data/hobo_files/plugin/lib/hobo/model.rb +236 -429
- data/hobo_files/plugin/lib/hobo/model_controller.rb +277 -437
- data/hobo_files/plugin/lib/hobo/model_router.rb +62 -29
- data/hobo_files/plugin/lib/hobo/rapid_helper.rb +48 -9
- data/hobo_files/plugin/lib/hobo/scopes.rb +98 -0
- data/hobo_files/plugin/lib/hobo/scopes/association_proxy_extensions.rb +31 -0
- data/hobo_files/plugin/lib/hobo/scopes/automatic_scopes.rb +282 -0
- data/hobo_files/plugin/lib/hobo/scopes/defined_scope_proxy_extender.rb +88 -0
- data/hobo_files/plugin/lib/hobo/scopes/scope_reflection.rb +18 -0
- data/hobo_files/plugin/lib/hobo/scopes/scoped_proxy.rb +59 -0
- data/hobo_files/plugin/lib/hobo/undefined.rb +2 -0
- data/hobo_files/plugin/lib/hobo/user.rb +31 -14
- data/hobo_files/plugin/lib/hobo/user_controller.rb +41 -27
- data/hobo_files/plugin/taglibs/core.dryml +9 -11
- data/hobo_files/plugin/taglibs/rapid.dryml +51 -108
- data/hobo_files/plugin/taglibs/rapid_editing.dryml +25 -25
- data/hobo_files/plugin/taglibs/rapid_forms.dryml +111 -79
- data/hobo_files/plugin/taglibs/rapid_generics.dryml +74 -0
- data/hobo_files/plugin/taglibs/rapid_navigation.dryml +23 -21
- data/hobo_files/plugin/taglibs/rapid_pages.dryml +83 -169
- data/hobo_files/plugin/taglibs/rapid_plus.dryml +16 -2
- data/hobo_files/plugin/taglibs/rapid_support.dryml +3 -3
- data/hobo_files/plugin/taglibs/rapid_user_pages.dryml +104 -0
- metadata +60 -55
- data/hobo_files/plugin/generators/hobo_migration/hobo_migration_generator.rb +0 -276
- data/hobo_files/plugin/generators/hobo_migration/templates/migration.rb +0 -9
- data/hobo_files/plugin/lib/active_record/table_definition.rb +0 -34
- data/hobo_files/plugin/lib/extensions.rb +0 -375
- data/hobo_files/plugin/lib/hobo/email_address.rb +0 -12
- data/hobo_files/plugin/lib/hobo/enum_string.rb +0 -50
- data/hobo_files/plugin/lib/hobo/field_declaration_dsl.rb +0 -43
- data/hobo_files/plugin/lib/hobo/field_spec.rb +0 -68
- data/hobo_files/plugin/lib/hobo/html_string.rb +0 -7
- data/hobo_files/plugin/lib/hobo/lazy_hash.rb +0 -40
- data/hobo_files/plugin/lib/hobo/markdown_string.rb +0 -11
- data/hobo_files/plugin/lib/hobo/migrations.rb +0 -12
- data/hobo_files/plugin/lib/hobo/model_queries.rb +0 -117
- data/hobo_files/plugin/lib/hobo/password_string.rb +0 -7
- data/hobo_files/plugin/lib/hobo/percentage.rb +0 -14
- data/hobo_files/plugin/lib/hobo/predicate_dispatch.rb +0 -78
- data/hobo_files/plugin/lib/hobo/proc_binding.rb +0 -32
- data/hobo_files/plugin/lib/hobo/text.rb +0 -3
- data/hobo_files/plugin/lib/hobo/textile_string.rb +0 -25
- data/hobo_files/plugin/lib/hobo/where_fragment.rb +0 -28
@@ -87,12 +87,10 @@ module Hobo
|
|
87
87
|
page << renderer.part_contexts_storage if renderer
|
88
88
|
end
|
89
89
|
end
|
90
|
-
|
91
|
-
|
92
|
-
def
|
93
|
-
|
94
|
-
text = Hobo::Dryml.render_tag(@template, tag, options)
|
95
|
-
text && render({:text => text, :layout => false }.merge(render_options))
|
90
|
+
|
91
|
+
|
92
|
+
def dryml_context
|
93
|
+
@this
|
96
94
|
end
|
97
95
|
|
98
96
|
|
@@ -111,11 +109,12 @@ module Hobo
|
|
111
109
|
|
112
110
|
|
113
111
|
def site_search(query)
|
114
|
-
results = Hobo.find_by_search(query).select
|
112
|
+
results = Hobo.find_by_search(query).select{|r| Hobo.can_view?(current_user, r, nil)}
|
115
113
|
if results.empty?
|
116
114
|
render :text => "<p>Your search returned no matches.</p>"
|
117
115
|
else
|
118
|
-
|
116
|
+
# TODO: call one tag that renders all the search results with headings for each model
|
117
|
+
render_tags(results.map {|r|r.last}.flatten, :search_card, :for_type => true)
|
119
118
|
end
|
120
119
|
end
|
121
120
|
|
@@ -0,0 +1,21 @@
|
|
1
|
+
class Hobo::DevController < ActionController::Base
|
2
|
+
|
3
|
+
hobo_controller
|
4
|
+
|
5
|
+
before_filter :developer_modes_only
|
6
|
+
|
7
|
+
def set_current_user
|
8
|
+
model = params[:model] || Hobo::User.default_user_model
|
9
|
+
self.current_user = params[:name] ? model[params[:name]] : model.find(params[:id])
|
10
|
+
redirect_to(request.env["HTTP_REFERER"] ? :back : home_page)
|
11
|
+
end
|
12
|
+
|
13
|
+
private
|
14
|
+
|
15
|
+
def developer_modes_only
|
16
|
+
# Belt and braces. In addition to this check, the routes only get
|
17
|
+
# defined when developer_features? is true
|
18
|
+
render :text => "Permission Denied", :status => 403 unless Hobo.developer_features?
|
19
|
+
end
|
20
|
+
|
21
|
+
end
|
@@ -2,13 +2,17 @@ module Hobo::Dryml
|
|
2
2
|
|
3
3
|
class DRYMLBuilder
|
4
4
|
|
5
|
-
def initialize(
|
6
|
-
@
|
5
|
+
def initialize(template)
|
6
|
+
@template = template
|
7
7
|
@build_instructions = Array.new
|
8
8
|
@part_names = []
|
9
9
|
end
|
10
10
|
|
11
|
-
attr_reader :
|
11
|
+
attr_reader :template
|
12
|
+
|
13
|
+
def template_path
|
14
|
+
template.template_path
|
15
|
+
end
|
12
16
|
|
13
17
|
|
14
18
|
def set_environment(environment)
|
@@ -34,7 +38,7 @@ module Hobo::Dryml
|
|
34
38
|
|
35
39
|
def add_part(name, src, line_num)
|
36
40
|
raise DrymlException.new("duplicate part: #{name}", template_path, line_num) if name.in?(@part_names)
|
37
|
-
add_build_instruction(:
|
41
|
+
add_build_instruction(:def, :src => src, :line_num => line_num)
|
38
42
|
@part_names << name
|
39
43
|
end
|
40
44
|
|
@@ -73,9 +77,6 @@ module Hobo::Dryml
|
|
73
77
|
src = erb_process(instruction[:src])
|
74
78
|
@environment.class_eval(src, template_path, instruction[:line_num])
|
75
79
|
|
76
|
-
when :part
|
77
|
-
@environment.class_eval(erb_process(instruction[:src]), template_path, instruction[:line_num])
|
78
|
-
|
79
80
|
when :render_page
|
80
81
|
method_src = render_page_source(erb_process(instruction[:src]), local_names)
|
81
82
|
@environment.compiled_local_names = local_names
|
@@ -107,7 +108,12 @@ module Hobo::Dryml
|
|
107
108
|
import_module(options[:module].constantize, options[:as])
|
108
109
|
else
|
109
110
|
template_dir = File.dirname(template_path)
|
110
|
-
|
111
|
+
options = options.merge(:template_dir => template_dir)
|
112
|
+
|
113
|
+
# Pass on the current bundle, if there is one, to the sub-taglib
|
114
|
+
options[:bundle] = template.bundle.name unless template.bundle.nil? || options[:bundle] || options[:plugin]
|
115
|
+
|
116
|
+
taglib = Taglib.get(options)
|
111
117
|
taglib.import_into(@environment, options[:as])
|
112
118
|
end
|
113
119
|
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
class Hobo::Dryml::DrymlSupportController < ActionController::Base
|
2
|
+
|
3
|
+
def edit_source
|
4
|
+
dryml_editor = ENV['DRYML_EDITOR']
|
5
|
+
if dryml_editor
|
6
|
+
file = File.join(RAILS_ROOT, params[:file])
|
7
|
+
command = dryml_editor.sub(":file", file).sub(":line", params[:line])
|
8
|
+
system(command)
|
9
|
+
end
|
10
|
+
render :nothing => true
|
11
|
+
end
|
12
|
+
|
13
|
+
end
|
@@ -14,10 +14,9 @@ module Hobo
|
|
14
14
|
taglib.reload
|
15
15
|
else
|
16
16
|
src_file = taglib_filename(options)
|
17
|
-
|
18
|
-
Bundle.bundles[bundle]._?.renames)
|
17
|
+
bundle = options[:bundle] && Bundle.bundles[options[:bundle]]
|
19
18
|
|
20
|
-
taglib = Taglib.new(src_file,
|
19
|
+
taglib = Taglib.new(src_file, bundle)
|
21
20
|
@cache[options] = taglib
|
22
21
|
end
|
23
22
|
taglib
|
@@ -38,7 +37,7 @@ module Hobo
|
|
38
37
|
elsif options[:src] =~ /\//
|
39
38
|
"app/views"
|
40
39
|
else
|
41
|
-
options[:template_dir]
|
40
|
+
options[:template_dir].gsub(/^\//, "") # remove leading / if there is one
|
42
41
|
end
|
43
42
|
|
44
43
|
filename = "#{RAILS_ROOT}/#{base}/#{options[:src]}.dryml"
|
@@ -48,9 +47,9 @@ module Hobo
|
|
48
47
|
|
49
48
|
end
|
50
49
|
|
51
|
-
def initialize(src_file,
|
50
|
+
def initialize(src_file, bundle)
|
52
51
|
@src_file = src_file
|
53
|
-
@
|
52
|
+
@bundle = bundle
|
54
53
|
load
|
55
54
|
end
|
56
55
|
|
@@ -84,7 +83,7 @@ module Hobo
|
|
84
83
|
end
|
85
84
|
|
86
85
|
end
|
87
|
-
template = Template.new(File.read(@src_file), @module, @src_file, @
|
86
|
+
template = Template.new(File.read(@src_file), @module, @src_file, @bundle)
|
88
87
|
template.compile([], [])
|
89
88
|
@last_load_time = File.mtime(@src_file)
|
90
89
|
end
|
@@ -12,6 +12,8 @@ module Hobo::Dryml
|
|
12
12
|
|
13
13
|
CODE_ATTRIBUTE_CHAR = "&"
|
14
14
|
|
15
|
+
NO_METADATA_TAGS = %w(doctype if else unless repeat do with name type-name)
|
16
|
+
|
15
17
|
SPECIAL_ATTRIBUTES = %w(param merge merge-params merge-attrs
|
16
18
|
for-type
|
17
19
|
if unless repeat
|
@@ -28,19 +30,19 @@ module Hobo::Dryml
|
|
28
30
|
end
|
29
31
|
end
|
30
32
|
|
31
|
-
def initialize(src, environment, template_path,
|
33
|
+
def initialize(src, environment, template_path, bundle=nil)
|
32
34
|
@src = src
|
33
35
|
@environment = environment # a class or a module
|
34
36
|
@template_path = template_path.sub(/^#{Regexp.escape(RAILS_ROOT)}/, "")
|
35
|
-
@
|
37
|
+
@bundle = bundle
|
36
38
|
|
37
|
-
@builder = Template.build_cache[@template_path] || DRYMLBuilder.new(
|
39
|
+
@builder = Template.build_cache[@template_path] || DRYMLBuilder.new(self)
|
38
40
|
@builder.set_environment(environment)
|
39
41
|
|
40
42
|
@last_element = nil
|
41
43
|
end
|
42
44
|
|
43
|
-
attr_reader :tags, :template_path, :
|
45
|
+
attr_reader :tags, :template_path, :bundle
|
44
46
|
|
45
47
|
def compile(local_names=[], auto_taglibs=[])
|
46
48
|
now = Time.now
|
@@ -74,6 +76,7 @@ module Hobo::Dryml
|
|
74
76
|
|
75
77
|
def create_render_page_method
|
76
78
|
erb_src = process_src
|
79
|
+
|
77
80
|
@builder.add_build_instruction(:render_page, :src => erb_src, :line_num => 1)
|
78
81
|
end
|
79
82
|
|
@@ -127,7 +130,7 @@ module Hobo::Dryml
|
|
127
130
|
REXML::Comment::START + node.to_s + REXML::Comment::STOP
|
128
131
|
|
129
132
|
when REXML::Text
|
130
|
-
node.to_s
|
133
|
+
strip_suppressed_whiteaspace(node.to_s)
|
131
134
|
|
132
135
|
when REXML::Element
|
133
136
|
element_to_erb(node)
|
@@ -135,6 +138,11 @@ module Hobo::Dryml
|
|
135
138
|
end
|
136
139
|
|
137
140
|
|
141
|
+
def strip_suppressed_whiteaspace(s)
|
142
|
+
s # s.gsub(/ -(\s*\n\s*)/, '<% \1 %>')
|
143
|
+
end
|
144
|
+
|
145
|
+
|
138
146
|
def element_to_erb(el)
|
139
147
|
dryml_exception("old-style parameter tag (<#{el.name}>)", el) if el.name.starts_with?(":")
|
140
148
|
|
@@ -194,7 +202,7 @@ module Hobo::Dryml
|
|
194
202
|
|
195
203
|
def set_element(el)
|
196
204
|
assigns = el.attributes.map do |name, value|
|
197
|
-
dryml_exception(
|
205
|
+
dryml_exception("invalid name in <set>", el) unless name =~ /^#{DRYML_NAME}(\.#{DRYML_NAME})*$/
|
198
206
|
"#{ruby_name name} = #{attribute_to_ruby(value)}; "
|
199
207
|
end.join
|
200
208
|
code = apply_control_attributes("begin; #{assigns}; end", el)
|
@@ -204,7 +212,7 @@ module Hobo::Dryml
|
|
204
212
|
|
205
213
|
def set_scoped_element(el)
|
206
214
|
assigns = el.attributes.map do |name, value|
|
207
|
-
dryml_exception(
|
215
|
+
dryml_exception("invalid name in <set-scoped>", el) unless name =~ DRYML_NAME_RX
|
208
216
|
"scope[:#{ruby_name name}] = #{attribute_to_ruby(value)}; "
|
209
217
|
end.join
|
210
218
|
"<% scope.new_scope { #{assigns}#{tag_newlines(el)} %>#{children_to_erb(el)}<% } %>"
|
@@ -214,7 +222,7 @@ module Hobo::Dryml
|
|
214
222
|
def declared_attributes(def_element)
|
215
223
|
attrspec = def_element.attributes["attrs"]
|
216
224
|
attr_names = attrspec ? attrspec.split(/\s*,\s*/).map{ |n| n.underscore.to_sym } : []
|
217
|
-
invalids = attr_names & ([:with, :field, :this] + SPECIAL_ATTRIBUTES
|
225
|
+
invalids = attr_names & ([:with, :field, :this] + SPECIAL_ATTRIBUTES.*.to_sym)
|
218
226
|
dryml_exception("invalid attrs in def: #{invalids * ', '}", def_element) unless invalids.empty?
|
219
227
|
attr_names
|
220
228
|
end
|
@@ -243,11 +251,10 @@ module Hobo::Dryml
|
|
243
251
|
unsafe_name = el.attributes["tag"]
|
244
252
|
name = Hobo::Dryml.unreserve(unsafe_name)
|
245
253
|
if (for_type = el.attributes['for'])
|
246
|
-
type_name =
|
247
|
-
when /^[a-z]/
|
254
|
+
type_name = if defined?(HoboFields) && for_type =~ /^[a-z]/
|
248
255
|
# It's a symbolic type name - look up the Ruby type name
|
249
|
-
|
250
|
-
|
256
|
+
HoboFields.to_class(for_type).name
|
257
|
+
elsif for_type =~ /^_.*_$/
|
251
258
|
rename_class(for_type)
|
252
259
|
else
|
253
260
|
for_type
|
@@ -257,13 +264,8 @@ module Hobo::Dryml
|
|
257
264
|
unsafe_name += suffix
|
258
265
|
end
|
259
266
|
|
260
|
-
|
261
|
-
|
262
|
-
# disambiguate local variables as a workaround for the broken
|
263
|
-
# scope semantics of Ruby 1.8.
|
264
|
-
old_def_name = @def_name
|
265
|
-
@def_name = @def_name ? "#{@def_name}_#{unsafe_name}" : unsafe_name
|
266
|
-
|
267
|
+
@def_element = el
|
268
|
+
|
267
269
|
alias_of = el.attributes['alias-of']
|
268
270
|
extend_with = el.attributes['extend-with']
|
269
271
|
|
@@ -272,7 +274,8 @@ module Hobo::Dryml
|
|
272
274
|
|
273
275
|
|
274
276
|
@builder.add_build_instruction(:alias_method,
|
275
|
-
:new => ruby_name(name).to_sym,
|
277
|
+
:new => ruby_name(name).to_sym,
|
278
|
+
:old => ruby_name(Hobo::Dryml.unreserve(alias_of)).to_sym) if alias_of
|
276
279
|
|
277
280
|
res = if alias_of
|
278
281
|
"<% #{tag_newlines(el)} %>"
|
@@ -293,7 +296,7 @@ module Hobo::Dryml
|
|
293
296
|
# keep line numbers matching up
|
294
297
|
"<% #{"\n" * src.count("\n")} %>"
|
295
298
|
end
|
296
|
-
@
|
299
|
+
@def_element = nil
|
297
300
|
res
|
298
301
|
end
|
299
302
|
|
@@ -332,13 +335,52 @@ module Hobo::Dryml
|
|
332
335
|
"#{start} " +
|
333
336
|
# reproduce any line breaks in the start-tag so that line numbers are preserved
|
334
337
|
tag_newlines(el) + "%>" +
|
335
|
-
children_to_erb(el) +
|
338
|
+
wrap_tag_method_body_with_metadata(children_to_erb(el)) +
|
336
339
|
"<% _erbout; end"
|
337
340
|
end
|
338
341
|
|
342
|
+
|
343
|
+
def wrap_source_with_metadata(content, kind, name, *args)
|
344
|
+
if (!include_source_metadata) || name.in?(NO_METADATA_TAGS)
|
345
|
+
content
|
346
|
+
else
|
347
|
+
metadata = [kind, name] + args + [@template_path]
|
348
|
+
"<!--[DRYML|#{metadata * '|'}[-->" + content + "<!--]DRYML]-->"
|
349
|
+
end
|
350
|
+
end
|
351
|
+
|
352
|
+
|
353
|
+
def wrap_tag_method_body_with_metadata(content)
|
354
|
+
name = @def_element.attributes['tag']
|
355
|
+
extend = @def_element.attributes['extend-with']
|
356
|
+
for_ = @def_element.attributes['for']
|
357
|
+
name = extend ? "#{name}-with-#{extend}" : name
|
358
|
+
name += " for #{for_}" if for_
|
359
|
+
wrap_source_with_metadata(content, "def", name, element_line_num(@def_element))
|
360
|
+
end
|
361
|
+
|
362
|
+
|
363
|
+
def wrap_tag_call_with_metadata(el, content)
|
364
|
+
name = el.expanded_name
|
365
|
+
param = el.attributes['param']
|
366
|
+
|
367
|
+
if param == "&true"
|
368
|
+
name += " param"
|
369
|
+
elsif param
|
370
|
+
name += " param='#{param}'"
|
371
|
+
end
|
372
|
+
|
373
|
+
wrap_source_with_metadata(content, "call", name, element_line_num(el))
|
374
|
+
end
|
375
|
+
|
339
376
|
|
340
|
-
def param_content_element(
|
341
|
-
name =
|
377
|
+
def param_content_element(name_or_el)
|
378
|
+
name = if name_or_el.is_a?(String)
|
379
|
+
name_or_el
|
380
|
+
else
|
381
|
+
el = name_or_el
|
382
|
+
el.attributes['for'] || @containing_tag_name
|
383
|
+
end
|
342
384
|
local_name = param_content_local_name(name)
|
343
385
|
"<%= #{local_name} && #{local_name}.call %>"
|
344
386
|
end
|
@@ -346,10 +388,19 @@ module Hobo::Dryml
|
|
346
388
|
|
347
389
|
def part_element(el, content)
|
348
390
|
require_attribute(el, "part", DRYML_NAME_RX)
|
391
|
+
|
392
|
+
if contains_param?(el)
|
393
|
+
delegated_part_element(el, content)
|
394
|
+
else
|
395
|
+
simple_part_element(el, content)
|
396
|
+
end
|
397
|
+
end
|
398
|
+
|
399
|
+
|
400
|
+
def simple_part_element(el, content)
|
349
401
|
part_name = el.attributes['part']
|
350
402
|
dom_id = el.attributes['id'] || part_name
|
351
403
|
part_name = ruby_name(part_name)
|
352
|
-
|
353
404
|
part_locals = el.attributes["part-locals"]
|
354
405
|
|
355
406
|
part_src = "<% def #{part_name}_part(#{part_locals._?.gsub('@', '')}) #{tag_newlines(el)}; new_context do %>" +
|
@@ -363,6 +414,22 @@ module Hobo::Dryml
|
|
363
414
|
end
|
364
415
|
|
365
416
|
|
417
|
+
def delegated_part_element(el, content)
|
418
|
+
# TODO
|
419
|
+
end
|
420
|
+
|
421
|
+
|
422
|
+
def contains_param?(el)
|
423
|
+
# TODO
|
424
|
+
false
|
425
|
+
end
|
426
|
+
|
427
|
+
|
428
|
+
def part_delegate_tag_name(el)
|
429
|
+
"#{@def_name}_#{el.attributes['part']}__part_delegate"
|
430
|
+
end
|
431
|
+
|
432
|
+
|
366
433
|
def get_param_name(el)
|
367
434
|
param_name = el.attributes["param"]
|
368
435
|
|
@@ -391,8 +458,8 @@ module Hobo::Dryml
|
|
391
458
|
'this_type'
|
392
459
|
elsif t =~ /^[A-Z]/
|
393
460
|
t
|
394
|
-
elsif t =~ /^[a-z]/
|
395
|
-
"Hobo.
|
461
|
+
elsif t =~ /^[a-z]/ && defined? HoboFields.to_class
|
462
|
+
"Hobo.to_class(:#{t})"
|
396
463
|
elsif is_code_attribute?(t)
|
397
464
|
t[1..-1]
|
398
465
|
else
|
@@ -431,14 +498,21 @@ module Hobo::Dryml
|
|
431
498
|
elsif (call_type = polymorphic_call_type(el))
|
432
499
|
"send(find_polymorphic_tag(:#{ruby_name name}, #{call_type}), #{attributes}, #{parameters})"
|
433
500
|
elsif attributes == "{}" && parameters == "{}"
|
434
|
-
|
501
|
+
if name =~ /^[A-Z]/
|
502
|
+
# it's a tag with a cap name - not a local
|
503
|
+
"#{ruby_name name}()"
|
504
|
+
else
|
505
|
+
# could be a tag or a local variable
|
506
|
+
"#{ruby_name name}.to_s"
|
507
|
+
end
|
435
508
|
else
|
436
509
|
"#{ruby_name name}(#{attributes}, #{parameters})"
|
437
510
|
end
|
438
511
|
end
|
439
512
|
|
440
513
|
call = apply_control_attributes(call, el)
|
441
|
-
maybe_make_part_call(el, "<% _output(#{call}) %>")
|
514
|
+
call = maybe_make_part_call(el, "<% _output(#{call}) %>")
|
515
|
+
wrap_tag_call_with_metadata(el, call)
|
442
516
|
end
|
443
517
|
|
444
518
|
|
@@ -449,29 +523,20 @@ module Hobo::Dryml
|
|
449
523
|
end
|
450
524
|
|
451
525
|
|
452
|
-
def parameter_tags_hash(el)
|
526
|
+
def parameter_tags_hash(el, containing_tag_name=nil)
|
453
527
|
call_type = nil
|
454
528
|
|
529
|
+
metadata_name = containing_tag_name || el.expanded_name
|
530
|
+
|
455
531
|
param_items = el.map do |node|
|
456
532
|
case node
|
457
533
|
when REXML::Text
|
458
534
|
text = node.to_s
|
459
|
-
|
460
|
-
|
461
|
-
|
462
|
-
text
|
463
|
-
else
|
464
|
-
case call_type
|
465
|
-
when nil
|
466
|
-
call_type = :default_param_only
|
467
|
-
text
|
468
|
-
when :default_param_only
|
469
|
-
text
|
470
|
-
when :named_params
|
471
|
-
dryml_exception("mixed content and parameter tags", el)
|
472
|
-
end
|
535
|
+
unless text.blank?
|
536
|
+
dryml_exception("mixed content and parameter tags", el) if call_type == :named_params
|
537
|
+
call_type = :default_param_only
|
473
538
|
end
|
474
|
-
|
539
|
+
text
|
475
540
|
when REXML::Element
|
476
541
|
e = node
|
477
542
|
is_parameter_tag = e.parameter_tag?
|
@@ -487,19 +552,14 @@ module Hobo::Dryml
|
|
487
552
|
end
|
488
553
|
|
489
554
|
if is_parameter_tag
|
490
|
-
|
491
|
-
if param_name
|
492
|
-
":#{ruby_name e.name} => merge_tag_parameter(#{param_proc(e)}, all_parameters[:#{param_name}]), "
|
493
|
-
else
|
494
|
-
":#{ruby_name e.name} => #{param_proc(e)}, "
|
495
|
-
end
|
555
|
+
parameter_tag_hash_item(e, metadata_name) + ", "
|
496
556
|
end
|
497
557
|
end
|
498
558
|
end.join
|
499
559
|
|
500
|
-
if call_type == :default_param_only
|
560
|
+
if call_type == :default_param_only || (el.children.empty? && el.has_end_tag?)
|
501
561
|
with_containing_tag_name(el) do
|
502
|
-
param_items = " :default => #{default_param_proc(el)}, "
|
562
|
+
param_items = " :default => #{default_param_proc(el, containing_tag_name)}, "
|
503
563
|
end
|
504
564
|
end
|
505
565
|
|
@@ -510,17 +570,72 @@ module Hobo::Dryml
|
|
510
570
|
elsif is_code_attribute?(merge_params)
|
511
571
|
merge_params[1..-1]
|
512
572
|
else
|
513
|
-
|
573
|
+
merge_param_names = merge_params.split(/\s*,\s*/).*.gsub("-", "_")
|
574
|
+
"all_parameters & #{merge_param_names.inspect}"
|
514
575
|
end
|
515
576
|
"{#{param_items}}.merge((#{extra_params}) || {})"
|
516
577
|
else
|
517
578
|
"{#{param_items}}"
|
518
579
|
end
|
519
580
|
end
|
581
|
+
|
582
|
+
|
583
|
+
def parameter_tag_hash_item(el, metadata_name)
|
584
|
+
if el.name =~ /^before-/
|
585
|
+
before_parameter_tag_hash_item(el, metadata_name)
|
586
|
+
elsif el.name =~ /^after-/
|
587
|
+
after_parameter_tag_hash_item(el, metadata_name)
|
588
|
+
elsif el.name =~ /^prepend-/
|
589
|
+
prepend_parameter_tag_hash_item(el, metadata_name)
|
590
|
+
elsif el.name =~ /^append-/
|
591
|
+
append_parameter_tag_hash_item(el, metadata_name)
|
592
|
+
elsif (param_name = get_param_name(el))
|
593
|
+
":#{ruby_name el.name} => merge_tag_parameter(#{param_proc(el, metadata_name)}, all_parameters[:#{param_name}])"
|
594
|
+
else
|
595
|
+
":#{ruby_name el.name} => #{param_proc(el, metadata_name)}"
|
596
|
+
end
|
597
|
+
end
|
598
|
+
|
599
|
+
|
600
|
+
def before_parameter_tag_hash_item(el, metadata_name)
|
601
|
+
param_name = get_param_name(el)
|
602
|
+
dryml_exception("param declaration not allowed on 'before' parameters", el) if param_name
|
603
|
+
name = el.name.sub(/^before-/, "")
|
604
|
+
content = children_to_erb(el) + "<% _output(#{param_restore_local_name(name)}.call({}, {})) %>"
|
605
|
+
":#{ruby_name name} => #{replace_parameter_proc(el, metadata_name, content)}"
|
606
|
+
end
|
520
607
|
|
521
608
|
|
522
|
-
def
|
523
|
-
|
609
|
+
def after_parameter_tag_hash_item(el, metadata_name)
|
610
|
+
param_name = get_param_name(el)
|
611
|
+
dryml_exception("param declaration not allowed on 'after' parameters", el) if param_name
|
612
|
+
name = el.name.sub(/^after-/, "")
|
613
|
+
content = "<% _output(#{param_restore_local_name(name)}.call({}, {})) %>" + children_to_erb(el)
|
614
|
+
":#{ruby_name name} => #{replace_parameter_proc(el, metadata_name, content)}"
|
615
|
+
end
|
616
|
+
|
617
|
+
|
618
|
+
def append_parameter_tag_hash_item(el, metadata_name)
|
619
|
+
name = el.name.sub(/^append-/, "")
|
620
|
+
":#{ruby_name name} => proc { [{}, { :default => proc { |#{param_content_local_name(name)}| new_context { %>" +
|
621
|
+
param_content_element(name) + children_to_erb(el) +
|
622
|
+
"<% } } } ] }"
|
623
|
+
end
|
624
|
+
|
625
|
+
|
626
|
+
def prepend_parameter_tag_hash_item(el, metadata_name)
|
627
|
+
name = el.name.sub(/^prepend-/, "")
|
628
|
+
":#{ruby_name name} => proc { [{}, { :default => proc { |#{param_content_local_name(name)}| new_context { %>" +
|
629
|
+
children_to_erb(el) + param_content_element(name) +
|
630
|
+
"<% } } } ] }"
|
631
|
+
end
|
632
|
+
|
633
|
+
|
634
|
+
def default_param_proc(el, containing_param_name=nil)
|
635
|
+
content = children_to_erb(el)
|
636
|
+
content = wrap_source_with_metadata(content, "param", containing_param_name,
|
637
|
+
element_line_num(el)) if containing_param_name
|
638
|
+
"proc { |#{param_content_local_name(el.dryml_name)}| new_context { %>#{content}<% } #{tag_newlines(el)}}"
|
524
639
|
end
|
525
640
|
|
526
641
|
|
@@ -529,26 +644,39 @@ module Hobo::Dryml
|
|
529
644
|
end
|
530
645
|
|
531
646
|
|
532
|
-
def
|
533
|
-
|
647
|
+
def wrap_replace_parameter(el, name)
|
648
|
+
wrap_source_with_metadata(children_to_erb(el), "replace", name, element_line_num(el))
|
649
|
+
end
|
650
|
+
|
651
|
+
|
652
|
+
def param_proc(el, metadata_name_prefix)
|
653
|
+
metadata_name = "#{metadata_name_prefix}><#{el.name}"
|
654
|
+
|
534
655
|
nl = tag_newlines(el)
|
535
656
|
|
536
657
|
if (repl = el.attribute("replace"))
|
537
658
|
dryml_exception("replace attribute must not have a value", el) if repl.has_rhs?
|
538
659
|
dryml_exception("replace parameters must not have attributes", el) if el.attributes.length > 1
|
539
660
|
|
540
|
-
|
661
|
+
replace_parameter_proc(el, metadata_name)
|
541
662
|
else
|
542
663
|
attributes = el.attributes.map do
|
543
664
|
|name, value| ":#{ruby_name name} => #{attribute_to_ruby(value, el)}" unless name.in?(SPECIAL_ATTRIBUTES)
|
544
665
|
end.compact
|
545
666
|
|
546
|
-
nested_parameters_hash = parameter_tags_hash(el)
|
667
|
+
nested_parameters_hash = parameter_tags_hash(el, metadata_name)
|
547
668
|
"proc { [{#{attributes * ', '}}, #{nested_parameters_hash}] #{nl}}"
|
548
669
|
end
|
549
670
|
end
|
550
671
|
|
551
672
|
|
673
|
+
def replace_parameter_proc(el, metadata_name, content=nil)
|
674
|
+
content ||= wrap_replace_parameter(el, metadata_name)
|
675
|
+
param_name = el.dryml_name.sub(/^(before|after|append|prepend)-/, "")
|
676
|
+
"proc { |#{param_restore_local_name(param_name)}| new_context { %>#{content}<% } #{tag_newlines(el)}}"
|
677
|
+
end
|
678
|
+
|
679
|
+
|
552
680
|
def param_content_local_name(name)
|
553
681
|
"_#{ruby_name name}__default_content"
|
554
682
|
end
|
@@ -576,7 +704,7 @@ module Hobo::Dryml
|
|
576
704
|
end.compact
|
577
705
|
|
578
706
|
# if there's a ':' el.name is just the part after the ':'
|
579
|
-
items << ":field => \"#{el.name}\"" if el.
|
707
|
+
items << ":field => \"#{ruby_name el.name}\"" if el.expanded_name =~ /:./
|
580
708
|
|
581
709
|
items = items.join(", ")
|
582
710
|
|
@@ -657,17 +785,17 @@ module Hobo::Dryml
|
|
657
785
|
|
658
786
|
|
659
787
|
def apply_control_attributes(expression, el)
|
660
|
-
|
661
|
-
controls.compact!
|
788
|
+
controls = %w(if unless repeat).map_hash { |x| el.attributes[x] }.compact
|
662
789
|
|
663
790
|
dryml_exception("You can't have multiple control attributes on the same element", el) if
|
664
791
|
controls.length > 1
|
665
792
|
|
666
|
-
|
793
|
+
attr = controls.keys.first
|
794
|
+
val = controls.values.first
|
667
795
|
if val.nil?
|
668
796
|
expression
|
669
797
|
else
|
670
|
-
control = if
|
798
|
+
control = if !el.attribute(attr).has_rhs?
|
671
799
|
"this"
|
672
800
|
elsif is_code_attribute?(val)
|
673
801
|
"#{val[1..-1]}"
|
@@ -676,13 +804,14 @@ module Hobo::Dryml
|
|
676
804
|
end
|
677
805
|
|
678
806
|
x = gensym
|
679
|
-
|
807
|
+
case attr
|
808
|
+
when "if"
|
680
809
|
"(if !(#{control}).blank?; (#{x} = #{expression}; Hobo::Dryml.last_if = true; #{x}) " +
|
681
810
|
"else (Hobo::Dryml.last_if = false; ''); end)"
|
682
|
-
|
811
|
+
when "unless"
|
683
812
|
"(if (#{control}).blank?; (#{x} = #{expression}; Hobo::Dryml.last_if = true; #{x}) " +
|
684
813
|
"else (Hobo::Dryml.last_if = false; ''); end)"
|
685
|
-
|
814
|
+
when "repeat"
|
686
815
|
"repeat_attribute(#{control}) { #{expression} }"
|
687
816
|
end
|
688
817
|
end
|
@@ -690,7 +819,7 @@ module Hobo::Dryml
|
|
690
819
|
|
691
820
|
|
692
821
|
def attribute_to_ruby(*args)
|
693
|
-
options =
|
822
|
+
options = args.extract_options!
|
694
823
|
attr, el = args
|
695
824
|
|
696
825
|
dryml_exception('erb scriptlet not allowed in this attribute (use #{ ... } instead)', el) if
|
@@ -747,7 +876,7 @@ module Hobo::Dryml
|
|
747
876
|
|
748
877
|
def element_line_num(el)
|
749
878
|
offset = el.source_offset
|
750
|
-
|
879
|
+
@xmlsrc[0..offset].count("\n") + 1
|
751
880
|
end
|
752
881
|
|
753
882
|
def tag_newlines(el)
|
@@ -770,9 +899,14 @@ module Hobo::Dryml
|
|
770
899
|
end
|
771
900
|
|
772
901
|
def rename_class(name)
|
773
|
-
name
|
774
|
-
|
775
|
-
|
902
|
+
@bundle && name.starts_with?("_") ? @bundle.send(name) : name
|
903
|
+
end
|
904
|
+
|
905
|
+
def include_source_metadata
|
906
|
+
# disabled for now -- we're still getting broken rendering with this feature on
|
907
|
+
return false
|
908
|
+
@include_source_metadata = RAILS_ENV == "development" && !ENV['DRYML_EDITOR'].blank? if @include_source_metadata.nil?
|
909
|
+
@include_source_metadata
|
776
910
|
end
|
777
911
|
|
778
912
|
end
|