spiderfw 0.5.7 → 0.5.9

Sign up to get free protection for your applications and to get access to all the features.
Files changed (161) hide show
  1. data/Rakefile +17 -6
  2. data/apps/cas_server/controllers/mixins/cas_login_mixin.rb +18 -5
  3. data/apps/cas_server/lib/cas.rb +1 -1
  4. data/apps/cms/models/content.rb +16 -0
  5. data/apps/cms/models/news_item.rb +7 -0
  6. data/apps/cms/models/translation.rb +14 -0
  7. data/apps/cms/views/admin/admin.shtml +16 -0
  8. data/apps/cms/views/admin/content.shtml +4 -0
  9. data/apps/core/acl/_init.rb +10 -0
  10. data/apps/core/acl/controllers/acl_controller.rb +14 -0
  11. data/apps/core/acl/models/permission.rb +11 -0
  12. data/apps/core/acl/views/acl.layout.shtml +8 -0
  13. data/apps/core/acl/views/index.shtml +3 -0
  14. data/apps/core/auth/controllers/mixins/auth_helper.rb +3 -3
  15. data/apps/core/auth/lib/authenticable.rb +4 -0
  16. data/apps/core/auth/models/super_user.rb +1 -0
  17. data/apps/core/auth/po/it/spider_auth.po +18 -10
  18. data/apps/core/auth/po/spider_auth.pot +13 -1
  19. data/apps/core/components/_init.rb +2 -1
  20. data/apps/core/components/po/it/spider_components.po +3 -3
  21. data/apps/core/components/po/spider_components.pot +3 -3
  22. data/apps/core/components/public/css/month_calendar.css +24 -0
  23. data/apps/core/components/public/js/jquery/jquery-1.4.2-min.js +154 -0
  24. data/apps/core/components/public/js/jquery/jquery-1.4.2.js +6240 -0
  25. data/apps/core/components/public/js/jquery/plugins/jquery.form.js +1 -1
  26. data/apps/core/components/public/js/spider.js +26 -20
  27. data/apps/core/components/widgets/admin/admin.rb +1 -1
  28. data/apps/core/components/widgets/crud/crud.rb +1 -1
  29. data/apps/core/components/widgets/list/list.rb +2 -2
  30. data/apps/core/components/widgets/month_calendar/month_calendar.rb +67 -0
  31. data/apps/core/components/widgets/month_calendar/month_calendar.shtml +21 -0
  32. data/apps/core/components/widgets/table/table.rb +4 -2
  33. data/apps/core/components/widgets/table/table.shtml +37 -31
  34. data/apps/core/forms/_init.rb +2 -1
  35. data/apps/core/forms/po/it/spider_forms.po +14 -2
  36. data/apps/core/forms/po/spider_forms.pot +13 -1
  37. data/apps/core/forms/public/css/file_input.css +15 -0
  38. data/apps/core/forms/public/{form.css → css/form.css} +8 -0
  39. data/apps/core/forms/public/file_input.js +37 -0
  40. data/apps/core/forms/tags/element_label.erb +4 -1
  41. data/apps/core/forms/tags/element_row.erb +7 -2
  42. data/apps/core/forms/tags/row.erb +10 -1
  43. data/apps/core/forms/widgets/form/form.rb +43 -10
  44. data/apps/core/forms/widgets/form/form.shtml +12 -5
  45. data/apps/core/forms/widgets/inputs/date_time/date_time.shtml +1 -0
  46. data/apps/core/forms/widgets/inputs/file_input/file_input.rb +43 -0
  47. data/apps/core/forms/widgets/inputs/file_input/file_input.shtml +12 -0
  48. data/apps/core/forms/widgets/inputs/input/input.rb +23 -1
  49. data/apps/core/forms/widgets/inputs/password/password.rb +1 -0
  50. data/apps/core/forms/widgets/inputs/text/text.shtml +1 -1
  51. data/apps/core/forms/widgets/inputs/text_area/text_area.shtml +2 -2
  52. data/apps/git_model_versioning/models/mixins/git_versioned.rb +91 -0
  53. data/apps/hippo/models/mixins/hippo_struct.rb +42 -26
  54. data/apps/master/controllers/git.rb +32 -0
  55. data/apps/messenger/_init.rb +1 -1
  56. data/apps/messenger/config/options.rb +2 -0
  57. data/apps/messenger/config/worker/queue.rb +3 -0
  58. data/apps/messenger/controllers/mixins/{messenger_controller_mixin.rb → messenger_helper.rb} +8 -6
  59. data/apps/messenger/messenger.rb +10 -3
  60. data/apps/messenger/models/message.rb +2 -2
  61. data/apps/messenger/po/it/spider_messenger.po +1 -1
  62. data/apps/messenger/po/spider_messenger.pot +1 -1
  63. data/apps/saml/_init.rb +13 -0
  64. data/apps/saml/controllers/saml2idp.rb +18 -0
  65. data/apps/saml/lib/bindings/http_redirect_binding.rb +14 -0
  66. data/apps/saml/lib/messages/authn_request.rb +52 -0
  67. data/apps/saml/lib/saml.rb +10 -0
  68. data/apps/soap/controllers/soap_controller.rb +12 -2
  69. data/apps/soap/lib/soap.rb +16 -1
  70. data/apps/soap/soap.gemspec +10 -0
  71. data/apps/webdav/lib/locking.rb +2 -2
  72. data/apps/worker/_init.rb +2 -0
  73. data/apps/worker/config/options.rb +1 -0
  74. data/apps/worker/worker.rb +17 -4
  75. data/blueprints/app/__APP__.appspec +4 -0
  76. data/blueprints/app/_init.rb +5 -8
  77. data/blueprints/app/controllers/__APP___controller.rb +2 -1
  78. data/blueprints/app/views/__APP__.layout.shtml +4 -1
  79. data/blueprints/install/config/config.yml +2 -4
  80. data/blueprints/model.rb +15 -0
  81. data/data/locale/it/LC_MESSAGES/spider.mo +0 -0
  82. data/data/locale/it/LC_MESSAGES/spider_auth.mo +0 -0
  83. data/data/locale/it/LC_MESSAGES/spider_components.mo +0 -0
  84. data/data/locale/it/LC_MESSAGES/spider_forms.mo +0 -0
  85. data/data/locale/it/LC_MESSAGES/spider_messenger.mo +0 -0
  86. data/lib/spiderfw/app.rb +93 -31
  87. data/lib/spiderfw/autoload.rb +1 -0
  88. data/lib/spiderfw/cmd/cmd.rb +8 -1
  89. data/lib/spiderfw/cmd/commands/config.rb +54 -0
  90. data/lib/spiderfw/config/configuration.rb +30 -0
  91. data/lib/spiderfw/config/options/spider.rb +18 -6
  92. data/lib/spiderfw/controller/controller.rb +12 -11
  93. data/lib/spiderfw/controller/dispatcher.rb +5 -4
  94. data/lib/spiderfw/controller/http_controller.rb +16 -2
  95. data/lib/spiderfw/controller/mixins/http_mixin.rb +3 -2
  96. data/lib/spiderfw/controller/mixins/static_content.rb +8 -2
  97. data/lib/spiderfw/controller/mixins/visual.rb +72 -52
  98. data/lib/spiderfw/controller/request.rb +7 -3
  99. data/lib/spiderfw/controller/scene.rb +6 -0
  100. data/lib/spiderfw/controller/session.rb +12 -8
  101. data/lib/spiderfw/env.rb +1 -1
  102. data/lib/spiderfw/http/adapters/mongrel.rb +1 -1
  103. data/lib/spiderfw/http/http.rb +48 -19
  104. data/lib/spiderfw/i18n/cldr.rb +53 -3
  105. data/lib/spiderfw/i18n/i18n.rb +52 -2
  106. data/lib/spiderfw/i18n/provider.rb +24 -0
  107. data/lib/spiderfw/i18n/rails.rb +24 -0
  108. data/lib/spiderfw/model/active_record.rb +3 -3
  109. data/lib/spiderfw/model/base_model.rb +45 -14
  110. data/lib/spiderfw/model/condition.rb +11 -2
  111. data/lib/spiderfw/model/data_type.rb +15 -7
  112. data/lib/spiderfw/model/datatypes/decimal.rb +15 -3
  113. data/lib/spiderfw/model/datatypes/file_path.rb +50 -0
  114. data/lib/spiderfw/model/datatypes/serialized_object.rb +0 -4
  115. data/lib/spiderfw/model/datatypes/uuid.rb +3 -3
  116. data/lib/spiderfw/model/datatypes.rb +1 -0
  117. data/lib/spiderfw/model/extended_models/managed.rb +11 -2
  118. data/lib/spiderfw/model/mappers/db_mapper.rb +116 -52
  119. data/lib/spiderfw/model/mappers/mapper.rb +36 -14
  120. data/lib/spiderfw/model/mixins/state_machine.rb +45 -9
  121. data/lib/spiderfw/model/mixins/versioned.rb +1 -1
  122. data/lib/spiderfw/model/model.rb +2 -1
  123. data/lib/spiderfw/model/query_set.rb +21 -3
  124. data/lib/spiderfw/model/request.rb +7 -0
  125. data/lib/spiderfw/model/storage/db/adapters/mssql.rb +2 -1
  126. data/lib/spiderfw/model/storage/db/adapters/mysql.rb +4 -1
  127. data/lib/spiderfw/model/storage/db/adapters/oci8.rb +35 -18
  128. data/lib/spiderfw/model/storage/db/adapters/sqlite.rb +68 -34
  129. data/lib/spiderfw/model/storage/db/connectors/odbc.rb +1 -1
  130. data/lib/spiderfw/model/storage/db/db_schema.rb +33 -4
  131. data/lib/spiderfw/model/storage/db/db_storage.rb +27 -8
  132. data/lib/spiderfw/requires.rb +2 -0
  133. data/lib/spiderfw/tag/tag.rb +1 -1
  134. data/lib/spiderfw/templates/blocks/attr_if.rb +7 -1
  135. data/lib/spiderfw/templates/blocks/each.rb +8 -3
  136. data/lib/spiderfw/templates/blocks/html.rb +12 -22
  137. data/lib/spiderfw/templates/blocks/render.rb +3 -3
  138. data/lib/spiderfw/templates/blocks/run.rb +47 -11
  139. data/lib/spiderfw/templates/blocks/tag_if.rb +2 -2
  140. data/lib/spiderfw/templates/blocks/text.rb +2 -1
  141. data/lib/spiderfw/templates/blocks/widget.rb +5 -3
  142. data/lib/spiderfw/templates/blocks/yield.rb +1 -1
  143. data/lib/spiderfw/templates/template.rb +27 -24
  144. data/lib/spiderfw/templates/template_blocks.rb +37 -14
  145. data/lib/spiderfw/utils/monkey/exception.rb +1 -1
  146. data/lib/spiderfw/utils/monkey/nil_class.rb +7 -0
  147. data/lib/spiderfw/utils/monkey/numeric.rb +15 -0
  148. data/lib/spiderfw/version.rb +1 -1
  149. data/lib/spiderfw/widget/widget.rb +36 -33
  150. data/lib/spiderfw/widget/widget_attributes.rb +1 -1
  151. data/lib/spiderfw.rb +18 -5
  152. data/spider.gemspec +5 -5
  153. metadata +44 -18
  154. data/apps/core/components/public/js/jquery/plugins/jtree/jquery.jtree.1.0.js +0 -187
  155. data/apps/core/components/public/js/jquery/plugins/jtree/jquery.jtree.1.0.min.js +0 -1
  156. data/apps/core/components/public/js/jquery/plugins/jtree/jquery.jtree.spider.1.0.js +0 -193
  157. data/apps/core/forms/widgets/inputs/subform/subform.rb +0 -10
  158. data/apps/core/forms/widgets/inputs/subform/subform.shtml +0 -5
  159. data/apps/messenger/config/worker.rb +0 -3
  160. data/lib/spiderfw/controller/app_controller.rb +0 -14
  161. data/lib/spiderfw/utils/test_case.rb +0 -24
@@ -24,6 +24,7 @@ module Spider; module Model; module Storage; module Db
24
24
  @sequences = {}
25
25
  @pass = {}
26
26
  @foreign_key_constraints = []
27
+ @order = []
27
28
  end
28
29
 
29
30
  # Returns the main table name.
@@ -74,6 +75,8 @@ module Spider; module Model; module Storage; module Db
74
75
 
75
76
  # Returns table_name + '.' + #foreign_key_field
76
77
  def qualified_foreign_key_field(element_name, key_name)
78
+ f = foreign_key_field(element_name, key_name)
79
+ return f.expression if f.is_a?(FieldExpression)
77
80
  return @table.name + '.' + foreign_key_field(element_name, key_name).name
78
81
  end
79
82
 
@@ -95,13 +98,24 @@ module Spider; module Model; module Storage; module Db
95
98
  def set_column(element_name, field)
96
99
  field = Field.new(@table, field[:name], field[:type], field[:attributes] || {}) if field.is_a?(Hash)
97
100
  @columns[element_name] = field
101
+ @order << field
98
102
  end
99
103
 
100
104
  # Sets a foreign key to the primary key of an element.
101
105
  def set_foreign_key(element_name, element_key, field)
102
- field = Field.new(@table, field[:name], field[:type], field[:attributes] || {}) if field.is_a?(Hash)
106
+ if field.is_a?(Hash)
107
+ field[:attributes] ||= {}
108
+ field[:attributes][:expression] ||= field[:expression]
109
+ if field[:attributes][:expression]
110
+ field[:name] = "#{@table}_#{element_name}_#{element_key}".upcase
111
+ field = FieldExpression.new(@table, field[:name], field[:type], field[:attributes] || {})
112
+ else
113
+ field = Field.new(@table, field[:name], field[:type], field[:attributes] || {})
114
+ end
115
+ end
103
116
  @foreign_keys[element_name] ||= {}
104
117
  @foreign_keys[element_name][element_key] = field
118
+ @order << field
105
119
  end
106
120
 
107
121
  def set_foreign_key_constraint(name, table, keys, options={})
@@ -133,7 +147,7 @@ module Spider; module Model; module Storage; module Db
133
147
  # }}
134
148
  def get_schemas
135
149
  schemas = {}
136
- schemas[@table.name] = {:columns => {}, :attributes => {}}
150
+ schemas[@table.name] = {:columns => {}, :attributes => {}, :fields_order => @order}
137
151
  @columns.each do |element, column|
138
152
  schemas[@table.name][:columns][column.name] = {:type => column.type, :attributes => column.attributes}
139
153
  end
@@ -179,8 +193,8 @@ module Spider; module Model; module Storage; module Db
179
193
  end
180
194
 
181
195
  class Field
182
- attr_reader :name, :table
183
- attr_accessor :type
196
+ attr_reader :table
197
+ attr_accessor :name, :type
184
198
  attr_accessor :attributes
185
199
 
186
200
  def initialize(table, name, type, attributes={})
@@ -212,6 +226,21 @@ module Spider; module Model; module Storage; module Db
212
226
 
213
227
  end
214
228
 
229
+ class FieldExpression < Field
230
+ attr_reader :expression
231
+
232
+ def initialize(table, name, type, attributes={})
233
+ super
234
+ @expression = attributes[:expression]
235
+ end
236
+
237
+
238
+ def to_s
239
+ "#{@expression} AS #{@name}"
240
+ end
241
+
242
+ end
243
+
215
244
  class ForeignKeyConstraint
216
245
  attr_reader :name, :table, :fields, :options
217
246
 
@@ -96,7 +96,7 @@ module Spider; module Model; module Storage; module Db
96
96
  end
97
97
 
98
98
  # Instantiates a new connection with current connection params.
99
- def connect()
99
+ def connect
100
100
  return self.class.get_connection(*@connection_params)
101
101
  #Spider::Logger.debug("#{self.class.name} in thread #{Thread.current} acquired connection #{@conn}")
102
102
  end
@@ -163,6 +163,10 @@ module Spider; module Model; module Storage; module Db
163
163
  return self.class.capabilities[:transactions]
164
164
  end
165
165
 
166
+ def transactions_enabled?
167
+ @configuration['enable_transactions'] && supports_transactions?
168
+ end
169
+
166
170
  def start_transaction
167
171
  return savepoint("point#{curr[:savepoints].length}") if in_transaction?
168
172
  curr[:transaction_nesting] += 1
@@ -191,12 +195,14 @@ module Spider; module Model; module Storage; module Db
191
195
  end
192
196
 
193
197
  def commit
198
+ return false unless transactions_enabled?
194
199
  raise StorageException, "Commit without a transaction" unless in_transaction?
195
200
  return curr[:savepoints].pop unless curr[:savepoints].empty?
196
201
  commit!
197
202
  end
198
203
 
199
204
  def commit_or_continue
205
+ return false unless transactions_enabled?
200
206
  raise StorageException, "Commit without a transaction" unless in_transaction?
201
207
  if curr[:transaction_nesting] == 1
202
208
  commit
@@ -473,12 +479,16 @@ module Spider; module Model; module Storage; module Db
473
479
  condition = query[:condition]
474
480
  return ['', []] unless (condition && condition[:values])
475
481
  bind_vars = []
482
+ condition[:values].reject!{ |v| v.is_a?(Hash) && v[:values].empty? }
476
483
  mapped = condition[:values].map do |v|
477
484
  if (v.is_a? Hash) # subconditions
478
485
  # FIXME: optimize removing recursion
486
+
479
487
  sql, vals = sql_condition({:condition => v})
480
488
  bind_vars += vals
481
- !sql.empty? ? "(#{sql})" : nil
489
+ sql = nil if sql.empty?
490
+ sql = "(#{sql})" if sql && v[:values].length > 1
491
+ sql
482
492
  elsif (v[2].is_a? Spider::QueryFuncs::Expression)
483
493
  sql_condition_value(v[0], v[1], v[2].to_s, false)
484
494
  else
@@ -541,7 +551,11 @@ module Spider; module Model; module Storage; module Db
541
551
  }
542
552
  values = []
543
553
  sql = joins.map{ |join|
544
- sql_on = join[:keys].map{ |from_f, to_f| "#{from_f} = #{to_f}"}.join(' AND ')
554
+ to_t = join[:as] || join[:to]
555
+ sql_on = join[:keys].map{ |from_f, to_f|
556
+ to_field = to_f.is_a?(FieldExpression) ? to_f : "#{to_t}.#{to_f.name}"
557
+ "#{from_f} = #{to_field}"
558
+ }.join(' AND ')
545
559
  if (join[:condition])
546
560
  condition_sql, condition_values = sql_condition({:condition => join[:condition]})
547
561
  sql_on += " and #{condition_sql}"
@@ -556,9 +570,14 @@ module Spider; module Model; module Storage; module Db
556
570
  end
557
571
 
558
572
  # Returns SQL for the ORDER part.
559
- def sql_order(query)
573
+ def sql_order(query, replacements={})
560
574
  return '' unless query[:order]
561
- return query[:order].map{|o| "#{o[0]} #{o[1]}"}.join(' ,')
575
+ replacements ||= {}
576
+ return query[:order].map{|o|
577
+ repl = replacements[o[0].to_s]
578
+ ofield = repl ? repl : o[0]
579
+ "#{ofield} #{o[1]}"
580
+ }.join(' ,')
562
581
  end
563
582
 
564
583
  # Returns the LIMIT and OFFSET SQL.
@@ -572,7 +591,7 @@ module Spider; module Model; module Storage; module Db
572
591
  # Returns SQL and values for an insert statement.
573
592
  def sql_insert(insert)
574
593
  curr[:last_query_type] = :insert
575
- sql = "INSERT INTO #{insert[:table]} (#{insert[:values].keys.join(', ')}) " +
594
+ sql = "INSERT INTO #{insert[:table]} (#{insert[:values].keys.map{ |k| k.name }.join(', ')}) " +
576
595
  "VALUES (#{insert[:values].values.map{'?'}.join(', ')})"
577
596
  return [sql, insert[:values].values]
578
597
  end
@@ -599,7 +618,7 @@ module Spider; module Model; module Storage; module Db
599
618
  # Returns the COLUMN = val, ... part of an update statement.
600
619
  def sql_update_values(update)
601
620
  update[:values].map{ |k, v|
602
- v.is_a?(Spider::QueryFuncs::Expression) ? "#{k} = #{v}" : "#{k} = ?"
621
+ v.is_a?(Spider::QueryFuncs::Expression) ? "#{k.name} = #{v}" : "#{k.name} = ?"
603
622
  }.join(', ')
604
623
  end
605
624
 
@@ -650,7 +669,7 @@ module Spider; module Model; module Storage; module Db
650
669
  sqls += sql_alter_field(table_name, field[:name], field[:type], field[:attributes])
651
670
  end
652
671
  if (alter_attributes[:primary_keys] && !alter_attributes[:primary_keys].empty?)
653
- sqls << sql_drop_primary_key(table_name) if (!current[:primary_keys].empty? && current[:primary_keys] != alter_attributes[:primary_keys])
672
+ sqls << sql_drop_primary_key(table_name) if (current[:primary_keys] && !current[:primary_keys].empty? && current[:primary_keys] != alter_attributes[:primary_keys])
654
673
  sqls << sql_create_primary_key(table_name, alter_attributes[:primary_keys])
655
674
  end
656
675
  if (alter_attributes[:foreign_key_constraints])
@@ -7,7 +7,9 @@ require 'spiderfw/utils/monkey/class'
7
7
  require 'spiderfw/utils/monkey/symbol'
8
8
  require 'spiderfw/utils/monkey/time'
9
9
  require 'spiderfw/utils/monkey/date_time'
10
+ require 'spiderfw/utils/monkey/numeric'
10
11
  require 'spiderfw/utils/monkey/exception'
12
+ require 'spiderfw/utils/monkey/nil_class'
11
13
  require 'spiderfw/utils/multi_level_hash'
12
14
  require 'spiderfw/utils/thread_out'
13
15
  require 'spiderfw/utils/inflector'
@@ -15,7 +15,7 @@ module Spider
15
15
  end
16
16
 
17
17
  def initialize(el)
18
- @attributes = el.attributes
18
+ @attributes = el.attributes.to_hash
19
19
  @content = el.innerHTML
20
20
  end
21
21
 
@@ -6,17 +6,23 @@ module Spider; module TemplateBlocks
6
6
  # Adds an attribute if a condition holds
7
7
  # Example:
8
8
  # <div sp:attr-if="@my_condition,class,coolDiv"></div>
9
+ # The attribute's value can be a scene variable, but not an expression: so
10
+ # <div sp:attr-if"@my_condition,attr_name,@attr_value" /> is valid, but
11
+ # <div sp:attr-if"@my_condition,attr_name,@attr_value_start+@attr_value_end" /> is not
9
12
 
10
13
  class AttrIf < Block
11
14
 
12
15
  def compile(options={})
13
16
  init = ""
14
- attr_if = @el.attributes['sp:attr-if']
17
+ attr_if = @el.get_attribute('sp:attr-if')
15
18
  @el.remove_attribute('sp:attr-if')
16
19
  @el.set_attribute("tmp-attr-if", attr_if)
17
20
  compiled = Spider::TemplateBlocks.parse_element(@el, @allowed_blocks, @template).compile(options)
18
21
  c, init = compiled.run_code, compiled.init_code
19
22
  cond, name, val = attr_if.split(',')
23
+ if val && val.strip[0].chr == '@'
24
+ val = "'+#{var_to_scene(val)}+'"
25
+ end
20
26
  cond = vars_to_scene(cond)
21
27
  full_attr = val ? "#{name}=\"#{val}\"" : "#{name}"
22
28
  replace = "'+"+"( (#{cond}) ? '#{full_attr}' : '' )"+"+'"
@@ -14,9 +14,9 @@ module Spider; module TemplateBlocks
14
14
  rep_type = nil
15
15
  rep = nil
16
16
  ['sp:each', 'sp:each_index'].each do |name|
17
- if (@el.attributes[name])
17
+ if (@el.has_attribute?(name))
18
18
  rep_type = name[3..-1]
19
- rep = @el.attributes[name]
19
+ rep = @el.get_attribute(name)
20
20
  @el.remove_attribute(name)
21
21
  break
22
22
  end
@@ -27,6 +27,7 @@ module Spider; module TemplateBlocks
27
27
  arguments = $2.strip
28
28
  end
29
29
  c = "#{vars_to_scene(repeated)}.#{rep_type} do |#{arguments}|\n"
30
+
30
31
  content = Spider::TemplateBlocks.parse_element(@el, @allowed_blocks, @template).compile(options)
31
32
  content.run_code.each_line do |line|
32
33
  c += ' '+line
@@ -34,7 +35,11 @@ module Spider; module TemplateBlocks
34
35
  c += ' $out << "\n"'
35
36
  c += "\n"
36
37
  c += "end\n"
37
- init += content.init_code if content.init_code
38
+ if content.init_code && !content.init_code.strip.empty?
39
+ init = "#{vars_to_scene(repeated, '@scene')}.#{rep_type} do |#{arguments}|\n"
40
+ init += content.init_code
41
+ init += "end\n"
42
+ end
38
43
  return CompiledBlock.new(init, c)
39
44
  end
40
45
 
@@ -8,7 +8,7 @@ module Spider; module TemplateBlocks
8
8
  c = ""
9
9
  init = ""
10
10
  start = get_start(options)
11
- c += "$out << '#{start}'\n"
11
+ c += start
12
12
  is_root = options[:root]
13
13
  options.delete(:root)
14
14
  c += "unless self[:widget][:target_only] && !self[:widget][:is_target]\n" if (options[:mode] == :widget && is_root)
@@ -21,40 +21,30 @@ module Spider; module TemplateBlocks
21
21
 
22
22
  def get_start(options)
23
23
  if options[:mode] == :widget
24
- cl = @el.attributes['class'] || ''
25
- if @el.attributes['id']
24
+ cl = @el.get_attribute('class') || ''
25
+ if @el.has_attribute?('id')
26
26
  cl += ' ' unless cl.empty?
27
- cl += "id-#{@el.attributes['id']}"
28
- @el.raw_attributes.delete('id')
27
+ cl += "id-#{@el.get_attribute('id')}"
28
+ @el.remove_attribute('id')
29
29
  end
30
30
  if (options[:root])
31
31
  cl += " widget"
32
32
  if options[:owner_class]
33
33
  cl += " wdgt-#{options[:owner_class].name.gsub('::', '-')}"
34
34
  end
35
- @el.raw_attributes['id'] = "{ @widget[:full_id] }"
35
+ @el.set_attribute('id', "{ @widget[:full_id] }")
36
36
  cl += ' ' unless cl.empty?
37
37
  cl += '{ @widget[:css_classes] }'
38
38
  end
39
- @el.raw_attributes['class'] = cl
39
+ @el.set_attribute('class', cl)
40
40
  end
41
- start = "<"+@el.name
42
- @el.attributes.each do |key, val|
41
+ start = "$out << '<"+@el.name
42
+ @el.attributes.to_hash.each do |key, val|
43
43
  start += " #{key}=\""
44
- rest = scan_vars(val) do |text, code|
45
- start += text+"'+("+vars_to_scene(code)+").to_s+'"
46
- end
47
- start += rest
48
- # start += replace_vars(val)
49
- # if (val =~ /(.*)\{ (.+) \}(.*)/)
50
- # start += $1+"'+"+var_to_scene($2)+".to_s+'"+$3
51
- # else
52
- # start += val
53
- # end
54
- start += '"'
44
+ start += compile_text(val)
45
+ start += "\""
55
46
  end
56
- #start += " /" unless @el.etag
57
- start += ">"
47
+ start += ">'\n"
58
48
  return start
59
49
  end
60
50
 
@@ -7,9 +7,9 @@ module Spider; module TemplateBlocks
7
7
  def compile(options={})
8
8
  c = ""
9
9
  init = ""
10
- if (@el.attributes['obj'])
11
- c_scene_obj = var_to_scene(@el.attributes['obj'])
12
- i_scene_obj = var_to_scene(@el.attributes['obj'], 'scene')
10
+ if (@el.has_attribute?('obj'))
11
+ c_scene_obj = var_to_scene(@el.get_attribute('obj'))
12
+ i_scene_obj = var_to_scene(@el.get_attribute('obj'), 'scene')
13
13
  init += "#{i_scene_obj}.request = @request\n"
14
14
  init += "#{i_scene_obj}.response = @response\n"
15
15
  c += "#{c_scene_obj}.render(self)\n"
@@ -4,21 +4,57 @@ module Spider; module TemplateBlocks
4
4
 
5
5
  class Run < Block
6
6
 
7
+ def escape_runtime_content(html)
8
+ html.strip.gsub("'", "\\\\'")
9
+ end
10
+
7
11
  def compile(options={})
8
12
  c = ""
9
- init = nil
10
- runtime_contents = @el.children_of_type('tpl:runtime-content')
11
- if (@el.attributes['obj'])
12
- scene_obj = var_to_scene(@el.attributes['obj'])
13
- runtime_contents.each do |rc|
14
- content = rc.innerHTML.strip
15
- content.gsub!("'", "\\\\'")
16
- condition = ""
17
- if (rc.attributes['for'])
18
- condition = " if #{scene_obj}.local_id.to_s == '#{rc.attributes['for']}'"
13
+ init = ""
14
+ runtime_contents = @el.children ? @el.children_of_type('tpl:runtime-content') : []
15
+ run_attributes = @el.attributes.to_hash
16
+ if @el.has_attribute?('obj')
17
+ scene_obj = var_to_scene(run_attributes.delete('obj'))
18
+ widget_id = run_attributes.delete('widget')
19
+ if widget_id
20
+ runtime_content_obj = "@widgets[#{widget_id}]"
21
+ else
22
+ runtime_content_obj = scene_obj
23
+ end
24
+ # runtime_contents.each do |rc|
25
+ # content = escape_runtime_content(rc.innerHTML)
26
+ # condition = ""
27
+ # if (rc.has_attribute?('for'))
28
+ # condition = " if #{runtime_content_obj}.local_id.to_s == '#{rc.get_attribute('for')}'"
29
+ # end
30
+ # parse_runtime = "#{runtime_content_obj}.parse_runtime_content_xml('<sp:widget-content>#{content}</sp:widget-content>')#{condition}\n"
31
+ # if widget_id
32
+ # init += parse_runtime
33
+ # else
34
+ # c += parse_runtime
35
+ # end
36
+ # @el.children.delete(rc)
37
+ # end
38
+ # unless @el.innerHTML.strip.empty?
39
+ # content = escape_runtime_content(@el.innerHTML)
40
+ # parse_runtime = "#{runtime_content_obj}.parse_runtime_content_xml('<sp:widget-content>#{content}</sp:widget-content>')\n"
41
+ # if widget_id
42
+ # init += parse_runtime
43
+ # else
44
+ # c += parse_runtime
45
+ # end
46
+ # end
47
+ if widget_id && @el.children
48
+ attributes = @el.children_of_type('sp:attribute')
49
+ init += "@owner.widget_attributes[#{widget_id}] ||= {}\n" if attributes.length > 0
50
+ attributes.each do |at|
51
+ attr_name = at.get_attribute('name').gsub("'", "\\\\'")
52
+ attr_value = at.get_attribute('value').gsub("'", "\\\\'")
53
+
54
+ init += "@owner.widget_attributes[#{widget_id}][:#{attr_name}] = '#{attr_value}'\n"
19
55
  end
20
- c += "#{scene_obj}.parse_runtime_content_xml('#{content}')#{condition}\n"
21
56
  end
57
+ @el.innerHTML = ''
22
58
  c += "#{scene_obj}.render if (#{scene_obj})\n"
23
59
  end
24
60
  return CompiledBlock.new(init, c)
@@ -6,11 +6,11 @@ module Spider; module TemplateBlocks
6
6
 
7
7
  def compile(options={})
8
8
  init = ""
9
- cond = vars_to_scene(@el.attributes['sp:tag-if'])
9
+ cond = vars_to_scene(@el.get_attribute('sp:tag-if'))
10
10
  @el.remove_attribute('sp:tag-if')
11
11
  html = HTML.new(@el, @template)
12
12
  c = "if (#{cond})\n"
13
- c += " $out << '#{html.get_start(options)}'\n"
13
+ c += html.get_start(options)
14
14
  c += "end\n"
15
15
  c, init = html.compile_content(c, init, options)
16
16
  tag_end = html.get_end
@@ -3,7 +3,7 @@ require 'strscan'
3
3
 
4
4
  module Spider; module TemplateBlocks
5
5
  ExpressionOutputRegexp = /\{\s([^\s].*?)\s\}/
6
- GettextRegexp = /_\((.+)?\)(\s%\s(\S+)(,\s\S+)?)?/
6
+ GettextRegexp = /_\(([^\)]+)?\)(\s%\s([^\s,]+)(,\s*\S+\s*\])?)?/
7
7
  ERBRegexp = /(<%(.+)?%>)/
8
8
 
9
9
  class Text < Block
@@ -37,6 +37,7 @@ module Spider; module TemplateBlocks
37
37
  end
38
38
 
39
39
 
40
+
40
41
  end
41
42
 
42
43
 
@@ -7,13 +7,15 @@ module Spider; module TemplateBlocks
7
7
  def compile(options={})
8
8
  klass = Spider::Template.get_registered_class(@el.name)
9
9
  init_params = []
10
- id = @el.attributes['id']
10
+ id = @el.get_attribute('id')
11
11
  raise TemplateCompileError, "Widget #{@el.name} does not have an id" unless id
12
- template_attr = @el.attributes['template']
12
+ template_attr = @el.get_attribute('template')
13
13
  @el.remove_attribute('template')
14
- @el.attributes.each do |key, val|
14
+ @el.attributes.to_hash.each do |key, val|
15
15
  if (!val.empty? && val[0].chr == '@')
16
16
  sval = var_to_scene(val, 'scene')
17
+ elsif (!val.empty? && val[0].chr == '$')
18
+ sval = val[1..-1]
17
19
  else
18
20
  sval = '"'+val+'"'
19
21
  end
@@ -6,7 +6,7 @@ module Spider; module TemplateBlocks
6
6
 
7
7
  def compile(options={})
8
8
  init = nil
9
- to = @el.attributes['to'] || 'yield_to'
9
+ to = @el.get_attribute('to') || 'yield_to'
10
10
  #c = "self[:yield_to][:controller].send(self[:yield_to][:action], *self[:yield_to][:arguments])\n"
11
11
  c = "yield :#{to}\n"
12
12
  return CompiledBlock.new(init, c)
@@ -204,11 +204,11 @@ module Spider
204
204
  el = process_tags(root)
205
205
  @overrides.each{ |o| apply_override(root, o) } if (@overrides)
206
206
  root.search('tpl:placeholder').remove # remove empty placeholders
207
- res = root.children_of_type('tpl:asset')
207
+ res = root.children ? root.children_of_type('tpl:asset') : []
208
208
  res_init = ""
209
209
  res.each do |r|
210
210
  r.set_attribute('class', 'to_delete')
211
- pr = parse_asset(r.attributes['type'], r.attributes['src'], r.attributes)
211
+ pr = parse_asset(r.get_attribute('type'), r.get_attribute('src'), r.attributes.to_hash)
212
212
  assets << pr
213
213
  res_init += "@assets << {
214
214
  :type => :#{pr[:type]},
@@ -274,16 +274,18 @@ module Spider
274
274
  doc = open(path){ |f| Hpricot.XML(f) }
275
275
  root = doc.root
276
276
  overrides = []
277
- override_tags.each do |tag|
278
- overrides += root.children_of_type('tpl:'+tag)
277
+ if root.children
278
+ override_tags.each do |tag|
279
+ overrides += root.children_of_type('tpl:'+tag)
280
+ end
279
281
  end
280
282
  overrides.each{ |o| o.set_attribute('class', 'to_delete') }
281
283
  root.search('.to_delete').remove
282
284
  add_overrides overrides
283
285
  if (root.name == 'tpl:extend')
284
- ext_src = root.attributes['src']
285
- ext_app = root.attributes['app']
286
- ext_widget = root.attributes['widget']
286
+ ext_src = root.get_attribute('src')
287
+ ext_app = root.get_attribute('app')
288
+ ext_widget = root.get_attribute('widget')
287
289
  if ext_widget
288
290
  ext_widget = Spider::Template.get_registered_class(ext_widget)
289
291
  ext_src ||= ext_widget.default_template
@@ -297,7 +299,7 @@ module Spider
297
299
  ext_search_paths = ext_owner.template_paths
298
300
  end
299
301
  ext = self.class.real_path(ext_src, @path, ext_owner, ext_search_paths)
300
- assets = root.children_of_type('tpl:asset')
302
+ assets = root.children ? root.children_of_type('tpl:asset') : []
301
303
  @dependencies << ext
302
304
  tpl = Template.new(ext)
303
305
  root = get_el(ext)
@@ -308,10 +310,10 @@ module Spider
308
310
  end
309
311
  else
310
312
  root.search('tpl:include').each do |incl|
311
- src = real_path(incl.attributes['src'])
313
+ src = real_path(incl.get_attribute('src'))
312
314
  @dependencies << src
313
315
  incl_el = self.get_el(src)
314
- assets = incl_el.children_of_type('tpl:asset')
316
+ assets = incl_el.children ? incl_el.children_of_type('tpl:asset') : []
315
317
  assets_html = ""
316
318
  assets.each{ |ass| assets_html += ass.to_html }
317
319
  incl.swap(assets_html+self.get_el(src).to_html)
@@ -322,20 +324,20 @@ module Spider
322
324
 
323
325
  def process_tags(el)
324
326
  block = TemplateBlocks.get_block_type(el, true)
325
- raise "Bad html in #{@path} at '#{el}', can't parse" if (el == Hpricot::BogusETag)
327
+ raise "Bad html in #{@path}, can't parse" if el.is_a?(Hpricot::BogusETag)
326
328
  if (block == :Tag)
327
329
  sp_attributes = {}
328
330
  # FIXME: should use blocks instead
329
- el.attributes.each do |key, value|
331
+ el.attributes.to_hash.each do |key, value|
330
332
  if (key[0..1] == 'sp')
331
333
  sp_attributes[key] = value
332
- el.raw_attributes.delete(key)
334
+ el.remove_attribute(key)
333
335
  end
334
336
  end
335
337
  klass = Spider::Template.get_registered_class(el.name)
336
338
  tag = klass.new(el)
337
339
  res = process_tags(Hpricot(tag.render).root)
338
- sp_attributes.each{ |key, value| res.raw_attributes[key] = value }
340
+ sp_attributes.each{ |key, value| res.set_attribute(key, value) }
339
341
  return res
340
342
  else
341
343
  el.each_child do |child|
@@ -480,13 +482,13 @@ module Spider
480
482
 
481
483
  def add_overrides(overrides)
482
484
  overrides.each do |ov|
483
- w = ov.attributes['widget']
485
+ w = ov.get_attribute('widget')
484
486
  if (w)
485
487
  first, rest = w.split('/', 2)
486
488
  if (rest)
487
- ov.raw_attributes['widget'] = rest
489
+ ov.set_attribute('widget', rest)
488
490
  else
489
- ov.raw_attributes.delete('widget')
491
+ ov.remove_attribute('widget')
490
492
  end
491
493
  # debugger
492
494
  @widgets_overrides[first] ||= []
@@ -504,7 +506,7 @@ module Spider
504
506
 
505
507
  # Applies an override to an (Hpricot) element.
506
508
  def apply_override(el, override)
507
- search_string = override.attributes['search']
509
+ search_string = override.get_attribute('search')
508
510
  override.name = 'tpl:override-content' if override.name == 'tpl:inline-override'
509
511
  if (search_string)
510
512
  # # Fix Hpricot bug!
@@ -513,7 +515,7 @@ module Spider
513
515
  # end
514
516
  found = el.parent.search(search_string)
515
517
  elsif (override.name == 'tpl:content')
516
- found = el.search("tpl:placeholder[@name='#{override.attributes['name']}']")
518
+ found = el.search("tpl:placeholder[@name='#{override.get_attribute('name')}']")
517
519
  else
518
520
  found = [el]
519
521
  end
@@ -531,10 +533,10 @@ module Spider
531
533
  f.swap(override.innerHTML)
532
534
  parent.search('tpl:overridden').each{ |o| o.swap(overridden) }
533
535
  elsif (override.name == 'tpl:override-attr')
534
- f.set_attribute(override.attributes["name"], override.attributes["value"])
536
+ f.set_attribute(override.get_attribute("name"), override.get_attribute("value"))
535
537
  elsif (override.name == 'tpl:append-attr')
536
- f.set_attribute(override.attributes["name"], \
537
- (f.attributes[override.attributes["name"]] || '')+override.attributes["value"])
538
+ f.set_attribute(override.get_attribute("name"), \
539
+ (f.get_attribute(override.get_attribute("name")) || '')+override.get_attribute("value"))
538
540
  elsif (override.name == 'tpl:append')
539
541
  f.innerHTML += override.innerHTML
540
542
  elsif (override.name == 'tpl:prepend')
@@ -560,13 +562,14 @@ module Spider
560
562
 
561
563
  # Assets for the template and contained widgets.
562
564
  def all_assets
563
- res = assets
565
+ res = []
564
566
  seen = {}
565
567
  @widgets.each do |id, w|
566
568
  # next if seen[w.class]
567
569
  seen[w.class] = true
568
570
  res += w.assets
569
571
  end
572
+ res += assets
570
573
  return res
571
574
  end
572
575
 
@@ -622,4 +625,4 @@ module Spider
622
625
  class TemplateCompileError < RuntimeError
623
626
  end
624
627
 
625
- end
628
+ end