agile_rails 0.0.0.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 (259) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGELOG.md +5 -0
  3. data/MIT-LICENSE +20 -0
  4. data/README.md +285 -0
  5. data/Rakefile +39 -0
  6. data/agile_rails.gemspec +36 -0
  7. data/app/assets/fonts/ibm-plex-sans-300.woff2 +0 -0
  8. data/app/assets/fonts/ibm-plex-sans-400.woff2 +0 -0
  9. data/app/assets/fonts/ibm-plex-sans-500.woff2 +0 -0
  10. data/app/assets/fonts/ibm-plex-sans-600.woff2 +0 -0
  11. data/app/assets/fonts/ibm-plex-sans-700.woff2 +0 -0
  12. data/app/assets/fonts/ibm-plex-sans-italic.woff2 +0 -0
  13. data/app/assets/images/32px.png +0 -0
  14. data/app/assets/images/throbber.gif +0 -0
  15. data/app/assets/javascripts/agile/agile.js +1489 -0
  16. data/app/assets/javascripts/agile/jquery-migrate.js +702 -0
  17. data/app/assets/javascripts/agile/jquery.bpopup.js +372 -0
  18. data/app/assets/javascripts/agile/jquery.datetimepicker.js +1353 -0
  19. data/app/assets/javascripts/agile/jstree.min.js +6 -0
  20. data/app/assets/javascripts/agile/select-multiple.js +459 -0
  21. data/app/assets/javascripts/agile/some_scripts.js +33 -0
  22. data/app/assets/javascripts/agile.js +22 -0
  23. data/app/assets/javascripts/agile_application.js +22 -0
  24. data/app/assets/javascripts/agile_editor.js +22 -0
  25. data/app/assets/stylesheets/agile/agile.css +1882 -0
  26. data/app/assets/stylesheets/agile/agile_apps.css +149 -0
  27. data/app/assets/stylesheets/agile/jquery.datetimepicker.css +304 -0
  28. data/app/assets/stylesheets/agile/jstree.css +1107 -0
  29. data/app/assets/stylesheets/agile/select-multiple.css +110 -0
  30. data/app/assets/stylesheets/agile/th-bg.png +0 -0
  31. data/app/assets/stylesheets/agile/theme.css +49 -0
  32. data/app/assets/stylesheets/agile.css +21 -0
  33. data/app/assets/stylesheets/agile_application.css +20 -0
  34. data/app/assets/stylesheets/agile_editor.css +19 -0
  35. data/app/controllers/agile_application_controller.rb +735 -0
  36. data/app/controllers/agile_common_controller.rb +345 -0
  37. data/app/controllers/agile_controller.rb +977 -0
  38. data/app/controllers/agile_main_controller.rb +36 -0
  39. data/app/controls/agile_control.rb +120 -0
  40. data/app/controls/agile_report.rb +364 -0
  41. data/app/controls/ar_category_control.rb +39 -0
  42. data/app/controls/ar_help_control.rb +139 -0
  43. data/app/controls/ar_image_control.rb +180 -0
  44. data/app/controls/ar_journal_control.rb +47 -0
  45. data/app/controls/ar_menu_item_control.rb +55 -0
  46. data/app/controls/ar_page_control.rb +64 -0
  47. data/app/controls/ar_poll_result_control.rb +84 -0
  48. data/app/controls/ar_setup_control.rb +62 -0
  49. data/app/controls/belongs_to_control.rb +61 -0
  50. data/app/controls/browse_models_control.rb +98 -0
  51. data/app/controls/settings_form_control.rb +137 -0
  52. data/app/forms/agile_help.yml +112 -0
  53. data/app/forms/agile_menu.yml +140 -0
  54. data/app/forms/agile_report_defaults.yml +39 -0
  55. data/app/forms/all_options.yml +810 -0
  56. data/app/forms/ar_ad.yml +121 -0
  57. data/app/forms/ar_big_table.yml +60 -0
  58. data/app/forms/ar_big_table_value.yml +52 -0
  59. data/app/forms/ar_browse_fields.yml +35 -0
  60. data/app/forms/ar_browse_models.yml +48 -0
  61. data/app/forms/ar_category.yml +73 -0
  62. data/app/forms/ar_category_as_tree.yml +31 -0
  63. data/app/forms/ar_design.yml +75 -0
  64. data/app/forms/ar_filter.yml +52 -0
  65. data/app/forms/ar_folder_permission.yml +56 -0
  66. data/app/forms/ar_folder_rule.yml +48 -0
  67. data/app/forms/ar_gallery.yml +55 -0
  68. data/app/forms/ar_image.yml +126 -0
  69. data/app/forms/ar_image_search.yml +83 -0
  70. data/app/forms/ar_journal.yml +76 -0
  71. data/app/forms/ar_json_ld.yml +56 -0
  72. data/app/forms/ar_key_value.yml +33 -0
  73. data/app/forms/ar_key_value_store.yml +33 -0
  74. data/app/forms/ar_link.yml +60 -0
  75. data/app/forms/ar_menu.yml +67 -0
  76. data/app/forms/ar_menu_item.yml +141 -0
  77. data/app/forms/ar_page.yml +187 -0
  78. data/app/forms/ar_part.yml +91 -0
  79. data/app/forms/ar_permission.yml +52 -0
  80. data/app/forms/ar_permission_rule.yml +40 -0
  81. data/app/forms/ar_piece.yml +106 -0
  82. data/app/forms/ar_policy.yml +64 -0
  83. data/app/forms/ar_policy_rule.yml +42 -0
  84. data/app/forms/ar_policy_rule_nocms.yml +40 -0
  85. data/app/forms/ar_poll.yml +118 -0
  86. data/app/forms/ar_poll_item.yml +78 -0
  87. data/app/forms/ar_poll_result.yml +88 -0
  88. data/app/forms/ar_poll_result_export.yml +35 -0
  89. data/app/forms/ar_removed_url.yml +41 -0
  90. data/app/forms/ar_role.yml +43 -0
  91. data/app/forms/ar_seo.yml +32 -0
  92. data/app/forms/ar_setup.yml +45 -0
  93. data/app/forms/ar_site.yml +149 -0
  94. data/app/forms/ar_steps_template.yml +51 -0
  95. data/app/forms/ar_user.yml +140 -0
  96. data/app/forms/ar_user_role.yml +57 -0
  97. data/app/forms/help/dc_category_as_tree.en +4 -0
  98. data/app/forms/help/dc_category_as_tree.sl +5 -0
  99. data/app/forms/json_ld_schema.yml +168 -0
  100. data/app/helpers/agile_application_helper.rb +1162 -0
  101. data/app/helpers/agile_category_helper.rb +128 -0
  102. data/app/helpers/agile_common_helper.rb +308 -0
  103. data/app/helpers/agile_edit_helper.rb +645 -0
  104. data/app/helpers/agile_helper.rb +509 -0
  105. data/app/helpers/agile_index_helper.rb +677 -0
  106. data/app/helpers/ar_image_helper.rb +128 -0
  107. data/app/models/agile_form_fields/action.rb +61 -0
  108. data/app/models/agile_form_fields/agile_form_field.rb +322 -0
  109. data/app/models/agile_form_fields/belongs_to.rb +112 -0
  110. data/app/models/agile_form_fields/check_box.rb +73 -0
  111. data/app/models/agile_form_fields/comment.rb +62 -0
  112. data/app/models/agile_form_fields/date_picker.rb +104 -0
  113. data/app/models/agile_form_fields/date_select.rb +68 -0
  114. data/app/models/agile_form_fields/datetime_picker.rb +88 -0
  115. data/app/models/agile_form_fields/datetime_select.rb +73 -0
  116. data/app/models/agile_form_fields/file_field.rb +52 -0
  117. data/app/models/agile_form_fields/file_select.rb +69 -0
  118. data/app/models/agile_form_fields/hidden_field.rb +51 -0
  119. data/app/models/agile_form_fields/html_field.rb +69 -0
  120. data/app/models/agile_form_fields/journal_diff.rb +62 -0
  121. data/app/models/agile_form_fields/link_to.rb +69 -0
  122. data/app/models/agile_form_fields/method.rb +66 -0
  123. data/app/models/agile_form_fields/multitext_autocomplete.rb +215 -0
  124. data/app/models/agile_form_fields/number_field.rb +92 -0
  125. data/app/models/agile_form_fields/password_field.rb +63 -0
  126. data/app/models/agile_form_fields/radio_button.rb +95 -0
  127. data/app/models/agile_form_fields/readonly.rb +77 -0
  128. data/app/models/agile_form_fields/select.rb +281 -0
  129. data/app/models/agile_form_fields/submit_tag.rb +58 -0
  130. data/app/models/agile_form_fields/text_area.rb +61 -0
  131. data/app/models/agile_form_fields/text_autocomplete.rb +171 -0
  132. data/app/models/agile_form_fields/text_field.rb +55 -0
  133. data/app/models/agile_form_fields/text_with_select.rb +94 -0
  134. data/app/models/agile_form_fields/tree_select.rb +170 -0
  135. data/app/models/ar_big_table.rb +82 -0
  136. data/app/models/ar_big_table_value.rb +53 -0
  137. data/app/models/ar_category.rb +109 -0
  138. data/app/models/ar_design.rb +116 -0
  139. data/app/models/ar_filter.rb +200 -0
  140. data/app/models/ar_folder_permission.rb +50 -0
  141. data/app/models/ar_folder_rule.rb +47 -0
  142. data/app/models/ar_gallery.rb +53 -0
  143. data/app/models/ar_image.rb +198 -0
  144. data/app/models/ar_internals.rb +60 -0
  145. data/app/models/ar_journal.rb +46 -0
  146. data/app/models/ar_json_ld.rb +131 -0
  147. data/app/models/ar_key_value_store.rb +128 -0
  148. data/app/models/ar_link.rb +48 -0
  149. data/app/models/ar_memory.rb +172 -0
  150. data/app/models/ar_menu.rb +144 -0
  151. data/app/models/ar_menu_item.rb +106 -0
  152. data/app/models/ar_page.rb +74 -0
  153. data/app/models/ar_part.rb +66 -0
  154. data/app/models/ar_permission.rb +180 -0
  155. data/app/models/ar_permission_rule.rb +65 -0
  156. data/app/models/ar_policy.rb +78 -0
  157. data/app/models/ar_policy_rule.rb +65 -0
  158. data/app/models/ar_poll.rb +74 -0
  159. data/app/models/ar_poll_item.rb +47 -0
  160. data/app/models/ar_poll_result.rb +38 -0
  161. data/app/models/ar_removed_url.rb +42 -0
  162. data/app/models/ar_role.rb +84 -0
  163. data/app/models/ar_setup.rb +115 -0
  164. data/app/models/ar_site.rb +68 -0
  165. data/app/models/ar_temp.rb +150 -0
  166. data/app/models/ar_user.rb +72 -0
  167. data/app/models/ar_user_group.rb +38 -0
  168. data/app/models/ar_user_role.rb +54 -0
  169. data/app/models/ar_visit.rb +41 -0
  170. data/app/models/concerns/ar_page_concern.rb +128 -0
  171. data/app/models/concerns/ar_part_concern.rb +48 -0
  172. data/app/models/concerns/ar_piece_concern.rb +48 -0
  173. data/app/models/concerns/ar_policy_rule_concern.rb +87 -0
  174. data/app/models/concerns/ar_seo_concern.rb +66 -0
  175. data/app/models/concerns/ar_site_concern.rb +103 -0
  176. data/app/models/concerns/ar_user_concern.rb +195 -0
  177. data/app/renderers/agile_common_renderer.rb +93 -0
  178. data/app/renderers/agile_renderer.rb +59 -0
  179. data/app/renderers/ar_ad_renderer.rb +219 -0
  180. data/app/renderers/ar_captcha_renderer.rb +113 -0
  181. data/app/renderers/ar_common_renderer.rb +90 -0
  182. data/app/renderers/ar_gallery_renderer.rb +107 -0
  183. data/app/renderers/ar_menu_renderer.rb +195 -0
  184. data/app/renderers/ar_page_renderer.rb +147 -0
  185. data/app/renderers/ar_part_renderer.rb +235 -0
  186. data/app/renderers/ar_piece_renderer.rb +119 -0
  187. data/app/renderers/ar_poll_renderer.rb +272 -0
  188. data/app/views/agile/_edit_stuff.html.erb +57 -0
  189. data/app/views/agile/_form.html.erb +24 -0
  190. data/app/views/agile/_result.html.erb +28 -0
  191. data/app/views/agile/edit.html.erb +13 -0
  192. data/app/views/agile/error.html.erb +2 -0
  193. data/app/views/agile/index.html.erb +14 -0
  194. data/app/views/agile/login.html.erb +19 -0
  195. data/app/views/agile/new.html.erb +12 -0
  196. data/app/views/agile_common/_help.html.erb +18 -0
  197. data/app/views/agile_common/_iframe_edit.html.erb +2 -0
  198. data/app/views/agile_common/paste_clipboard.html.erb +17 -0
  199. data/app/views/layouts/agile.html.erb +17 -0
  200. data/app/views/layouts/content.html.erb +20 -0
  201. data/app/views/models/dump_models.html.erb +47 -0
  202. data/config/initializers/kaminari_patch.rb +56 -0
  203. data/config/locales/agile_de.yml +138 -0
  204. data/config/locales/agile_en.yml +162 -0
  205. data/config/locales/agile_sl.yml +163 -0
  206. data/config/locales/datetimepicker.yml +19 -0
  207. data/config/locales/de.yml +231 -0
  208. data/config/locales/en.yml +13 -0
  209. data/config/locales/kaminari.yml +26 -0
  210. data/config/locales/models_en.yml +1032 -0
  211. data/config/locales/models_sl.yml +1065 -0
  212. data/config/locales/sl.yml +211 -0
  213. data/db/migrate/20240120160001_add_sessions_table.rb +12 -0
  214. data/db/migrate/20240120160002_ar_big_table.rb +17 -0
  215. data/db/migrate/20240120160003_ar_big_table_value.rb +18 -0
  216. data/db/migrate/20240120160004_ar_category.rb +22 -0
  217. data/db/migrate/20240120160005_ar_design.rb +20 -0
  218. data/db/migrate/20240120160006_ar_filter.rb +17 -0
  219. data/db/migrate/20240120160007_ar_gallery.rb +21 -0
  220. data/db/migrate/20240120160008_ar_journal.rb +19 -0
  221. data/db/migrate/20240120160009_ar_key_value_store.rb +11 -0
  222. data/db/migrate/20240120160010_ar_link.rb +19 -0
  223. data/db/migrate/20240120160011_ar_memory.rb +8 -0
  224. data/db/migrate/20240120160012_ar_menu.rb +21 -0
  225. data/db/migrate/20240120160013_ar_menu_item.rb +28 -0
  226. data/db/migrate/20240120160014_ar_page.rb +50 -0
  227. data/db/migrate/20240120160015_ar_part.rb +33 -0
  228. data/db/migrate/20240120160016_ar_permission.rb +16 -0
  229. data/db/migrate/20240120160017_ar_permission_rule.rb +17 -0
  230. data/db/migrate/20240120160018_ar_piece.rb +28 -0
  231. data/db/migrate/20240120160019_ar_policy.rb +21 -0
  232. data/db/migrate/20240120160020_ar_policy_rule.rb +18 -0
  233. data/db/migrate/20240120160021_ar_poll.rb +27 -0
  234. data/db/migrate/20240120160022_ar_poll_item.rb +23 -0
  235. data/db/migrate/20240120160023_ar_poll_result.rb +14 -0
  236. data/db/migrate/20240120160024_ar_removed_url.rb +16 -0
  237. data/db/migrate/20240120160025_ar_role.rb +17 -0
  238. data/db/migrate/20240120160026_ar_site.rb +37 -0
  239. data/db/migrate/20240120160027_ar_temp.rb +11 -0
  240. data/db/migrate/20240120160028_ar_user.rb +42 -0
  241. data/db/migrate/20240120160029_ar_user_group.rb +12 -0
  242. data/db/migrate/20240120160030_ar_user_role.rb +18 -0
  243. data/db/migrate/20240120160031_ar_visit.rb +15 -0
  244. data/db/migrate/20240703016001_ar_setup.rb +16 -0
  245. data/db/migrate/20240703016002_ar_folder_permission.rb +15 -0
  246. data/db/migrate/20240703016003_ar_folder_rule.rb +14 -0
  247. data/db/migrate/20250115000001_ar_image.rb +25 -0
  248. data/lib/agile/configuration.rb +43 -0
  249. data/lib/agile/engine.rb +29 -0
  250. data/lib/agile/version.rb +27 -0
  251. data/lib/agile.rb +282 -0
  252. data/lib/agile_rails.rb +1 -0
  253. data/lib/generators/agile/USAGE +11 -0
  254. data/lib/generators/agile/new_form_generator.rb +369 -0
  255. data/lib/generators/convert_to_ar/convert_to_ar_generator.rb +158 -0
  256. data/lib/tasks/agile_db_clone.rake +132 -0
  257. data/lib/tasks/agile_db_export_to_yaml.rake +37 -0
  258. data/lib/tasks/agile_db_migrate.rake +35 -0
  259. metadata +414 -0
@@ -0,0 +1,171 @@
1
+ #--
2
+ # Copyright (c) 2024+ Damjan Rems
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining
5
+ # a copy of this software and associated documentation files (the
6
+ # "Software"), to deal in the Software without restriction, including
7
+ # without limitation the rights to use, copy, modify, merge, publish,
8
+ # distribute, sublicense, and/or sell copies of the Software, and to
9
+ # permit persons to whom the Software is furnished to do so, subject to
10
+ # the following conditions:
11
+ #
12
+ # The above copyright notice and this permission notice shall be
13
+ # included in all copies or substantial portions of the Software.
14
+ #
15
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+ #+
23
+ module AgileFormFields
24
+
25
+ ###########################################################################
26
+ # Implementation of text_autocomplete AgileRails form field.
27
+ #
28
+ # ===Form options:
29
+ # * +name:+ field name (required)
30
+ # * +type:+ text_autocomplete (required)
31
+ # * +table+ Collection (table) name. When defined search must contain field name
32
+ # * +with_new+ Will add an icon for shortcut to add new document to related collection
33
+ # * +with_edit+ Will add an icon for shortcut to edit (view) related document
34
+ # * +is_id+ Field value represent value as id. If false, field will use entered value and not value selected with autocomplete. Default is true.
35
+ # * +search:+ Search may consist of three parameters from which are separated either by dot (.)
36
+ # * search_field_name; when table option is defined search must define field name which will be used for search query
37
+ # * collection_name.search_field_name; Same as above except that table options must be ommited.
38
+ # * collection_name.search_field_name.method_name; When searching is more complex custom search
39
+ # method may be defined in CollectionName model which will provide dataset for search.
40
+ #
41
+ # Form example:
42
+ # 10:
43
+ # name: user_id
44
+ # type: text_autocomplete
45
+ # search: ar_user.name
46
+ # is_id: false
47
+ # size: 30
48
+ # with_new: user
49
+ # with_edit: user
50
+ ###########################################################################
51
+ class TextAutocomplete < AgileFormField
52
+
53
+ ###########################################################################
54
+ # Render text_autocomplete AgileRails form field code
55
+ ###########################################################################
56
+ def render
57
+ # Return descriptive text and put it into input field
58
+ # search field name
59
+ if @yaml['search'].class.to_s == 'Hash'
60
+ table = @yaml['search']['table']
61
+ ret_name = @yaml['search']['field']
62
+ method = @yaml['search']['method']
63
+ elsif @yaml['search'].match(/\.|\,| /)
64
+ table, ret_name, method = @yaml['search'].split(/\.|\,| /).map(&:strip)
65
+ else
66
+ ret_name = @yaml['search']
67
+ end
68
+ # determine table name
69
+ if @yaml['table']
70
+ table = if @yaml['table'].is_a?(String)
71
+ @yaml['table']
72
+ elsif @yaml['table']['eval']
73
+ eval @yaml['table']['eval']
74
+ else
75
+ Rails.logger.error "Field #{ @yaml['name'] }: Invalid table parameter!"
76
+ nil
77
+ end
78
+ end
79
+ return ro_standard 'Table or field keyword not defined!' unless (table && ret_name)
80
+ # TODO check if table exists
81
+ model_klass = table.classify.constantize
82
+ # find record and return value of field
83
+ value_send_as = 'p_' + @yaml['name']
84
+ value = if @env.params[value_send_as]
85
+ @env.params[value_send_as]
86
+ elsif @record && @record[@yaml['name']]
87
+ @record[@yaml['name']]
88
+ end
89
+ not_id = @env.agile_dont?(@yaml['is_id'], false)
90
+
91
+ # Found value to be written in field. If field is not found write out value.
92
+ value_displayed = value
93
+ if value && !not_id
94
+ if value.class == Integer
95
+ record = model_klass.find(value)
96
+ value_displayed = record.send(ret_name) if record
97
+ else
98
+ value_displayed = model_klass.send(ret_name, method, @env, value)
99
+ end
100
+ end
101
+ return ro_standard(value_displayed) if @readonly
102
+
103
+ # Add method back, so autocomplete will know that it must search for method inside class
104
+ ret_name = "#{ret_name}.#{method}" if method
105
+ @yaml['html'] ||= {}
106
+ @yaml['html']['value'] = value_displayed
107
+ @yaml['html']['placeholder'] ||= t('agile.search_placeholder') || nil
108
+
109
+ _name = '_' + @yaml['name']
110
+ record = record_text_for(@yaml['name'])
111
+ @html += '<span class="ar-text-autocomplete">' + @env.text_field(record, _name, @yaml['html']) + '<span></span>'
112
+ # with new icon
113
+ if @yaml['with_new'] && !@readonly
114
+ @html += ' ' + @env.mi_icon('plus-square-o', class: 'in-edit-add', title: t('agile.new'),
115
+ style: "vertical-align: top;", 'data-table' => @yaml['with_new'] )
116
+ end
117
+ # with edit icon
118
+ if @yaml['with_edit'] && @record && @record[@yaml['name']].present? && !@readonly
119
+ @html += ' ' + @env.mi_icon('edit-o', class: 'in-edit-add', title: t('agile.edit'),
120
+ style: "vertical-align: top;", 'data-table' => @yaml['with_edit'], 'data-id' => @record[@yaml['name']] )
121
+ end
122
+ @html += '</span>' + @env.hidden_field(record, @yaml['name'], value: value) # actual value will be in hidden field
123
+
124
+ # JS stuff
125
+ # allow unselected values on is_id: false option
126
+ not_id_code = %(
127
+ if (ui.item == null) {
128
+ $("##{record}_#{@yaml['name']}").val($("##{record}__#{@yaml['name']}").val() );
129
+ return;
130
+ } ) if not_id
131
+
132
+ @js = <<EOJS
133
+ $(document).ready(function() {
134
+ $("##{record}_#{_name}").autocomplete( {
135
+ source: function(request, response) {
136
+ $.ajax({
137
+ url: "/agile/autocomplete",
138
+ type: "POST",
139
+ dataType: "json",
140
+ data: { input: request.term, table: "#{table}", search: "#{ret_name}" #{(',id: "'+@yaml['id'] + '"') if @yaml['id']} },
141
+ success: function(data) {
142
+ response( $.map( data, function(key) {
143
+ return key;
144
+ }));
145
+ }
146
+ });
147
+ },
148
+
149
+ change: function (event, ui) {
150
+ #{not_id_code}
151
+ if (ui.item == null) return;
152
+ $("##{record}_#{@yaml['name']}").val(ui.item.id).trigger('change');
153
+ },
154
+
155
+ minLength: 2
156
+ });
157
+ });
158
+ EOJS
159
+
160
+ self
161
+ end
162
+
163
+ ###########################################################################
164
+ # Return value. Return nil if input field is empty
165
+ ###########################################################################
166
+ def self.get_data(params, name)
167
+ params['record']["_#{name}"].blank? ? nil : params['record'][name]
168
+ end
169
+
170
+ end
171
+ end
@@ -0,0 +1,55 @@
1
+ #--
2
+ # Copyright (c) 2024+ Damjan Rems
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining
5
+ # a copy of this software and associated documentation files (the
6
+ # "Software"), to deal in the Software without restriction, including
7
+ # without limitation the rights to use, copy, modify, merge, publish,
8
+ # distribute, sublicense, and/or sell copies of the Software, and to
9
+ # permit persons to whom the Software is furnished to do so, subject to
10
+ # the following conditions:
11
+ #
12
+ # The above copyright notice and this permission notice shall be
13
+ # included in all copies or substantial portions of the Software.
14
+ #
15
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+ #+
23
+ module AgileFormFields
24
+
25
+ ###########################################################################
26
+ # Implementation of text_field AgileRails form field.
27
+ #
28
+ # ===Form options:
29
+ # * +type:+ text_field (required)
30
+ # * +name:+ Field name (required)
31
+ # * +html:+ html options which apply to text_field field (optional)
32
+ #
33
+ # Form example:
34
+ # 10:
35
+ # name: title
36
+ # type: text_field
37
+ # size: 30
38
+ # html:
39
+ # required: yes
40
+ ###########################################################################
41
+ class TextField < AgileFormField
42
+
43
+ ###########################################################################
44
+ # Render text_field AgileRails form field code
45
+ ###########################################################################
46
+ def render
47
+ set_initial_value
48
+
49
+ record = record_text_for(@yaml['name'])
50
+ @html += @env.text_field( record, @yaml['name'], @yaml['html'])
51
+ self
52
+ end
53
+
54
+ end
55
+ end
@@ -0,0 +1,94 @@
1
+ #--
2
+ # Copyright (c) 2024+ Damjan Rems
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining
5
+ # a copy of this software and associated documentation files (the
6
+ # "Software"), to deal in the Software without restriction, including
7
+ # without limitation the rights to use, copy, modify, merge, publish,
8
+ # distribute, sublicense, and/or sell copies of the Software, and to
9
+ # permit persons to whom the Software is furnished to do so, subject to
10
+ # the following conditions:
11
+ #
12
+ # The above copyright notice and this permission notice shall be
13
+ # included in all copies or substantial portions of the Software.
14
+ #
15
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+ #+
23
+ module AgileFormFields
24
+
25
+ ###########################################################################
26
+ # Implementation of text_with_select AgileRails form field. Field will provide
27
+ # text_field entry field with select dropdown box with optional values for the field.
28
+ # Form options are mostly same as in select field.
29
+ #
30
+ # ===Form options:
31
+ # * +name:+ field name (required)
32
+ # * +type:+ text_with_select (required)
33
+ # * +choices:+ Values for choices separated by comma. Values can also be specified like description:value.
34
+ # In this case description will be shown to user, but value will be saved to document.
35
+ # choices: 'OK:0,Ready:1,Error:2'
36
+ # choices: Ruby,Pyton,PHP
37
+ # * +choices: eval+ Choices will be provided by evaluating expression
38
+ # choices: eval agile_choices_for('model_name','description_field_name','_id'); agile_choices_for helper will provide data for select field.
39
+ # choices: eval ModelName.choices_for_field; ModelName class will define method choices_for_field which
40
+ # will provide data for select field. Since expression is evaluated in the context of Form Field object
41
+ # Even session session variables can be accessed.
42
+ # choices: eval MyClass.method(@env.session[:user_id])
43
+ # When searching is more complex custom search method may be defined in CollectionName
44
+ # model which will provide dataset for search.
45
+ # choices: eval collection_name.search_field_name.method_name;
46
+ # If choices or eval is not defined choices will be provided from translation helpers. For example:
47
+ # Collection has field status. Choices for field will be provided by en.helpers.model_name.choices_for_status
48
+ # entry of english translation. English is of course default translation. If you provide translations in
49
+ # your local language then select choices will be localized.
50
+ # en.helpers.model_name.choices_for_status: 'OK:0,Ready:1,Error:2'
51
+ # sl.helpers.model_name.choices_for_status: 'V redu:0,Pripravljen:1,Napaka:2'
52
+ # * +html:+ html options which apply to select and text_field fields (optional)
53
+ #
54
+ # Form example:
55
+ # 10:
56
+ # name: link
57
+ # type: text_with_select
58
+ # choices: eval @env.agile_page_class.all_pages_for_site(@env.agile_get_site)
59
+ # size: 50
60
+ ###########################################################################
61
+ class TextWithSelect < Select
62
+
63
+ ###########################################################################
64
+ # Render text_with_select AgileRails form field code
65
+ ###########################################################################
66
+ def render
67
+ set_initial_value('html','value')
68
+
69
+ record = record_text_for(@yaml['name'])
70
+ @html += @env.text_field( record, @yaml['name'], @yaml['html'])
71
+ @yaml['html']['class'] ||= ''
72
+ @yaml['html']['class'] += ' text-with-select'
73
+ @yaml['html'].symbolize_keys!
74
+ unless @readonly
75
+ @html += @env.select( @yaml['name'] + '_', nil, get_choices, { include_blank: true }, { class: 'text-with-select' })
76
+ end
77
+
78
+ # javascript to update text field if new value is selected in select field
79
+ @js =<<EOJS
80
+ $(document).ready(function() {
81
+ $('##{@yaml['name']}_').change( function() {
82
+ if ($(this).val().toString().length > 0) {
83
+ $('##{record}_#{@yaml['name']}').val( $(this).val() );
84
+ $('##{record}_#{@yaml['name']}').trigger("change");
85
+ }
86
+ $('##{record}_#{@yaml['name']}').focus();
87
+ });
88
+ });
89
+ EOJS
90
+ self
91
+ end
92
+
93
+ end
94
+ end
@@ -0,0 +1,170 @@
1
+ #--
2
+ # Copyright (c) 2024+ Damjan Rems
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining
5
+ # a copy of this software and associated documentation files (the
6
+ # "Software"), to deal in the Software without restriction, including
7
+ # without limitation the rights to use, copy, modify, merge, publish,
8
+ # distribute, sublicense, and/or sell copies of the Software, and to
9
+ # permit persons to whom the Software is furnished to do so, subject to
10
+ # the following conditions:
11
+ #
12
+ # The above copyright notice and this permission notice shall be
13
+ # included in all copies or substantial portions of the Software.
14
+ #
15
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+ #+
23
+ module AgileFormFields
24
+
25
+ ###########################################################################
26
+ # Implementation of tree_select AgileRails form field. Field will provides
27
+ # multiple select functionality displayed as a tree. Might be used for selecting
28
+ # multiple categories in a env-child tree view.#
29
+ #
30
+ # ===Form options:
31
+ # * +name:+ field name (required)
32
+ # * +type:+ tree_select (required)
33
+ # * +choices:+ Values for choices separated by comma. Values can also be specified like description:value.
34
+ # In this case description will be shown to user, but value will be saved to document.
35
+ # choices: 'OK:0,Ready:1,Error:2'
36
+ # choices: Ruby,Pyton,PHP
37
+ # * +eval:+ Choices will be provided by evaluating expression
38
+ # choices: eval ModelName.choices_for_field; Model class should define method which will provide data for field.
39
+ # Data returned must be of type Array and have 3 elements.
40
+ # 1 - description text
41
+ # 2 - id values separated by ;
42
+ # 3 - parent id
43
+ # 4 - order
44
+ # * +html:+ html options which apply to select and text_field fields (optional)
45
+ #
46
+ # Form example:
47
+ # 10:
48
+ # name: categories
49
+ # type: tree_select
50
+ # choices: eval Categories.all_categories
51
+ # multiple: true
52
+ # parent_disabled: false
53
+ # parent_opened: false
54
+ # size: 50x10
55
+ ###########################################################################
56
+ class TreeSelect < Select
57
+
58
+ ###########################################################################
59
+ # Prepare choices for AgileRails form field rendering.
60
+ ###########################################################################
61
+ def make_tree(parent)
62
+ return '' unless @choices[parent.to_s]
63
+
64
+ @html += '<ul>'
65
+ choices = if @choices[parent.to_s].first[3] != 0
66
+ @choices[parent.to_s].sort_by { _1[3].to_i } # sort by order if first is not 0
67
+ else
68
+ #@choices[parent.to_s].sort_alphabetical_by(&:first) # use UTF-8 sort
69
+ @choices[parent.to_s].sort_by(&:first)
70
+ end
71
+ choices.each do |choice|
72
+ data = [%("selected" : #{choice.last ? 'true' : 'false'} )]
73
+ # only for parent objects
74
+ if @choices[ choice[1].to_s ]
75
+ # parent is not selectable
76
+ data += '"disabled" : true' unless @env.agile_dont?(@yaml['parent_disabled'], true)
77
+ # parents are opened on start
78
+ data += '"opened" : true' unless @env.agile_dont?(@yaml['parent_opened'], true)
79
+ end
80
+ # data-jstree must be singe quoted
81
+ @html += %(<li data-id="#{choice[1]}" data-jstree='{#{data.join(' , ')}}'>#{choice.first}\n)
82
+ # call recursively for children
83
+ make_tree(choice[1]) if @choices[choice[1].to_s]
84
+ @html += '</li>'
85
+ end
86
+ @html + '</ul>'
87
+ end
88
+
89
+ ###########################################################################
90
+ # Render tree_select field html code
91
+ ###########################################################################
92
+ def render
93
+ set_initial_value('html','value')
94
+ record = record_text_for(@yaml['name'])
95
+ clas = 'tree-select' + (@readonly ? ' ar-readonly' : '')
96
+ @html += %(<div id="#{@yaml['name']}" class="#{clas}" #{set_style()} >)
97
+
98
+ # Create @choices hash. The key is parent object id
99
+ @choices = {}
100
+ choices_in_eval(@yaml['choices']).each do |data|
101
+ @choices[ data[2].to_s ] ||= []
102
+ @choices[ data[2].to_s ] << (data << false)
103
+ end
104
+ # Set last element of hash to true when selected. To speed up selection when there is a lot of items
105
+ current_values = {}
106
+ current = @record.send(@yaml['name']) || []
107
+ current = [current] unless current.is_a?(Array) # non array fields
108
+ current.each { |e| current_values[e.to_s] = true }
109
+
110
+ # set third element of @choices when selected
111
+ @choices.keys.each do |key|
112
+ 0.upto( @choices[key].size - 1 ) do |i|
113
+ choice = @choices[key][i]
114
+ choice[choice.size - 1] = true if current_values[ choice[1].to_s ]
115
+ end
116
+ end
117
+ make_tree(nil)
118
+ @html += '</div>'
119
+ # add hidden communication field
120
+ @html += @env.hidden_field(record, @yaml['name'], value: current.join(','))
121
+ # save multiple indicator for data processing on return
122
+ @html += @env.hidden_field(record, "#{@yaml['name']}_multiple", value: 1) if @yaml['multiple']
123
+ # javascript to update hidden record field when tree looses focus
124
+ readonly_code = %(
125
+ ,
126
+ "conditionalselect" : function (node) {
127
+ return false; }
128
+ )
129
+
130
+ @js =<<~EOJS
131
+ $(function(){
132
+ $("##{@yaml['name']}").jstree( {
133
+ "checkbox" : {"three_state" : false},
134
+ "core" : { "themes" : { "icons": false },
135
+ "multiple" : #{@yaml['multiple'] ? 'true' : 'false'} },
136
+ "plugins" : ["checkbox", "conditionalselect"]
137
+ #{@readonly ? readonly_code : ''}
138
+ });
139
+ });
140
+
141
+ $(document).ready(function() {
142
+ $('##{@yaml['name']}').on('focusout', function(e) {
143
+ var checked_ids = [];
144
+ var checked = $('##{@yaml['name']}').jstree("get_checked", true);
145
+ $.each(checked, function() {
146
+ checked_ids.push( this.data.id );
147
+ });
148
+ $('#record_#{@yaml['name']}').val( checked_ids.join(",") );
149
+ });
150
+ });
151
+ EOJS
152
+ self
153
+ end
154
+
155
+ ###########################################################################
156
+ # Return value. Return nil if input field is empty
157
+ ###########################################################################
158
+ def self.get_data(params, name)
159
+ return nil if params['record'][name].blank?
160
+
161
+ result = params['record'][name].split(',')
162
+ result.delete_if(&:blank?)
163
+ return nil if result.size == 0
164
+
165
+ # return only first element if multiple values select was not allowed
166
+ params['record']["#{name}_multiple"] == '1' ? result : result.first
167
+ end
168
+
169
+ end
170
+ end
@@ -0,0 +1,82 @@
1
+ #--
2
+ # Copyright (c) 2024+ Damjan Rems
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining
5
+ # a copy of this software and associated documentation files (the
6
+ # "Software"), to deal in the Software without restriction, including
7
+ # without limitation the rights to use, copy, modify, merge, publish,
8
+ # distribute, sublicense, and/or sell copies of the Software, and to
9
+ # permit persons to whom the Software is furnished to do so, subject to
10
+ # the following conditions:
11
+ #
12
+ # The above copyright notice and this permission notice shall be
13
+ # included in all copies or substantial portions of the Software.
14
+ #
15
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+ #+
23
+
24
+ ##########################################################################
25
+ # == Schema information
26
+ #
27
+ # Table name: ar_big_table : Big Table
28
+ #
29
+ # id Integer id
30
+ # created_at Time created_at
31
+ # updated_at Time updated_at
32
+ # key String Key (ident) used to retrieve key/values
33
+ # description String description
34
+ # site_id Integer Data will be used only for defined site. If empty, then it is default for all sites in database.
35
+ # active Boolean This key is active
36
+ # created_by Integer created_by
37
+ # updated_by Integer updated_by
38
+ # ar_big_table_values Embedded: ArBigTableValue Values defined by this key
39
+ #
40
+ # Big table is meant to be a common space for defining default choices for select fields on forms.
41
+ # Documents are organized as key-value pair with the difference that values for the key can
42
+ # be defined for each site and can also be localized.
43
+ #
44
+ # Usage (as used in forms):
45
+ #
46
+ # In the example administrator may help user by providing values that can be used
47
+ # on ArAd document position field by defining them in ads-position key of big table.
48
+ # Example is from ar_ads.yml form.
49
+ #
50
+ # 10:
51
+ # name: position
52
+ # type: text_with_select
53
+ # eval: ar_big_table 'ads-positions'
54
+ # size: 20
55
+ #
56
+ ##########################################################################
57
+ class ArBigTable < ApplicationRecord
58
+
59
+ has_many :ar_big_table_values
60
+
61
+ validates :key, presence: true
62
+ validates :description, presence: true
63
+
64
+ ########################################################################
65
+ # Will return possible choices for specified key prepared for usage in select input field.
66
+ ########################################################################
67
+ def self.choices_for(key, site = nil, locale = nil)
68
+ result = []
69
+ data = find_by(key: key, site_id: site)
70
+ data ||= find_by(key: key, site_id: nil) if site
71
+ if data
72
+ data.ar_big_table_values.order(description: 'asc').each do |one_value|
73
+ next unless one_value.active
74
+
75
+ description = one_value.get_localized_description(locale)
76
+ result << [description, one_value.value]
77
+ end
78
+ end
79
+ result.empty? ? [nil] : result
80
+ end
81
+
82
+ end
@@ -0,0 +1,53 @@
1
+ #--
2
+ # Copyright (c) 2024+ Damjan Rems
3
+ #
4
+ # Permission is hereby granted, free of charge, to any person obtaining
5
+ # a copy of this software and associated documentation files (the
6
+ # "Software"), to deal in the Software without restriction, including
7
+ # without limitation the rights to use, copy, modify, merge, publish,
8
+ # distribute, sublicense, and/or sell copies of the Software, and to
9
+ # permit persons to whom the Software is furnished to do so, subject to
10
+ # the following conditions:
11
+ #
12
+ # The above copyright notice and this permission notice shall be
13
+ # included in all copies or substantial portions of the Software.
14
+ #
15
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17
+ # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19
+ # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20
+ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21
+ # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22
+ #+
23
+
24
+ #####################################################################
25
+ # == Schema information
26
+ #
27
+ # Table name: ar_big_table_value : Big Table - values
28
+ #
29
+ # id Integer id
30
+ # created_at Time created_at
31
+ # updated_at Time updated_at
32
+ # value String Value to be returned
33
+ # locales String Translations written in YAML as en: English
34
+ # sl: Slovensko
35
+ # active Boolean Is Active
36
+ # created_by Integer created_by
37
+ # updated_by Integer updated_by
38
+ # ar_big_table_id Integer
39
+ #
40
+ # Documents are embedded in ArBigTable document. Every value defined has its own description,
41
+ # which can further be translated in embedded ArBigTableLocale documents.
42
+ #####################################################################
43
+ class ArBigTableValue < ApplicationRecord
44
+ belongs_to :ar_big_table
45
+
46
+ validates :value, presence: true
47
+
48
+ def get_localized_description(locale = I18n.locale.to_s)
49
+ hash = YAML.load(locales) rescue {}
50
+ hash&.dig(locale) || (description.blank? ? value : description)
51
+ end
52
+
53
+ end