lolita 3.1.6 → 3.1.7

Sign up to get free protection for your applications and to get access to all the features.
Files changed (33) hide show
  1. data/Gemfile +1 -1
  2. data/History.rdoc +8 -1
  3. data/README.rdoc +1 -1
  4. data/VERSION +1 -1
  5. data/app/controllers/lolita/info_controller.rb +38 -0
  6. data/app/controllers/lolita/rest_controller.rb +4 -4
  7. data/app/views/components/lolita/configuration/column/_display.html.erb +1 -1
  8. data/app/views/components/lolita/configuration/column/_header.html.erb +1 -1
  9. data/app/views/components/lolita/configuration/column/_sort.html.erb +1 -1
  10. data/app/views/components/lolita/configuration/columns/_last.html.erb +2 -2
  11. data/app/views/components/lolita/configuration/field/_display.html.erb +1 -1
  12. data/app/views/components/lolita/configuration/field/_label.html.erb +1 -1
  13. data/app/views/components/lolita/configuration/list/_filter.html.erb +1 -1
  14. data/app/views/components/lolita/configuration/list/_new_resource.html.erb +1 -1
  15. data/app/views/components/lolita/configuration/list/_title.html.erb +1 -1
  16. data/app/views/components/lolita/shared/_header.html.erb +1 -1
  17. data/app/views/components/lolita/shared/_right_sidebar.html.erb +1 -1
  18. data/app/views/layouts/lolita/application.html.erb +2 -2
  19. data/app/views/lolita/info/index.html.erb +232 -0
  20. data/lib/lolita.rb +3 -0
  21. data/lib/lolita/builder.rb +218 -55
  22. data/lib/lolita/configuration/filter.rb +1 -1
  23. data/lib/lolita/configuration/tab.rb +2 -2
  24. data/lib/lolita/controllers/component_helpers.rb +4 -5
  25. data/lib/lolita/controllers/internal_helpers.rb +3 -4
  26. data/lib/lolita/rails/routes.rb +12 -4
  27. data/lolita.gemspec +9 -6
  28. data/public/javascripts/lolita/application.js +1 -0
  29. data/public/javascripts/lolita/main.js +5 -0
  30. data/spec/builder_spec.rb +97 -18
  31. data/spec/controllers/lolita_rest_spec.rb +1 -1
  32. data/spec/navigation/branch_spec.rb +0 -1
  33. metadata +117 -118
@@ -7,79 +7,242 @@ module Lolita
7
7
  # * #builder is setter/getter method for Lolita::Configuration, that accept Hash or Array or single
8
8
  # String or Symbol for buider.
9
9
  #
10
+ # Usage in your model
11
+ # You can change behaviour of any of configuraton elements, to do so you should specify what
12
+ # builder you want to use.
13
+ # lolita do
14
+ # list do
15
+ # column do
16
+ # name :my_column
17
+ # builder :name => "my_columns",:state => :display, :if=>{:state => :display}
18
+ # end
19
+ # end
20
+ # end
21
+ # This expample show, how to replace :display component of column by your own :display.
22
+ # <i>:if</i> is determine, that column use builder provided to component render, but when state is <i>:display</i>
23
+ # then it will be replaced with this on. There are elements, that only have one <i>:display</i> state, than it's
24
+ # not necessary to provide <i>:if</i> or <i>:unless</i> state.
10
25
  module Builder
11
- lolita_accessor :builder
12
-
13
- # Build response. Render component for current class with given options.
14
- def build(*args)
15
- args||=[]
16
- options=args.extract_options!
17
- builder_options=self.builder_options || {}
18
- options=(options || {}).merge(builder_options)
19
- builder_values=self.get_builder(*args)
20
- return builder_values[:name].to_sym,builder_values[:state].to_sym,options
21
- end
22
26
 
23
- # Default options for class. This method should be overwritten.
24
- def builder_options
25
- {builder_local_variable_name=>self}
26
- end
27
+ class Custom
27
28
 
28
- # Set or get builder for class.
29
- # _Value_ can be
30
- # * <tt>Hash</tt> where key <code>:name</code> is component name and <code>:state</code> is component state
31
- # * <tt>Array or two args</tt> - first is used as _name_ and second as _state_.
32
- # * <tt>String or Symbol (one arg)</tt> - is used as _name_.
33
- # Default _name_ is Lolita::Configuration class name (example <code>:list</code>) and
34
- # default state is <code>:display</code>
35
- def get_builder(*value)
36
- if value && !value.empty?
37
- builder_values_from(value)
38
- elsif @builder
39
- builder_values_from(@builder)
40
- else
41
- unless @builder
42
- default_builder
29
+ class << self
30
+ def create(element, *args)
31
+ possible_builder = extract_args(*args)
32
+ if possible_builder.is_a?(Hash)
33
+ Lolita::Builder::Custom.new(element, possible_builder)
34
+ else
35
+ possible_builder
36
+ end
37
+ end
38
+
39
+ def extract_args(*args)
40
+ if args && args.any?
41
+ options = args.extract_options! || {}
42
+ if args[0] && args[0].is_a?(self)
43
+ args[0]
44
+ elsif args[0].is_a?(String) || args[0].is_a?(Symbol)
45
+ options[:name] = args[0]
46
+ if args[1]
47
+ options[:state] = args[1]
48
+ end
49
+ options
50
+ elsif options
51
+ options
52
+ else
53
+ raise ArgumentError, "Don't know how to make builder from #{options}."
54
+ end
55
+ else
56
+ return {}
57
+ end
58
+ end
59
+ end
60
+
61
+ attr_accessor :options,:build_attributes
62
+
63
+ def initialize(element, attributes_as_hash)
64
+ @element = element
65
+ @options = {}
66
+ @build_attributes = {}
67
+ @conditions = {}
68
+ set_attributes(attributes_as_hash)
69
+ set_default_attribute_values
70
+ end
71
+
72
+ def with(*values)
73
+ new_values = self.class.extract_args(*values)
74
+ if new_values.is_a?(Hash)
75
+ @build_attributes = new_values
43
76
  else
44
- @builder
77
+ raise ArgumentError, "Can't build with other builder, use build on that builder!"
45
78
  end
79
+ self
46
80
  end
47
- end
48
81
 
49
- # Return default builder information.
50
- def default_builder
51
- {:name=>"/#{builder_name}".to_sym,:state=>default_build_state}
52
- end
53
-
54
- private
82
+ def build
83
+
84
+ path = if conditions?
85
+ switch_path do |name,state|
86
+ if conditions_met?
87
+ [fixed_name(name).to_sym,state.to_sym]
88
+ else
89
+ [self.name, self.state]
90
+ end
91
+ end
92
+ else
93
+ [self.name,self.state]
94
+ end
95
+ result = path + [merged_options]
96
+ return result
97
+ end
55
98
 
56
- def builder_values_from value
57
- if value.is_a?(Hash)
58
- value
59
- elsif value.is_a?(Array)
60
- {:name=>fix_name(value[0]),:state=>value[1] || default_build_state}
61
- else
62
- {:name=>fix_name(value),:state=>default_build_state}
99
+ def name
100
+ result = if build_attributes[:name].to_s.size > 0
101
+ fixed_name(build_attributes[:name])
102
+ else
103
+ fixed_name(@name,build_attributes[:name])
104
+ end
105
+ result.to_sym
106
+ end
107
+
108
+ def state
109
+ result = if build_attributes[:state] && build_attributes[:state].to_s.size > 0
110
+ build_attributes[:state]
111
+ else
112
+ @state
113
+ end
114
+ result.to_sym
63
115
  end
116
+
117
+ private
118
+
119
+ def switch_path
120
+ old_name = @name
121
+ old_state = @state
122
+ @name = nil
123
+ @state = default_state
124
+ result = yield old_name,old_state
125
+ @name = old_name
126
+ @state = old_state
127
+ result
128
+ end
129
+
130
+ def conditions?
131
+ @conditions.any?
132
+ end
133
+
134
+ def conditions_met?
135
+ @conditions_met = if conditions?
136
+ if @conditions[:if]
137
+ compare(@conditions[:if],true)
138
+ elsif @conditions[:unless]
139
+ compare(@conditions[:unless],false)
140
+ end
141
+ end
142
+ @conditions_met
143
+ end
144
+
145
+ def compare(pattern,predicate)
146
+ result = true
147
+ pattern.each do |key,value|
148
+ result &&= ((value.to_sym == self.send(key)) == predicate)
149
+ end
150
+ result
151
+ end
152
+
153
+ def fixed_name(name_to_fix, first_part = nil)
154
+ unless name_to_fix.to_s[0] == "/"
155
+ "/#{first_part.to_s.size > 0 ? first_part : default_name}/#{name_to_fix}".gsub(/\/{2,}/,"/").gsub(/\/$/,"")
156
+ else
157
+ name_to_fix
158
+ end
159
+ end
160
+
161
+ def default_name
162
+ @element.builder_default_name
163
+ end
164
+
165
+ def default_state
166
+ @element.builder_default_state
167
+ end
168
+
169
+ def attributes
170
+ [:name,:state]
171
+ end
172
+
173
+ def conditions
174
+ [:if,:unless]
175
+ end
176
+
177
+ def merged_options
178
+ result = {}
179
+ (@build_attributes || {}).merge(@options).each do |key,value|
180
+ unless attributes.include?(key.to_sym)
181
+ result[key.to_sym] = value
182
+ end
183
+ end
184
+ result
185
+ end
186
+
187
+ def set_attributes(attributes_as_hash)
188
+ attributes_as_hash.each do |attr_name, value|
189
+ if attributes.include?(attr_name.to_sym)
190
+ instance_variable_set(:"@#{attr_name}",value)
191
+ elsif conditions.include?(attr_name.to_sym)
192
+ @conditions[attr_name.to_sym] = value
193
+ else
194
+ @options[attr_name.to_sym] = value
195
+ end
196
+ end
197
+ end
198
+
199
+ def set_default_attribute_values
200
+ @state ||= default_state
201
+ end
202
+
64
203
  end
65
204
 
66
- def fix_name value
67
- name=if value.to_s[0] == '/'
68
- value
205
+ def builder *args
206
+ if args && args.any?
207
+ set_builder(*args)
69
208
  else
70
- "/#{builder_name}/#{value}"
209
+ @builder||=set_builder(nil)
210
+ @builder
71
211
  end
72
- name.gsub(/\/$/,"")
73
212
  end
74
213
 
75
- def default_build_state
76
- :display
214
+ def builder=(*args)
215
+ set_builder(*args)
77
216
  end
78
-
79
- def builder_name
217
+
218
+ def build *values
219
+ result = builder.with(*values).build
220
+ result[result.size-1].merge!(default_options)
221
+ result
222
+ end
223
+
224
+ def default_options
225
+ {builder_local_variable_name => self}
226
+ end
227
+
228
+ def builder_default_name
80
229
  self.class.to_s.split("::").map(&:underscore).join("/").to_sym
81
230
  end
82
-
231
+
232
+ alias :builder_name :builder_default_name
233
+
234
+ def builder_default_state
235
+ :display
236
+ end
237
+
238
+ alias :default_build_state :builder_default_state
239
+
240
+ private
241
+
242
+ def set_builder *args
243
+ @builder=Lolita::Builder::Custom.create(self,*args)
244
+ end
245
+
83
246
  def builder_local_variable_name
84
247
  self.class.to_s.split("::").last.underscore.to_sym
85
248
  end
@@ -101,7 +101,7 @@ module Lolita
101
101
 
102
102
  def html_option_for_select field
103
103
  {
104
- :include_blank => I18n.t('lolita.filter.include_blank_by_title', :title => field.title)
104
+ :include_blank => ::I18n.t('lolita.filter.include_blank_by_title', :title => field.title)
105
105
  }
106
106
  end
107
107
  end
@@ -158,8 +158,8 @@ module Lolita
158
158
  end
159
159
 
160
160
  def set_default_title
161
- if defined?(I18n)
162
- I18n.translate("lolita.tabs.titles.#{@type}")
161
+ if defined?(::I18n)
162
+ ::I18n.translate("lolita.tabs.titles.#{@type}")
163
163
  else
164
164
  @type.to_s.humanize
165
165
  end
@@ -28,7 +28,6 @@ module Lolita
28
28
  def render_component *args
29
29
  name,state,options=get_render_options(*args)
30
30
  format=options.delete(:format)
31
-
32
31
  raise "Can't render component without name!" unless name
33
32
  will_use_component name
34
33
  component_name=File.join(name.to_s,state ? state.to_s : nil)
@@ -60,12 +59,12 @@ module Lolita
60
59
  end
61
60
 
62
61
  def output_with_callbacks(partial_name,name,locals)
63
- output= Lolita::Hooks.component(name).run(:before,:run_scope=>self).to_s
64
- block_output=Lolita::Hooks.component(name).run(:around, :run_scope=>self) do
65
- render(:partial=>partial_name,:locals=>locals)
62
+ output = Lolita::Hooks.component(name).run(:before,:run_scope => self).to_s
63
+ block_output = Lolita::Hooks.component(name).run(:around, :run_scope => self) do
64
+ render(:partial => partial_name,:locals=>locals)
66
65
  end
67
66
  output << block_output.to_s
68
- output << Lolita::Hooks.component(name).run(:after,:run_scope=>self).to_s
67
+ output << Lolita::Hooks.component(name).run(:after,:run_scope => self).to_s
69
68
  output
70
69
  end
71
70
 
@@ -68,10 +68,9 @@ module Lolita
68
68
  def build_response_for(conf_part,options={})
69
69
  # FIXME when asked for some resources that always create new object, there may
70
70
  # not be any args, like lolita.report on something like that
71
-
72
- @component_options=options
73
- @component_object=resource_class.lolita.send(conf_part.to_sym)
74
- @component_builder=@component_object.build(@component_options)
71
+ @component_options = options
72
+ @component_object = resource_class.lolita.send(conf_part.to_sym)
73
+ @component_builder = @component_object.build(@component_options)
75
74
  end
76
75
 
77
76
 
@@ -12,6 +12,10 @@ module ActionDispatch::Routing
12
12
  end
13
13
  Lolita.run(:before_routes_loaded)
14
14
  draw_without_lolita *args,&block
15
+ draw_without_lolita *args, do
16
+ match '/lolita' => "lolita/info#index"
17
+ match '/lolita/info/properties' => "lolita/info#properties"
18
+ end
15
19
  Lolita.run(:after_routes_loaded)
16
20
  end
17
21
 
@@ -39,7 +43,7 @@ module ActionDispatch::Routing
39
43
  # # lolita_for try to call :lolita_gallery in Mapper class
40
44
  def lolita_for *resources
41
45
 
42
- return if migrating?
46
+ return if migrating? || generating_instalation?
43
47
  options = resources.extract_options!
44
48
 
45
49
  # if as = options.delete(:as)
@@ -91,7 +95,7 @@ module ActionDispatch::Routing
91
95
 
92
96
  tree=Lolita::Navigation::Tree[:"left_side_navigation"]
93
97
  unless tree.branches.detect{|b| b.object.is_a?(Lolita::Mapping) && b.object.to==mapping.to}
94
- tree.append(mapping,:title=>mapping.to.human_name(:count=>2))
98
+ tree.append(mapping,:title=>mapping.to.model_name.human(:count=>2))
95
99
  end
96
100
  }
97
101
  Lolita.common_routes(all_resource_classes).each do |route_name|
@@ -123,7 +127,11 @@ module ActionDispatch::Routing
123
127
  private
124
128
 
125
129
  def migrating?
126
- File.basename($0)=="rake" && (ARGV.include?("db:migrate"))
130
+ File.basename($0).match(/^rake/) && (ARGV.include?("db:migrate"))
131
+ end
132
+
133
+ def generating_instalation?
134
+ File.basename($0).match(/^rails/) && (ARGV.detect{|arg| arg.to_s.match(/lolita[^:]*:.*/)})
127
135
  end
128
136
  end
129
- end
137
+ end
data/lolita.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{lolita}
8
- s.version = "3.1.6"
8
+ s.version = "3.1.7"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["ITHouse (Latvia) and Arturs Meisters"]
12
- s.date = %q{2011-05-19}
12
+ s.date = %q{2011-06-10}
13
13
  s.description = %q{Great Rails CMS, that turns your business logic into good-looking, fully functional workspace. }
14
14
  s.email = %q{support@ithouse.lv}
15
15
  s.extra_rdoc_files = [
@@ -26,6 +26,7 @@ Gem::Specification.new do |s|
26
26
  "README.rdoc",
27
27
  "Rakefile",
28
28
  "VERSION",
29
+ "app/controllers/lolita/info_controller.rb",
29
30
  "app/controllers/lolita/rest_controller.rb",
30
31
  "app/helpers/components/lolita/configuration/list_component.rb",
31
32
  "app/helpers/lolita_helper.rb",
@@ -78,6 +79,7 @@ Gem::Specification.new do |s|
78
79
  "app/views/components/lolita/shared/_header.html.erb",
79
80
  "app/views/components/lolita/shared/_right_sidebar.html.erb",
80
81
  "app/views/layouts/lolita/application.html.erb",
82
+ "app/views/lolita/info/index.html.erb",
81
83
  "app/views/lolita/rest/form.html.erb",
82
84
  "app/views/lolita/rest/index.html.erb",
83
85
  "author",
@@ -149,6 +151,7 @@ Gem::Specification.new do |s|
149
151
  "public/images/lolita/plus.png",
150
152
  "public/javascripts/jquery-1.6.min.js",
151
153
  "public/javascripts/jquery-ui-1.8.13.min.js",
154
+ "public/javascripts/lolita/application.js",
152
155
  "public/javascripts/lolita/main.js",
153
156
  "public/javascripts/lolita/tab.js",
154
157
  "public/javascripts/modernizr-1.7.min.js",
@@ -324,7 +327,7 @@ Gem::Specification.new do |s|
324
327
  s.homepage = %q{http://github.com/ithouse/lolita}
325
328
  s.licenses = ["MIT"]
326
329
  s.require_paths = ["lib"]
327
- s.rubygems_version = %q{1.6.1}
330
+ s.rubygems_version = %q{1.6.2}
328
331
  s.summary = %q{Great Rails CMS.}
329
332
  s.test_files = [
330
333
  "spec/adapter_helper.rb",
@@ -385,7 +388,7 @@ Gem::Specification.new do |s|
385
388
 
386
389
  if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
387
390
  s.add_runtime_dependency(%q<rails>, ["~> 3.0"])
388
- s.add_runtime_dependency(%q<kaminari>, ["~> 0.11.0"])
391
+ s.add_runtime_dependency(%q<kaminari>, ["~> 0.12.4"])
389
392
  s.add_runtime_dependency(%q<abstract>, [">= 0"])
390
393
  s.add_runtime_dependency(%q<builder>, ["~> 2.1.2"])
391
394
  s.add_development_dependency(%q<jeweler>, ["~> 1.5.2"])
@@ -400,7 +403,7 @@ Gem::Specification.new do |s|
400
403
  s.add_development_dependency(%q<akephalos>, [">= 0"])
401
404
  else
402
405
  s.add_dependency(%q<rails>, ["~> 3.0"])
403
- s.add_dependency(%q<kaminari>, ["~> 0.11.0"])
406
+ s.add_dependency(%q<kaminari>, ["~> 0.12.4"])
404
407
  s.add_dependency(%q<abstract>, [">= 0"])
405
408
  s.add_dependency(%q<builder>, ["~> 2.1.2"])
406
409
  s.add_dependency(%q<jeweler>, ["~> 1.5.2"])
@@ -416,7 +419,7 @@ Gem::Specification.new do |s|
416
419
  end
417
420
  else
418
421
  s.add_dependency(%q<rails>, ["~> 3.0"])
419
- s.add_dependency(%q<kaminari>, ["~> 0.11.0"])
422
+ s.add_dependency(%q<kaminari>, ["~> 0.12.4"])
420
423
  s.add_dependency(%q<abstract>, [">= 0"])
421
424
  s.add_dependency(%q<builder>, ["~> 2.1.2"])
422
425
  s.add_dependency(%q<jeweler>, ["~> 1.5.2"])