drg_cms 0.5.50.2 → 0.5.51.1

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.
Files changed (61) hide show
  1. checksums.yaml +4 -4
  2. data/History.log +47 -0
  3. data/README.md +2 -1
  4. data/app/assets/images/32px.png +0 -0
  5. data/app/assets/images/drg_cms/32px.png +0 -0
  6. data/app/assets/images/drg_cms/40px.png +0 -0
  7. data/app/assets/images/drg_cms/throbber.gif +0 -0
  8. data/app/assets/images/throbber.gif +0 -0
  9. data/app/assets/javascripts/drg_cms/drg_cms.js +3 -3
  10. data/app/assets/javascripts/drg_cms/jstree.min.js +6 -0
  11. data/app/assets/javascripts/drg_cms_cms.js +2 -1
  12. data/app/assets/stylesheets/drg_cms/drg_cms.css +9 -0
  13. data/app/assets/stylesheets/drg_cms/jstree.css +1108 -0
  14. data/app/assets/stylesheets/drg_cms_cms.css +1 -0
  15. data/app/controllers/cmsedit_controller.rb +14 -12
  16. data/app/controllers/dc_application_controller.rb +2 -2
  17. data/app/controllers/dc_common_controller.rb +15 -20
  18. data/app/controllers/dc_page_control.rb +8 -0
  19. data/app/controllers/design_element_settings_control.rb +135 -0
  20. data/app/forms/all_options.yml +7 -1
  21. data/app/forms/cms_menu.yml +1 -1
  22. data/app/forms/dc_browse_fields.yml +1 -1
  23. data/app/forms/dc_browse_models.yml +2 -2
  24. data/app/forms/dc_category.yml +4 -4
  25. data/app/forms/dc_menu.yml +6 -0
  26. data/app/forms/dc_page.yml +22 -12
  27. data/app/forms/dc_simple_menu.yml +6 -0
  28. data/app/forms/dc_site.yml +6 -0
  29. data/app/helpers/cmsedit_helper.rb +12 -8
  30. data/app/helpers/dc_application_helper.rb +79 -18
  31. data/app/helpers/dc_menu_renderer.rb +6 -1
  32. data/app/helpers/dc_part_renderer.rb +1 -1
  33. data/app/models/concerns/dc_page_concern.rb +133 -0
  34. data/app/models/concerns/dc_piece_concern.rb +57 -0
  35. data/app/models/concerns/dc_policy_rule_concern.rb +78 -0
  36. data/app/models/concerns/dc_site_concern.rb +94 -0
  37. data/app/models/concerns/dc_user_concern.rb +130 -0
  38. data/app/models/dc_ad.rb +1 -1
  39. data/app/models/dc_big_menu.rb +1 -1
  40. data/app/models/dc_category.rb +19 -4
  41. data/app/models/dc_dummy.rb +3 -2
  42. data/app/models/dc_link.rb +1 -1
  43. data/app/models/dc_memory.rb +127 -0
  44. data/app/models/dc_menu.rb +69 -3
  45. data/app/models/dc_menu_item.rb +17 -0
  46. data/app/models/dc_page.rb +0 -106
  47. data/app/models/dc_part.rb +0 -1
  48. data/app/models/dc_piece.rb +0 -35
  49. data/app/models/dc_policy_rule.rb +0 -56
  50. data/app/models/dc_simple_menu.rb +36 -0
  51. data/app/models/dc_simple_menu_item.rb +0 -0
  52. data/app/models/dc_site.rb +1 -71
  53. data/app/models/dc_user.rb +0 -108
  54. data/app/models/drgcms_form_fields.rb +187 -26
  55. data/app/views/cmsedit/_result.html.erb +3 -4
  56. data/config/locales/models_en.yml +11 -3
  57. data/config/locales/models_sl.yml +7 -0
  58. data/lib/drg_cms.rb +1 -0
  59. data/lib/drg_cms/version.rb +1 -1
  60. data/lib/tasks/log_statistics.rb +14 -8
  61. metadata +16 -2
@@ -11,6 +11,7 @@
11
11
  *= require drg_cms/drg_cms
12
12
  *= require drg_cms/jquery.datetimepicker.css
13
13
  *= require drg_cms/select-multiple
14
+ *= require drg_cms/jstree
14
15
 
15
16
  *= require jquery-ui/all
16
17
 
@@ -234,7 +234,7 @@ def index
234
234
  return render(action: :index)
235
235
  end
236
236
  # pagination but only if not already set
237
- unless (@form['table'] == 'dc_dummy' or @records.options[:limit])
237
+ unless (@form['table'] == 'dc_memory' or @records.options[:limit])
238
238
  per_page = (@form['result_set']['per_page'] || 30).to_i
239
239
  @records = @records.page(params[:page]).per(per_page) if per_page > 0
240
240
  end
@@ -590,6 +590,11 @@ def read_drg_cms_form
590
590
  if @form['extend']
591
591
  form = YAML.load_file( dc_find_form_file(@form['extend']) )
592
592
  @form = forms_merge(form, @form)
593
+ # If combined form contains tabs and fields options, merge fields into tabs
594
+ if @form['form']['tabs'] and @form['form']['fields']
595
+ @form['form']['tabs']['fields'] = @form['form']['fields']
596
+ @form['form']['fields'] = nil
597
+ end
593
598
  end
594
599
  # add readonly key to form if readonly parameter is passed in url
595
600
  @form['readonly'] = 1 if params['readonly'] #and %w(1 yes true).include?(params['readonly'].to_s.downcase.strip)
@@ -756,7 +761,7 @@ def process_return_to(return_to)
756
761
  when return_to.match(/reload/i) then 'location.href=location.href;'
757
762
  else "location.href='#{return_to}'"
758
763
  end
759
- render text: js_tag(script)
764
+ render html: js_tag(script).html_safe, layout: false
760
765
  end
761
766
 
762
767
  ########################################################################
@@ -785,11 +790,12 @@ def save_data
785
790
  return true if fields.size == 0
786
791
  #
787
792
  fields.each do |v|
788
- next if v['type'].nil?
789
- next if v['type'].match('embedded') # don't wipe embedded fields
790
- next if params[:edit_only] and params[:edit_only] != v['name'] # otherwise other fields would be wiped
791
- next unless @record.respond_to?(v['name']) # there can be temporary fields on the form
792
- next if v['readonly'] # fields with readonly option don't retain value and would be wiped
793
+ session[:form_processing] = v['name'] # for debuging
794
+ next if v['type'].nil? or
795
+ v['type'].match('embedded') or # don't wipe embedded types
796
+ (params[:edit_only] and params[:edit_only] != v['name']) or # otherwise other fields would be wiped
797
+ v['readonly'] or # fields with readonly option don't return value and would be wiped
798
+ !@record.respond_to?(v['name']) # there can be temporary fields on the form
793
799
  # return value from form field definition
794
800
  value = DrgcmsFormFields.const_get(v['type'].camelize).get_data(params, v['name'])
795
801
  @record.send("#{v['name']}=", value)
@@ -802,17 +808,13 @@ def save_data
802
808
  # dont's save if callback method returns false
803
809
  return false if ret.class == FalseClass
804
810
  end
805
- # maybe model has dc_before_save method defined. Call it. This was before callback
806
- @record.dc_before_save(self) if @record.respond_to?('dc_before_save')
807
- #
811
+ # save data
808
812
  changes = @record.changes
809
813
  update_standards() if changes.size > 0 # update only if there has been some changes
810
814
  if (saved = @record.save)
811
815
  save_journal(operation, changes)
812
816
  # callback methods
813
817
  if (m = callback_method('after_save') ) then call_callback_method(m) end
814
- # check if model has dc_after_save method
815
- @record.dc_after_save(self) if @record.respond_to?('dc_after_save')
816
818
  end
817
819
  saved
818
820
  end
@@ -143,8 +143,8 @@ end
143
143
  # return dc_render_404('Site') unless site
144
144
  ########################################################################
145
145
  def dc_render_404(where_the_error_is=nil)
146
- render(file: "#{Rails.root}/public/404", :status => 404, :layout => false, :formats => [:html],
147
- locals: {error_is: where_the_error_is})
146
+ logger.info("Error 404: path=#{params[:path]} site=#{@site.name if @site} page=#{@page.subject if @page} design=#{@design}")
147
+ render(file: "#{Rails.root}/public/404", :status => 404, :layout => false, :formats => [:html])
148
148
  end
149
149
 
150
150
  ########################################################################
@@ -46,7 +46,7 @@ layout false
46
46
  ########################################################################
47
47
  def autocomplete
48
48
  # return '' unless session[:edit_mode] > 0 #
49
- return render text: t('drgcms.not_authorized') unless dc_user_can(DcPermission::CAN_VIEW)
49
+ return render plain: t('drgcms.not_authorized') unless dc_user_can(DcPermission::CAN_VIEW)
50
50
  # TODO Double check if previous line works as it should.
51
51
  table = params['table'].classify.constantize
52
52
  id = [params['id']] || '_id'
@@ -144,7 +144,7 @@ def login
144
144
  end
145
145
 
146
146
  ####################################################################
147
- # Action is called when restore document from journal is requested.
147
+ # Action for restoring document data from journal document.
148
148
  ####################################################################
149
149
  def restore_from_journal
150
150
  # Only administrators can perform this operation
@@ -152,17 +152,18 @@ def restore_from_journal
152
152
  return render inline: { 'msg_info' => (t ('drgcms.not_authorized')) }.to_json, formats: 'js'
153
153
  end
154
154
  # selected fields to hash
155
- restore = params[:select].inject({}) {|r,v| r[v.first] = 0 if v.last == '1'; r}
155
+ restore = {}
156
+ params[:select].each {|key,value| restore[key] = value if value == '1' }
156
157
  result = if restore.size == 0
157
158
  { 'msg_error' => (t ('drgcms.dc_journal.zero_selected')) }
158
159
  else
159
- j = DcJournal.find(params[:id])
160
+ journal_doc = DcJournal.find(params[:id])
160
161
  # update hash with data to be restored
161
- JSON.parse(j.diff).each {|k,v| restore[k] = v.first if restore[k] }
162
- # determine tables and record ids
163
- tables = j.tables.split(';')
164
- ids = (j.ids.blank? ? [] : j.ids.split(';') ) << j.doc_id
165
- # find record
162
+ JSON.parse(journal_doc.diff).each {|k,v| restore[k] = v.first if restore[k] }
163
+ # determine tables and document ids
164
+ tables = journal_doc.tables.split(';')
165
+ ids = (journal_doc.ids.blank? ? [] : journal_doc.ids.split(';') ) << journal_doc.doc_id
166
+ # find document
166
167
  doc = nil
167
168
  tables.each_index do |i|
168
169
  doc = if doc.nil?
@@ -171,11 +172,8 @@ def restore_from_journal
171
172
  doc.send(tables[i].pluralize).find(ids[i])
172
173
  end
173
174
  end
174
- # restore values
175
- restore.each do |k,v|
176
- doc.send("#{k}=",v)
177
- end
178
- # save record
175
+ # restore and save values
176
+ restore.each { |field,value| doc.send("#{field}=",value) }
179
177
  doc.save
180
178
  # TODO Error checking
181
179
  { 'msg_info' => (t ('drgcms.dc_journal.restored')) }
@@ -189,7 +187,7 @@ end
189
187
  ########################################################################
190
188
  def copy_clipboard
191
189
  # Only administrators can perform this operation
192
- return render(text: t('drgcms.not_authorized') ) unless dc_user_has_role('admin')
190
+ return render(plain: t('drgcms.not_authorized') ) unless dc_user_has_role('admin')
193
191
  #
194
192
  respond_to do |format|
195
193
  # just open new window to same url and come back with html request
@@ -198,7 +196,7 @@ def copy_clipboard
198
196
  format.html do
199
197
  doc = dc_find_document(params[:table], params[:id], params[:ids])
200
198
  text = "<br><br>[#{params[:table]},#{params[:id]},#{params[:ids]}]<br>"
201
- render text: text + doc.as_document.to_json
199
+ render plain: text + doc.as_document.to_json
202
200
  end
203
201
 
204
202
  end
@@ -211,7 +209,7 @@ end
211
209
  ########################################################################
212
210
  def paste_clipboard
213
211
  # Only administrators can perform this operation
214
- return render(text: t('drgcms.not_authorized') ) unless dc_user_has_role('admin')
212
+ return render(plain: t('drgcms.not_authorized') ) unless dc_user_has_role('admin')
215
213
 
216
214
  result = ''
217
215
  respond_to do |format|
@@ -322,9 +320,7 @@ def fill_login_data(user, remember_me)
322
320
  # check if role is active in this site
323
321
  policy_role = default_policy.dc_policy_rules.find_by(dc_policy_role_id: role.dc_policy_role_id)
324
322
  next unless policy_role
325
-
326
323
  # set edit_mode
327
- # session[:edit_mode] = 1 if policy_role.has_cms_menu
328
324
  session[:edit_mode] = 1 if policy_role.permission > 1
329
325
  session[:user_roles] << role.dc_policy_role_id
330
326
  end
@@ -335,7 +331,6 @@ def fill_login_data(user, remember_me)
335
331
  guest = DcUserRole.find_by(:system_name => 'guest')
336
332
  session[:user_roles] << guest.id if guest
337
333
  end
338
-
339
334
  # Save remember me cookie if not CMS user and remember me is selected
340
335
  if session[:edit_mode] == 0 and remember_me
341
336
  cookies.signed[:remember_me] = { :value => user.id, :expires => 180.days.from_now}
@@ -40,4 +40,12 @@ def dc_new_record()
40
40
  end
41
41
  end
42
42
 
43
+ ######################################################################
44
+ # Caled just after record is saved to DB.
45
+ ######################################################################
46
+ def dc_after_save()
47
+ menu_class = dc_get_site.menu_class.classify.constantize
48
+ menu_class.update_menu_item_link(@record.menu_id, @record.subject_link)
49
+ end
50
+
43
51
  end
@@ -0,0 +1,135 @@
1
+ #encoding: utf-8
2
+ #--
3
+ # Copyright (c) 2014+ Damjan Rems
4
+ #
5
+ # Permission is hereby granted, free of charge, to any person obtaining
6
+ # a copy of this software and associated documentation files (the
7
+ # "Software"), to deal in the Software without restriction, including
8
+ # without limitation the rights to use, copy, modify, merge, publish,
9
+ # distribute, sublicense, and/or sell copies of the Software, and to
10
+ # permit persons to whom the Software is furnished to do so, subject to
11
+ # the following conditions:
12
+ #
13
+ # The above copyright notice and this permission notice shall be
14
+ # included in all copies or substantial portions of the Software.
15
+ #
16
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23
+ #++
24
+
25
+ ######################################################################
26
+ # DrgcmsControls for editing settings in a document.
27
+ #
28
+ # Parameters to settings call:
29
+ # :location - model_name where settings document is located. Typicaly dc_page or dc_site.
30
+ # :field_name - name of the field where settings are saved
31
+ # :element - element name as defined on design
32
+ # :id - document id
33
+ ######################################################################
34
+ module DesignElementSettingsControl
35
+
36
+ ######################################################################
37
+ # Check if settings control document exists and return document and
38
+ # settings values as yaml string.
39
+ #
40
+ # Return:
41
+ # [document, data] : Mongoid document, yaml as String
42
+ ######################################################################
43
+ def get_settings()
44
+ # On save. Set required variables
45
+ if params[:record]
46
+ params[:location] = params[:record][:dc_location]
47
+ params[:field_name] = params[:record][:dc_field_name]
48
+ params[:element] = params[:record][:dc_element]
49
+ params[:id] = params[:record][:dc_document_id]
50
+ end
51
+ # Check model
52
+ begin
53
+ model = params[:location].classify.constantize
54
+ rescue
55
+ flash[:error] = 'Invalid or undefined model name!'
56
+ return false
57
+ end
58
+ # Check fild name
59
+ begin
60
+ document = model.find(params[:id])
61
+ params[:field_name] = case
62
+ when params[:location] == 'dc_page' then 'params'
63
+ when params[:location] == 'dc_site' then 'options'
64
+ otherwise params[:field_name]
65
+ end
66
+ # field not defined on document
67
+ raise unless document.respond_to?(params[:field_name])
68
+ yaml = document[params[:field_name]]
69
+ yaml = '' if yaml.blank?
70
+ rescue
71
+ flash[:error] = 'Invalid or undefined field name!'
72
+ return false
73
+ end
74
+ # Check data
75
+ begin
76
+ data = YAML.load(yaml) || {}
77
+ rescue
78
+ flash[:error] = 'Invalid configuration data found!'
79
+ return false
80
+ end
81
+ [document, data]
82
+ end
83
+
84
+ ######################################################################
85
+ # Called before edit.
86
+ #
87
+ # Load fields on form with values from settings document.
88
+ ######################################################################
89
+ def dc_new_record()
90
+ document, data = get_settings
91
+ return false if document.class == FalseClass and data.nil?
92
+ # fill values with settings values
93
+ if data['settings'] and data['settings'][ params[:element] ]
94
+ data['settings'][ params[:element] ].each { |key, value| @record.send("#{key}=", value) }
95
+ end
96
+ # add some fields required at post as hidden fields to form
97
+ form = @form['form']['tabs'] ? @form['form']['tabs'].to_a.last : @form['form']['fields']
98
+ form[9999] = {'type' => 'hidden_field', 'name' => 'dc_location', 'html' => {'value' => params[:location]}}
99
+ form[9998] = {'type' => 'hidden_field', 'name' => 'dc_field_name'}
100
+ @record[:dc_field_name] = params[:field_name]
101
+ form[9997] = {'type' => 'hidden_field', 'name' => 'dc_element'}
102
+ @record.dc_element = params[:element]
103
+ form[9996] = {'type' => 'hidden_field', 'name' => 'dc_document_id', 'html' => {'value' => params[:id]}}
104
+ true
105
+ end
106
+
107
+ ######################################################################
108
+ # Called before save.
109
+ #
110
+ # Convert data from fields on form to yaml and save it to document settings field.
111
+ ######################################################################
112
+ def dc_before_save()
113
+ document, data = get_settings
114
+ return false if document.class == FalseClass and data.nil?
115
+ #
116
+ fields_on_form.each do |v|
117
+ session[:form_processing] = v['name'] # for debuging
118
+ next if v['type'].nil? or
119
+ v['readonly'] # fields with readonly option don't return value and would be wiped
120
+ # return value from form field definition
121
+ value = DrgcmsFormFields.const_get(v['type'].camelize).get_data(params, v['name'])
122
+ data['settings'] ||= {}
123
+ data['settings'][ params[:element] ] ||= {}
124
+ data['settings'][ params[:element] ][ v['name'] ] = value
125
+ end
126
+ # save data to document field
127
+ document.send("#{params[:field_name]}=", data.to_yaml)
128
+ document.save
129
+ # to re-set form again
130
+ dc_new_record
131
+ false # must be
132
+ end
133
+
134
+
135
+ end
@@ -202,4 +202,10 @@ form:
202
202
  field: custumer_name
203
203
  method: search
204
204
  with_new: customer
205
- size: 50
205
+ size: 50
206
+ 50:
207
+ name: kats
208
+ type: tree_select
209
+ eval: "DcCategory.choices4_categories(@parent.dc_get_site)"
210
+ style: 'max-height: 300px'
211
+
@@ -128,5 +128,5 @@ menu:
128
128
  caption: drgcms.browse_collections
129
129
  controller: cmsedit
130
130
  icon: table lg
131
- table: dc_dummy
131
+ table: dc_memory
132
132
  formname: dc_browse_models
@@ -1,6 +1,6 @@
1
1
  ## Registration form. Not yet implemented.
2
2
  ---
3
- table: dc_dummy
3
+ table: dc_memory
4
4
  title: Browse field definitions
5
5
  controls: browse_models
6
6
  permissions:
@@ -1,6 +1,6 @@
1
1
  ## Registration form. Not yet implemented.
2
2
  ---
3
- table: dc_dummy
3
+ table: dc_memory
4
4
  title: Browse collection models
5
5
  controls: browse_models
6
6
  permissions:
@@ -11,7 +11,7 @@ result_set:
11
11
 
12
12
  dblclick:
13
13
  type: link
14
- table: dc_dummy
14
+ table: dc_memory
15
15
  formname: dc_browse_fields
16
16
  action: index
17
17
 
@@ -50,15 +50,15 @@ form:
50
50
  html:
51
51
  size: 5
52
52
  50:
53
- name: parent
53
+ name: dc_site_id
54
54
  type: select
55
- eval: DcCategory.values_for_parent
55
+ eval: DcSite.choices4_site
56
56
  html:
57
57
  include_blank: true
58
58
  60:
59
- name: dc_site_id
59
+ name: parent
60
60
  type: select
61
- eval: DcSite.choices4_site
61
+ eval: DcCategory.values_for_parent
62
62
  html:
63
63
  include_blank: true
64
64
 
@@ -51,6 +51,12 @@ form:
51
51
  type: text_field
52
52
  html:
53
53
  size: 20
54
+ 50:
55
+ name: dc_site_id
56
+ type: select
57
+ eval: DcSite.choices4_site
58
+ html:
59
+ include_blank: true
54
60
 
55
61
  tab2:
56
62
  10:
@@ -87,18 +87,20 @@ form:
87
87
  type: datetime_select
88
88
  options:
89
89
  include_blank: true
90
+ # 120:
91
+ # name: kats
92
+ # type: select
93
+ # multiple: true
94
+ # eval: "dc_choices4('DcCategory','name','_id',site: :with_nil)"
95
+ # html:
96
+ # include_blank: true
97
+ # size: 4
90
98
  120:
91
99
  name: kats
92
- # type: multitext_autocomplete
93
- # search: dc_category.name
94
- # html:
95
- # size: 30
96
- type: select
97
- multiple: true
98
- eval: "dc_choices4('DcCategory','name','_id',site: :with_nil)"
99
- html:
100
- include_blank: true
101
- size: 4
100
+ type: tree_select
101
+ eval: "DcCategory.choices4_categories(@parent.dc_get_site)"
102
+ style: 'max-height: 300px'
103
+
102
104
 
103
105
  2advanced:
104
106
  10:
@@ -107,10 +109,18 @@ form:
107
109
  eval: DcDesign.choices4_design(@parent.dc_get_site)
108
110
  html:
109
111
  include_blank: true
112
+
110
113
  20:
111
114
  name: menu_id
112
- type: select
113
- eval: dc_choices4_menu
115
+ type: tree_select
116
+ eval: '@parent.dc_menu_class.choices4_menu_as_tree(@record.dc_site_id)'
117
+ style: 'max-height: 300px'
118
+ single: true
119
+
120
+ # 20:
121
+ # name: menu_id
122
+ # type: select
123
+ # eval: dc_choices4_menu
114
124
 
115
125
  30:
116
126
  name: params