avo 2.45.0 → 3.0.0.pre1

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of avo might be problematic. Click here for more details.

Files changed (415) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +23 -22
  3. data/Gemfile.lock +181 -160
  4. data/README.md +1 -1
  5. data/{public/avo-assets → app/assets/builds}/avo.base.css +479 -698
  6. data/app/assets/builds/avo.base.js +93804 -0
  7. data/app/assets/builds/avo.base.js.map +7 -0
  8. data/app/assets/stylesheets/avo.base.css +2 -2
  9. data/app/assets/svgs/failed_to_load.svg +1 -0
  10. data/app/assets/svgs/font.svg +1 -0
  11. data/app/assets/svgs/grid-empty-state.svg +1 -0
  12. data/app/assets/svgs/table-empty-state.svg +1 -0
  13. data/app/assets/svgs/triangle-up.svg +1 -0
  14. data/app/components/avo/actions_component.html.erb +18 -4
  15. data/app/components/avo/actions_component.rb +12 -18
  16. data/app/components/avo/alert_component.html.erb +1 -1
  17. data/app/components/avo/asset_manager/javascript_component.html.erb +3 -0
  18. data/app/components/avo/asset_manager/javascript_component.rb +13 -0
  19. data/app/components/avo/asset_manager/stylesheet_component.html.erb +3 -0
  20. data/app/components/avo/asset_manager/stylesheet_component.rb +13 -0
  21. data/app/components/avo/base_component.rb +14 -11
  22. data/app/components/avo/button_component.rb +20 -3
  23. data/app/components/avo/empty_state_component.rb +1 -1
  24. data/app/components/avo/field_wrapper_component.html.erb +4 -4
  25. data/app/components/avo/field_wrapper_component.rb +9 -9
  26. data/app/components/avo/fields/belongs_to_field/edit_component.html.erb +96 -118
  27. data/app/components/avo/fields/belongs_to_field/edit_component.rb +5 -20
  28. data/app/components/avo/fields/belongs_to_field/index_component.html.erb +1 -1
  29. data/app/components/avo/fields/belongs_to_field/show_component.rb +2 -2
  30. data/app/components/avo/fields/boolean_field/edit_component.html.erb +1 -2
  31. data/app/components/avo/fields/boolean_group_field/edit_component.html.erb +3 -3
  32. data/app/components/avo/fields/code_field/edit_component.html.erb +0 -1
  33. data/app/components/avo/fields/common/badge_viewer_component.html.erb +24 -1
  34. data/app/components/avo/fields/common/badge_viewer_component.rb +0 -24
  35. data/app/components/avo/fields/common/boolean_group_component.html.erb +2 -2
  36. data/app/components/avo/fields/common/files_list_viewer_component.html.erb +5 -0
  37. data/app/components/avo/fields/common/files_list_viewer_component.rb +8 -0
  38. data/app/components/avo/fields/common/heading_component.html.erb +1 -1
  39. data/app/components/avo/fields/common/single_file_viewer_component.html.erb +56 -0
  40. data/app/components/avo/fields/common/single_file_viewer_component.rb +55 -0
  41. data/app/components/avo/fields/country_field/edit_component.html.erb +1 -3
  42. data/app/components/avo/fields/edit_component.rb +1 -1
  43. data/app/components/avo/fields/file_field/edit_component.html.erb +2 -4
  44. data/app/components/avo/fields/file_field/edit_component.rb +0 -1
  45. data/app/components/avo/fields/file_field/index_component.rb +2 -2
  46. data/app/components/avo/fields/file_field/show_component.html.erb +1 -1
  47. data/app/components/avo/fields/files_field/edit_component.html.erb +2 -4
  48. data/app/components/avo/fields/files_field/edit_component.rb +0 -1
  49. data/app/components/avo/fields/files_field/show_component.html.erb +1 -1
  50. data/app/components/avo/fields/has_many_field/show_component.html.erb +1 -1
  51. data/app/components/avo/fields/has_one_field/index_component.html.erb +1 -1
  52. data/app/components/avo/fields/has_one_field/show_component.html.erb +2 -2
  53. data/app/components/avo/fields/has_one_field/show_component.rb +3 -7
  54. data/app/components/avo/fields/index_component.rb +5 -6
  55. data/app/components/avo/fields/markdown_field/edit_component.html.erb +3 -4
  56. data/app/components/avo/fields/markdown_field/show_component.html.erb +3 -3
  57. data/app/components/avo/fields/number_field/edit_component.html.erb +1 -3
  58. data/app/components/avo/fields/password_field/edit_component.html.erb +1 -3
  59. data/app/components/avo/fields/preview_field/index_component.html.erb +10 -0
  60. data/app/components/avo/fields/preview_field/index_component.rb +4 -0
  61. data/app/components/avo/fields/progress_bar_field/edit_component.html.erb +0 -1
  62. data/app/components/avo/fields/select_field/edit_component.html.erb +2 -3
  63. data/app/components/avo/fields/show_component.rb +4 -1
  64. data/app/components/avo/fields/status_field/edit_component.html.erb +1 -1
  65. data/app/components/avo/fields/text_field/edit_component.html.erb +2 -3
  66. data/app/components/avo/fields/textarea_field/edit_component.html.erb +0 -1
  67. data/app/components/avo/fields/trix_field/edit_component.html.erb +1 -2
  68. data/app/components/avo/fields/trix_field/edit_component.rb +1 -1
  69. data/app/components/avo/fields/trix_field/show_component.html.erb +1 -1
  70. data/app/components/avo/filters_component.html.erb +9 -3
  71. data/app/components/avo/filters_component.rb +4 -4
  72. data/app/components/avo/index/field_wrapper_component.html.erb +1 -1
  73. data/app/components/avo/index/grid_item_component.html.erb +5 -2
  74. data/app/components/avo/index/grid_item_component.rb +7 -6
  75. data/app/components/avo/index/resource_controls_component.html.erb +3 -81
  76. data/app/components/avo/index/resource_controls_component.rb +128 -18
  77. data/app/components/avo/index/resource_grid_component.html.erb +5 -3
  78. data/app/components/avo/index/resource_grid_component.rb +5 -2
  79. data/app/components/avo/index/resource_table_component.html.erb +5 -4
  80. data/app/components/avo/index/resource_table_component.rb +14 -20
  81. data/app/components/avo/index/table_row_component.html.erb +8 -4
  82. data/app/components/avo/index/table_row_component.rb +3 -2
  83. data/app/components/avo/item_switcher_component.html.erb +5 -10
  84. data/app/components/avo/item_switcher_component.rb +2 -3
  85. data/app/components/avo/modal_component.html.erb +7 -12
  86. data/app/components/avo/modal_component.rb +0 -21
  87. data/app/components/avo/paginator_component.html.erb +40 -29
  88. data/app/components/avo/paginator_component.rb +5 -23
  89. data/app/components/avo/panel_component.html.erb +8 -11
  90. data/app/components/avo/panel_component.rb +0 -1
  91. data/app/components/avo/profile_item_component.html.erb +2 -17
  92. data/app/components/avo/profile_item_component.rb +1 -13
  93. data/app/components/avo/referrer_params_component.html.erb +1 -4
  94. data/app/components/avo/resource_component.rb +142 -30
  95. data/app/components/avo/resource_sidebar_component.html.erb +6 -2
  96. data/app/components/avo/sidebar/link_component.html.erb +0 -2
  97. data/app/components/avo/sidebar/link_component.rb +3 -5
  98. data/app/components/avo/sidebar_component.html.erb +9 -2
  99. data/app/components/avo/sidebar_component.rb +5 -3
  100. data/app/components/avo/sidebar_profile_component.html.erb +27 -20
  101. data/app/components/avo/tab_group_component.html.erb +13 -7
  102. data/app/components/avo/tab_group_component.rb +1 -6
  103. data/app/components/avo/tab_switcher_component.html.erb +17 -40
  104. data/app/components/avo/tab_switcher_component.rb +4 -39
  105. data/app/components/avo/views/resource_edit_component.html.erb +16 -52
  106. data/app/components/avo/views/resource_edit_component.rb +7 -18
  107. data/app/components/avo/views/resource_index_component.html.erb +38 -53
  108. data/app/components/avo/views/resource_index_component.rb +60 -16
  109. data/app/components/avo/views/resource_show_component.html.erb +8 -151
  110. data/app/components/avo/views/resource_show_component.rb +6 -11
  111. data/app/controllers/avo/actions_controller.rb +19 -16
  112. data/app/controllers/avo/application_controller.rb +40 -109
  113. data/app/controllers/avo/associations_controller.rb +34 -41
  114. data/app/controllers/avo/attachments_controller.rb +10 -25
  115. data/app/controllers/avo/base_controller.rb +91 -103
  116. data/app/controllers/avo/debug_controller.rb +17 -5
  117. data/app/controllers/avo/search_controller.rb +29 -54
  118. data/app/controllers/avo/team_users_controller.rb +4 -0
  119. data/app/controllers/concerns/avo/initializes_avo.rb +26 -0
  120. data/app/helpers/avo/application_helper.rb +20 -21
  121. data/app/helpers/avo/resources_helper.rb +1 -1
  122. data/app/helpers/avo/url_helpers.rb +27 -11
  123. data/app/javascript/avo.base.js +1 -0
  124. data/app/javascript/js/application.js +0 -5
  125. data/app/javascript/js/controllers/action_controller.js +5 -3
  126. data/app/javascript/js/controllers/actions_overflow_controller.js +62 -0
  127. data/app/javascript/js/controllers/fields/{easy_mde_controller.js → simple_mde_controller.js} +3 -4
  128. data/app/javascript/js/controllers/filter_controller.js +1 -1
  129. data/app/javascript/js/controllers/input_autofocus_controller.js +12 -0
  130. data/app/javascript/js/controllers/preview_controller.js +24 -0
  131. data/app/javascript/js/controllers/search_controller.js +1 -3
  132. data/app/javascript/js/controllers/self_destroy_controller.js +7 -0
  133. data/app/javascript/js/controllers/toggle_controller.js +48 -0
  134. data/app/javascript/js/controllers.js +12 -8
  135. data/app/javascript/js/custom-stream-actions.js +15 -0
  136. data/app/views/avo/{attachments/destroy.turbo_stream.erb → actions/keep_modal_open.turbo_stream.erb} +0 -2
  137. data/app/views/avo/actions/show.html.erb +11 -10
  138. data/app/views/avo/associations/new.html.erb +4 -4
  139. data/app/views/avo/base/index.html.erb +3 -2
  140. data/app/views/avo/base/new.html.erb +2 -1
  141. data/app/views/avo/base/preview.html.erb +19 -0
  142. data/app/views/avo/base/show.html.erb +1 -1
  143. data/app/views/avo/debug/_valid_indicator.html.erb +9 -0
  144. data/app/views/avo/debug/report.html.erb +32 -17
  145. data/app/views/avo/debug/{index.html.erb → status.html.erb} +31 -15
  146. data/app/views/avo/home/index.html.erb +1 -1
  147. data/app/views/avo/partials/_custom_tools_alert.html.erb +2 -2
  148. data/app/views/avo/partials/_javascript.html.erb +5 -0
  149. data/app/views/avo/partials/_logo.html.erb +1 -1
  150. data/app/views/avo/partials/_navbar.html.erb +3 -5
  151. data/app/views/avo/partials/_table_header.html.erb +5 -3
  152. data/app/views/avo/partials/_view_toggle_button.html.erb +0 -9
  153. data/app/views/avo/private/design.html.erb +2 -2
  154. data/app/views/layouts/avo/application.html.erb +3 -0
  155. data/avo.gemspec +6 -7
  156. data/bin/dev +1 -1
  157. data/bin/prod +0 -0
  158. data/config/i18n-tasks.yml +1 -1
  159. data/config/initializers/pagy.rb +10 -14
  160. data/config/master.key +1 -0
  161. data/config/routes.rb +8 -12
  162. data/db/factories.rb +7 -18
  163. data/lib/avo/action_model.rb +20 -0
  164. data/lib/avo/app.rb +90 -162
  165. data/lib/avo/asset_manager.rb +30 -0
  166. data/lib/avo/base_action.rb +38 -35
  167. data/lib/avo/base_resource.rb +107 -95
  168. data/lib/avo/base_resource_tool.rb +9 -16
  169. data/lib/avo/concerns/{can_replace_fields.rb → can_replace_items.rb} +3 -3
  170. data/lib/avo/concerns/filters_session_handler.rb +1 -0
  171. data/lib/avo/concerns/has_controls.rb +37 -0
  172. data/lib/avo/concerns/has_item_type.rb +38 -0
  173. data/lib/avo/concerns/{has_fields.rb → has_items.rb} +110 -97
  174. data/lib/avo/concerns/is_resource_item.rb +24 -36
  175. data/lib/avo/concerns/is_visible.rb +15 -0
  176. data/lib/avo/concerns/visible_in_different_views.rb +126 -0
  177. data/lib/avo/configuration/branding.rb +0 -12
  178. data/lib/avo/configuration.rb +8 -45
  179. data/lib/avo/current.rb +5 -0
  180. data/lib/avo/dsl/field_parser.rb +1 -1
  181. data/lib/avo/dynamic_router.rb +6 -2
  182. data/lib/avo/engine.rb +37 -30
  183. data/lib/avo/error_manager.rb +25 -0
  184. data/lib/avo/execution_context.rb +9 -15
  185. data/lib/avo/fields/badge_field.rb +1 -1
  186. data/lib/avo/fields/base_field.rb +72 -123
  187. data/lib/avo/fields/belongs_to_field.rb +14 -25
  188. data/lib/avo/fields/concerns/handles_field_args.rb +49 -0
  189. data/lib/avo/fields/concerns/has_default.rb +1 -5
  190. data/lib/avo/fields/concerns/has_field_name.rb +22 -0
  191. data/lib/avo/fields/concerns/has_html_attributes.rb +110 -0
  192. data/lib/avo/fields/concerns/is_disabled.rb +1 -5
  193. data/lib/avo/fields/concerns/is_readonly.rb +1 -5
  194. data/lib/avo/fields/concerns/is_required.rb +5 -7
  195. data/lib/avo/fields/concerns/is_searchable.rb +13 -0
  196. data/lib/avo/fields/concerns/use_resource.rb +5 -1
  197. data/lib/avo/fields/country_field.rb +4 -0
  198. data/lib/avo/fields/date_field.rb +3 -16
  199. data/lib/avo/fields/date_time_field.rb +1 -5
  200. data/lib/avo/fields/field_manager.rb +45 -0
  201. data/lib/avo/fields/file_field.rb +0 -2
  202. data/lib/avo/fields/files_field.rb +0 -6
  203. data/lib/avo/fields/has_and_belongs_to_many_field.rb +1 -2
  204. data/lib/avo/fields/has_base_field.rb +11 -14
  205. data/lib/avo/fields/has_many_field.rb +5 -2
  206. data/lib/avo/fields/has_one_field.rb +5 -10
  207. data/lib/avo/fields/heading_field.rb +4 -1
  208. data/lib/avo/fields/hidden_field.rb +1 -1
  209. data/lib/avo/fields/id_field.rb +2 -3
  210. data/lib/avo/fields/password_field.rb +1 -1
  211. data/lib/avo/fields/preview_field.rb +14 -0
  212. data/lib/avo/fields/select_field.rb +12 -8
  213. data/lib/avo/fields/status_field.rb +4 -0
  214. data/lib/avo/filters/base_filter.rb +3 -8
  215. data/lib/avo/grid_collector.rb +7 -9
  216. data/lib/avo/html/builder.rb +5 -8
  217. data/lib/avo/item_grapher.rb +78 -0
  218. data/lib/avo/licensing/h_q.rb +3 -67
  219. data/lib/avo/licensing/license.rb +2 -2
  220. data/lib/avo/licensing/license_manager.rb +1 -1
  221. data/lib/avo/licensing/{nil_license.rb → null_license.rb} +1 -1
  222. data/lib/avo/licensing/pro_license.rb +1 -7
  223. data/lib/avo/plugin.rb +6 -0
  224. data/lib/avo/plugin_manager.rb +58 -0
  225. data/lib/avo/prefixed_test_helpers.rb +20 -0
  226. data/lib/avo/reloader.rb +3 -0
  227. data/lib/avo/resources/controls/actions_list.rb +6 -12
  228. data/lib/avo/resources/controls/attach_button.rb +15 -0
  229. data/lib/avo/resources/controls/back_button.rb +1 -1
  230. data/lib/avo/resources/controls/base_control.rb +15 -49
  231. data/lib/avo/resources/controls/create_button.rb +15 -0
  232. data/lib/avo/resources/controls/delete_button.rb +5 -1
  233. data/lib/avo/resources/controls/detach_button.rb +4 -1
  234. data/lib/avo/resources/controls/edit_button.rb +4 -1
  235. data/lib/avo/resources/controls/order_controls.rb +8 -0
  236. data/lib/avo/resources/controls/save_button.rb +13 -0
  237. data/lib/avo/resources/controls/show_button.rb +15 -0
  238. data/lib/avo/resources/items/holder.rb +76 -0
  239. data/lib/avo/resources/items/item_group.rb +48 -0
  240. data/lib/avo/resources/items/main_panel.rb +2 -0
  241. data/lib/avo/resources/items/panel.rb +2 -0
  242. data/lib/avo/resources/items/sidebar.rb +47 -0
  243. data/lib/avo/resources/items/tab.rb +60 -0
  244. data/lib/avo/resources/items/tab_group.rb +68 -0
  245. data/lib/avo/resources/resource_manager.rb +181 -0
  246. data/lib/avo/services/authorization_service.rb +11 -110
  247. data/lib/avo/services/debug_service.rb +92 -0
  248. data/lib/avo/services/telemetry_service.rb +84 -0
  249. data/lib/avo/test_helpers.rb +362 -0
  250. data/lib/avo/tools/tool_manager.rb +30 -0
  251. data/lib/avo/version.rb +1 -1
  252. data/lib/avo.rb +7 -0
  253. data/lib/generators/avo/eject_generator.rb +0 -1
  254. data/lib/generators/avo/install_generator.rb +1 -11
  255. data/lib/generators/avo/resource_generator.rb +5 -23
  256. data/lib/generators/avo/scope_generator.rb +15 -0
  257. data/lib/generators/avo/tailwindcss/install_generator.rb +1 -18
  258. data/lib/generators/avo/templates/action.tt +1 -1
  259. data/lib/generators/avo/templates/cards/chartkick_card.tt +1 -1
  260. data/lib/generators/avo/templates/cards/chartkick_card_sample.tt +1 -1
  261. data/lib/generators/avo/templates/cards/metric_card.tt +1 -1
  262. data/lib/generators/avo/templates/cards/metric_card_sample.tt +1 -1
  263. data/lib/generators/avo/templates/cards/partial_card.tt +1 -1
  264. data/lib/generators/avo/templates/cards/partial_card_sample.tt +1 -1
  265. data/lib/generators/avo/templates/dashboards/dashboard.tt +1 -1
  266. data/lib/generators/avo/templates/field/%singular_name%_field.rb.tt +1 -1
  267. data/lib/generators/avo/templates/filters/boolean_filter.tt +1 -1
  268. data/lib/generators/avo/templates/filters/multiple_select_filter.tt +1 -1
  269. data/lib/generators/avo/templates/filters/select_filter.tt +1 -1
  270. data/lib/generators/avo/templates/filters/text_filter.tt +1 -1
  271. data/lib/generators/avo/templates/initializer/avo.tt +1 -11
  272. data/lib/generators/avo/templates/locales/avo.ar.yml +5 -5
  273. data/lib/generators/avo/templates/locales/avo.en.yml +4 -5
  274. data/lib/generators/avo/templates/locales/avo.fr.yml +1 -2
  275. data/lib/generators/avo/templates/locales/avo.nb.yml +1 -2
  276. data/lib/generators/avo/templates/locales/avo.nn.yml +1 -2
  277. data/lib/generators/avo/templates/locales/avo.pt-BR.yml +1 -2
  278. data/lib/generators/avo/templates/locales/avo.pt.yml +1 -2
  279. data/lib/generators/avo/templates/locales/avo.ro.yml +6 -7
  280. data/lib/generators/avo/templates/locales/avo.tr.yml +1 -2
  281. data/lib/generators/avo/templates/resource/resource.tt +1 -1
  282. data/lib/generators/avo/templates/resource_tools/partial.tt +4 -4
  283. data/lib/generators/avo/templates/resource_tools/resource_tool.tt +1 -1
  284. data/lib/generators/avo/templates/scope.tt +6 -0
  285. data/lib/generators/avo/templates/standalone_action.tt +1 -1
  286. data/lib/generators/avo/templates/tailwindcss/Procfile.dev +1 -1
  287. data/lib/generators/avo/templates/tool/view.tt +2 -2
  288. data/lib/tasks/avo_tasks.rake +22 -0
  289. metadata +81 -159
  290. data/app/assets/stylesheets/css/tags.css +0 -32
  291. data/app/assets/svgs/map-empty-state.svg +0 -35
  292. data/app/assets/svgs/map-view-type.svg +0 -3
  293. data/app/components/avo/card_component.html.erb +0 -46
  294. data/app/components/avo/card_component.rb +0 -25
  295. data/app/components/avo/dashboards/divider_component.html.erb +0 -9
  296. data/app/components/avo/dashboards/divider_component.rb +0 -19
  297. data/app/components/avo/fields/area_field/edit_component.html.erb +0 -7
  298. data/app/components/avo/fields/area_field/edit_component.rb +0 -4
  299. data/app/components/avo/fields/area_field/show_component.html.erb +0 -8
  300. data/app/components/avo/fields/area_field/show_component.rb +0 -4
  301. data/app/components/avo/fields/belongs_to_field/autocomplete_component.html.erb +0 -47
  302. data/app/components/avo/fields/belongs_to_field/autocomplete_component.rb +0 -95
  303. data/app/components/avo/fields/common/files/controls_component.html.erb +0 -29
  304. data/app/components/avo/fields/common/files/controls_component.rb +0 -19
  305. data/app/components/avo/fields/common/files/list_viewer_component.html.erb +0 -20
  306. data/app/components/avo/fields/common/files/list_viewer_component.rb +0 -41
  307. data/app/components/avo/fields/common/files/view_type/grid_item_component.html.erb +0 -27
  308. data/app/components/avo/fields/common/files/view_type/grid_item_component.rb +0 -52
  309. data/app/components/avo/fields/common/files/view_type/list_item_component.html.erb +0 -22
  310. data/app/components/avo/fields/common/files/view_type/list_item_component.rb +0 -15
  311. data/app/components/avo/fields/location_field/edit_component.html.erb +0 -22
  312. data/app/components/avo/fields/location_field/edit_component.rb +0 -4
  313. data/app/components/avo/fields/location_field/show_component.html.erb +0 -7
  314. data/app/components/avo/fields/location_field/show_component.rb +0 -4
  315. data/app/components/avo/fields/tags_field/edit_component.html.erb +0 -35
  316. data/app/components/avo/fields/tags_field/edit_component.rb +0 -4
  317. data/app/components/avo/fields/tags_field/index_component.html.erb +0 -10
  318. data/app/components/avo/fields/tags_field/index_component.rb +0 -9
  319. data/app/components/avo/fields/tags_field/show_component.html.erb +0 -7
  320. data/app/components/avo/fields/tags_field/show_component.rb +0 -5
  321. data/app/components/avo/fields/tags_field/tag_component.html.erb +0 -9
  322. data/app/components/avo/fields/tags_field/tag_component.rb +0 -11
  323. data/app/components/avo/index/ordering/base_component.rb +0 -9
  324. data/app/components/avo/index/ordering/button_component.html.erb +0 -11
  325. data/app/components/avo/index/ordering/button_component.rb +0 -23
  326. data/app/components/avo/index/ordering/buttons_component.html.erb +0 -32
  327. data/app/components/avo/index/ordering/buttons_component.rb +0 -47
  328. data/app/components/avo/index/resource_map_component.html.erb +0 -16
  329. data/app/components/avo/index/resource_map_component.rb +0 -109
  330. data/app/components/avo/row_component.html.erb +0 -3
  331. data/app/components/avo/row_component.rb +0 -12
  332. data/app/components/avo/sidebar/item_switcher_component.html.erb +0 -16
  333. data/app/components/avo/sidebar/item_switcher_component.rb +0 -15
  334. data/app/controllers/avo/dashboards/cards_controller.rb +0 -37
  335. data/app/controllers/avo/dashboards_controller.rb +0 -22
  336. data/app/controllers/avo/reorder_controller.rb +0 -25
  337. data/app/javascript/js/controllers/base_controller.js +0 -22
  338. data/app/javascript/js/controllers/fields/reload_belongs_to_field_controller.js +0 -51
  339. data/app/javascript/js/controllers/fields/tags_field_controller.js +0 -127
  340. data/app/javascript/js/controllers/toggle_panel_controller.js +0 -18
  341. data/app/views/avo/base/_new_via_belongs_to.html.erb +0 -12
  342. data/app/views/avo/base/close_modal_and_reload_field.turbo_stream.erb +0 -8
  343. data/app/views/avo/base/create_fail_action.turbo_stream.erb +0 -13
  344. data/app/views/avo/dashboards/cards/_chartkick_card.html.erb +0 -3
  345. data/app/views/avo/dashboards/cards/_metric_card.html.erb +0 -5
  346. data/app/views/avo/dashboards/cards/chartkick_missing.html.erb +0 -14
  347. data/app/views/avo/dashboards/cards/show.html.erb +0 -3
  348. data/app/views/avo/dashboards/show.html.erb +0 -38
  349. data/app/views/avo/partials/_flash_alerts.turbo_stream.erb +0 -3
  350. data/app/views/avo/partials/_global_search.html.erb +0 -19
  351. data/app/views/avo/partials/_profile_menu_extra.html.erb +0 -2
  352. data/app/views/avo/sidebar/_license_warnings.html.erb +0 -6
  353. data/lib/avo/base_card.rb +0 -161
  354. data/lib/avo/concerns/fetches_things.rb +0 -150
  355. data/lib/avo/concerns/handles_field_args.rb +0 -47
  356. data/lib/avo/concerns/has_editable_controls.rb +0 -34
  357. data/lib/avo/concerns/has_html_attributes.rb +0 -108
  358. data/lib/avo/concerns/pagination.rb +0 -53
  359. data/lib/avo/concerns/policy_helpers.rb +0 -31
  360. data/lib/avo/concerns/visible_in_dashboard.rb +0 -31
  361. data/lib/avo/concerns/visible_items.rb +0 -51
  362. data/lib/avo/dashboards/base_dashboard.rb +0 -89
  363. data/lib/avo/dashboards/base_divider.rb +0 -35
  364. data/lib/avo/dashboards/chartkick_card.rb +0 -77
  365. data/lib/avo/dashboards/dashboard_card.rb +0 -6
  366. data/lib/avo/dashboards/metric_card.rb +0 -9
  367. data/lib/avo/dashboards/partial_card.rb +0 -7
  368. data/lib/avo/fields/area_field.rb +0 -39
  369. data/lib/avo/fields/concerns/file_authorization.rb +0 -31
  370. data/lib/avo/fields/field_extensions/has_field_name.rb +0 -19
  371. data/lib/avo/fields/field_extensions/visible_in_different_views.rb +0 -111
  372. data/lib/avo/fields/location_field.rb +0 -86
  373. data/lib/avo/fields/tags_field.rb +0 -102
  374. data/lib/avo/hosts/association_scope_host.rb +0 -8
  375. data/lib/avo/hosts/base_host.rb +0 -25
  376. data/lib/avo/hosts/card_visibility.rb +0 -20
  377. data/lib/avo/hosts/dashboard_card.rb +0 -22
  378. data/lib/avo/hosts/dashboard_visibility.rb +0 -19
  379. data/lib/avo/hosts/ordering.rb +0 -22
  380. data/lib/avo/hosts/record_host.rb +0 -7
  381. data/lib/avo/hosts/resource_record_host.rb +0 -7
  382. data/lib/avo/hosts/resource_view_record_host.rb +0 -7
  383. data/lib/avo/hosts/search_scope_host.rb +0 -7
  384. data/lib/avo/hosts/view_record_host.rb +0 -7
  385. data/lib/avo/hosts/visibility_host.rb +0 -12
  386. data/lib/avo/items_holder.rb +0 -96
  387. data/lib/avo/main_panel.rb +0 -3
  388. data/lib/avo/menu/base_item.rb +0 -25
  389. data/lib/avo/menu/builder.rb +0 -82
  390. data/lib/avo/menu/dashboard.rb +0 -22
  391. data/lib/avo/menu/group.rb +0 -2
  392. data/lib/avo/menu/link.rb +0 -6
  393. data/lib/avo/menu/menu.rb +0 -2
  394. data/lib/avo/menu/resource.rb +0 -22
  395. data/lib/avo/menu/section.rb +0 -2
  396. data/lib/avo/panel.rb +0 -24
  397. data/lib/avo/panel_builder.rb +0 -25
  398. data/lib/avo/resources/controls/action.rb +0 -38
  399. data/lib/avo/resources/controls/execution_context.rb +0 -58
  400. data/lib/avo/resources/controls/items_holder.rb +0 -19
  401. data/lib/avo/resources/controls/link_to.rb +0 -27
  402. data/lib/avo/row.rb +0 -26
  403. data/lib/avo/row_builder.rb +0 -24
  404. data/lib/avo/services/authorization_clients/nil_client.rb +0 -37
  405. data/lib/avo/services/authorization_clients/pundit_client.rb +0 -51
  406. data/lib/avo/sidebar.rb +0 -30
  407. data/lib/avo/sidebar_builder.rb +0 -24
  408. data/lib/avo/tab.rb +0 -72
  409. data/lib/avo/tab_builder.rb +0 -25
  410. data/lib/avo/tab_group.rb +0 -42
  411. data/lib/avo/tab_group_builder.rb +0 -43
  412. data/lib/avo/tools_manager.rb +0 -11
  413. data/lib/generators/avo/templates/locales/avo.es.yml +0 -126
  414. data/public/avo-assets/avo.base.js +0 -1037
  415. data/public/avo-assets/avo.base.js.map +0 -7
@@ -0,0 +1,92 @@
1
+ class Avo::Services::DebugService
2
+ class << self
3
+ def debug_report(request = nil)
4
+ payload = {}
5
+
6
+ hq = Avo::Licensing::HQ.new(request)
7
+
8
+ payload[:license_id] = Avo::Current&.license&.id
9
+ payload[:license_valid] = Avo::Current&.license&.valid?
10
+ payload[:license_payload] = Avo::Current&.license&.payload
11
+ payload[:license_response] = Avo::Current&.license&.response
12
+ payload[:hq_payload] = hq&.payload
13
+ payload[:thread_count] = get_thread_count
14
+ payload[:license_abilities] = Avo::Current&.license&.abilities
15
+ payload[:cache_store] = Avo::App.cache_store&.class&.to_s
16
+ payload[:avo_metadata] = avo_metadata
17
+ payload[:app_timezone] = Time.current.zone
18
+ payload[:cache_key] = Avo::Licensing::HQ.cache_key
19
+ payload[:cache_key_contents] = hq&.cached_response
20
+ payload[:plugins] = Avo.plugin_manager
21
+
22
+ payload
23
+ rescue => e
24
+ e
25
+ end
26
+
27
+ def get_thread_count
28
+ Thread.list.count { |thread| thread.status == "run" }
29
+ rescue => e
30
+ e
31
+ end
32
+
33
+ def avo_metadata
34
+ resources = Avo::Current.app.resource_manager.all
35
+ dashboards = defined?(AvoDashboards) ? AvoDashboards.dashboard_manager.all : []
36
+ field_definitions = resources.map(&:get_field_definitions)
37
+ fields_count = field_definitions.map(&:count).sum
38
+ fields_per_resource = sprintf("%0.01f", fields_count / (resources.count + 0.0))
39
+
40
+ field_types = {}
41
+ custom_fields_count = 0
42
+ field_definitions.each do |fields|
43
+ fields.each do |field|
44
+ field_types[field.type] ||= 0
45
+ field_types[field.type] += 1
46
+
47
+ custom_fields_count += 1 if field.custom?
48
+ end
49
+ end
50
+
51
+ {
52
+ resources_count: resources.count,
53
+ dashboards_count: dashboards.count,
54
+ fields_count: fields_count,
55
+ fields_per_resource: fields_per_resource,
56
+ custom_fields_count: custom_fields_count,
57
+ field_types: field_types,
58
+ **other_metadata(:actions),
59
+ **other_metadata(:filters),
60
+ main_menu_present: Avo.configuration.main_menu.present?,
61
+ profile_menu_present: Avo.configuration.profile_menu.present?,
62
+ **config_metadata
63
+ }
64
+ # rescue => error
65
+ # {
66
+ # error: error.message
67
+ # }
68
+ end
69
+
70
+ def other_metadata(type = :actions)
71
+ resources = Avo::Current.app.resource_manager.all
72
+
73
+ types = resources.map(&:"get_#{type}")
74
+ type_count = types.flatten.uniq.count
75
+ type_per_resource = sprintf("%0.01f", types.map(&:count).sum / (resources.count + 0.0))
76
+
77
+ {
78
+ "#{type}_count": type_count,
79
+ "#{type}_per_resource": type_per_resource
80
+ }
81
+ end
82
+
83
+ def config_metadata
84
+ {
85
+ config: {
86
+ root_path: Avo.configuration.root_path,
87
+ app_name: Avo.configuration.app_name
88
+ }
89
+ }
90
+ end
91
+ end
92
+ end
@@ -0,0 +1,84 @@
1
+ class Avo::Services::TelemetryService
2
+ class << self
3
+ def telemetry_info
4
+ {
5
+ # license: Avo.configuration.license,
6
+ # license_key: Avo.configuration.license_key,
7
+ avo_version: Avo::VERSION,
8
+ rails_version: Rails::VERSION::STRING,
9
+ ruby_version: RUBY_VERSION,
10
+ environment: Rails.env,
11
+ # ip: current_request&.ip,
12
+ # host: current_request&.host,
13
+ # port: current_request&.port,
14
+ app_name: app_name,
15
+ avo_metadata: avo_metadata,
16
+ }
17
+ end
18
+
19
+ def app_name
20
+ Rails.application.class.to_s.split("::").first
21
+ rescue
22
+ nil
23
+ end
24
+
25
+ def avo_metadata
26
+ resources = Avo::Current.app.resource_manager.all
27
+ dashboards = Avo::Current.app.dashboard_manager.all
28
+ field_definitions = resources.map(&:get_field_definitions)
29
+ fields_count = field_definitions.map(&:count).sum
30
+ fields_per_resource = sprintf("%0.01f", fields_count / (resources.count + 0.0))
31
+
32
+ field_types = {}
33
+ custom_fields_count = 0
34
+ field_definitions.each do |fields|
35
+ fields.each do |field|
36
+ field_types[field.type] ||= 0
37
+ field_types[field.type] += 1
38
+
39
+ custom_fields_count += 1 if field.custom?
40
+ end
41
+ end
42
+
43
+ {
44
+ resources_count: resources.count,
45
+ dashboards_count: dashboards.count,
46
+ fields_count: fields_count,
47
+ fields_per_resource: fields_per_resource,
48
+ custom_fields_count: custom_fields_count,
49
+ field_types: field_types,
50
+ **other_metadata(:actions),
51
+ **other_metadata(:filters),
52
+ main_menu_present: Avo.configuration.main_menu.present?,
53
+ profile_menu_present: Avo.configuration.profile_menu.present?,
54
+ **config_metadata
55
+ }
56
+ # rescue => error
57
+ # {
58
+ # error: error.message
59
+ # }
60
+ end
61
+
62
+ def other_metadata(type = :actions)
63
+ resources = Avo::Current.app.resource_manager.all
64
+
65
+ types = resources.map(&:"get_#{type}")
66
+ type_count = types.flatten.uniq.count
67
+ type_per_resource = sprintf("%0.01f", types.map(&:count).sum / (resources.count + 0.0))
68
+
69
+ {
70
+ "#{type}_count": type_count,
71
+ "#{type}_per_resource": type_per_resource
72
+ }
73
+ end
74
+
75
+ def config_metadata
76
+ {
77
+ config: {
78
+ root_path: Avo.configuration.root_path,
79
+ app_name: Avo.configuration.app_name
80
+ }
81
+ }
82
+ end
83
+ end
84
+ end
@@ -0,0 +1,362 @@
1
+ module Avo
2
+ module TestHelpers
3
+ # Finds the wrapper element on the index view for the given field id and type, and associated with the given record id
4
+ # Example usage:
5
+ # index_field_wrapper(id: "name", type: "text", record_id: 2)
6
+ # index_field_wrapper(id: "name", record_id: 2)
7
+ def index_field_wrapper(id:, record_id:, type: nil)
8
+ base_data = "#{row(record_id)} [data-field-id='#{id}']"
9
+
10
+ if type.present?
11
+ find("#{base_data}[data-resource-index-target='#{wrapper_name_for(id: id, type: type)}']")
12
+ else
13
+ find(base_data)
14
+ end
15
+ end
16
+
17
+ # Finds the wrapper element on the index grid view type for the given record id
18
+ # Example usage:
19
+ # grid_field_wrapper(record_id: 5)
20
+ def grid_field_wrapper(record_id:)
21
+ find("[data-component-name='avo/index/grid_item_component'][data-resource-id='#{record_id}']")
22
+ end
23
+
24
+ # Finds the wrapper element on the show view for the given field id and type
25
+ # Example usage:
26
+ # show_field_wrapper(id: "name", type: "text")
27
+ # show_field_wrapper(id: "name")
28
+ def show_field_wrapper(id:, type: nil)
29
+ base_data = "[data-panel-id='main'] [data-field-id='#{id}']"
30
+
31
+ if type.present?
32
+ find("#{base_data}[data-resource-show-target='#{wrapper_name_for(id: id, type: type)}']")
33
+ else
34
+ find(base_data)
35
+ end
36
+ end
37
+
38
+ # Finds the table on the show view for the given has_many field id and view
39
+ # Example usage:
40
+ # has_many_field_wrapper(id: :users)
41
+ # has_many_field_wrapper(id: :users, view: :edit)
42
+ def has_many_field_wrapper(id:, view: :show)
43
+ related_field_context(id: id, relation: :has_many, view: view)
44
+ end
45
+
46
+ # Finds the table on the show view for the given has_and_belongs_to_many field id and view
47
+ # Example usage:
48
+ # has_and_belongs_to_many_field_wrapper(id: :users)
49
+ # has_and_belongs_to_many_field_wrapper(id: :users, view: :edit)
50
+ def has_and_belongs_to_many_field_wrapper(id:, view: :show)
51
+ related_field_context(id: id, relation: :has_and_belongs_to_many, view: view)
52
+ end
53
+
54
+ # Finds the table on the show view for the given has_one field id and view
55
+ # Example usage:
56
+ # has_one_field_wrapper(id: :users)
57
+ # has_one_field_wrapper(id: :users, view: :edit)
58
+ def has_one_field_wrapper(id:, view: :show)
59
+ related_field_context(id: id, relation: :has_one, view: view)
60
+ end
61
+
62
+ # Finds the label element on the index view for the given field id
63
+ # Example usage:
64
+ # index_field_label(id: "name")
65
+ def index_field_label(id:)
66
+ find("[data-component-name='avo/partials/table_header'] [data-table-header-field-id='#{id}']").text
67
+ end
68
+
69
+ # Finds the label element on the show view for the given field id
70
+ # Example usage:
71
+ # show_field_label(id: "name")
72
+ def show_field_label(id:)
73
+ within(show_field_wrapper(id: id)) { find("[data-slot='label']").text }
74
+ end
75
+
76
+ # Finds the value element on the index view for the given field id
77
+ # Example usage:
78
+ # index_field_value(id: "name", record_id: 2)
79
+ def index_field_value(id:, record_id:, type: nil)
80
+ index_field_wrapper(id: id, record_id: record_id, type: type).text
81
+ end
82
+
83
+ # Finds the value element on the show view for the given field id
84
+ # Example usage:
85
+ # show_field_value(id: "name")
86
+ def show_field_value(id:, type: nil)
87
+ within(show_field_wrapper(id: id, type: type)) { find("[data-slot='value']").text }
88
+ end
89
+
90
+ def empty_dash
91
+ "—"
92
+ end
93
+
94
+ def confirm_alert
95
+ Capybara.using_wait_time(1) do
96
+ page.driver.browser.switch_to.alert.accept
97
+ rescue Selenium::WebDriver::Error::NoSuchAlertError
98
+ retry
99
+ end
100
+ end
101
+
102
+ # Example usage:
103
+ # click_resource_search_input # opens the first search box on the given page
104
+ # opens the search box for the "users" resource
105
+ # within(has_and_belongs_to_many_field_wrapper(id: :users)) {
106
+ # click_resource_search_input
107
+ # write_in_search("Bob")
108
+ # }
109
+ def click_resource_search_input
110
+ first("[data-search-resource]:not([data-search-resource='global'])").click
111
+ wait_for_search_loaded
112
+ end
113
+
114
+ def click_global_search_input
115
+ page.find(:xpath, "//*[contains(@class, 'global-search')]").click
116
+ wait_for_search_loaded
117
+ end
118
+
119
+ # Should use the click_global_search_input or click_resource_search_input method to open the search box first.
120
+ # Example usage:
121
+ # open_search_box(:users)
122
+ # within(has_and_belongs_to_many_field_wrapper(id: :users)) {
123
+ # click_resource_search_input # opens the search box for the "users" resource
124
+ # write_in_search("Bob")
125
+ # }
126
+ def write_in_search(input)
127
+ # Use xpath to find outside of within context if any
128
+ find(:xpath, "//input[@class='aa-Input']").set(input)
129
+ wait_for_search_loaded
130
+ end
131
+
132
+ # Should use the click_global_search_input or click_resource_search_input method to open the search box first and optionaly write_in_search.
133
+ # Example usage:
134
+ # open_search_box(:users) # opens the search box for the "users" resource
135
+ # write_in_search("John Doe")
136
+ # select_first_result_in_search
137
+ def select_first_result_in_search
138
+ find(".aa-Input").send_keys :arrow_down
139
+ find(".aa-Input").send_keys :enter
140
+ wait_for_search_loaded
141
+ end
142
+
143
+ # Save a record and wait for the page to load
144
+ def save
145
+ click_on "Save"
146
+ wait_for_loaded
147
+ end
148
+
149
+ def click_tab(tab_name = "", within_target: nil, **args)
150
+ if within_target.present?
151
+ within within_target do
152
+ within find('[data-controller="tabs"] turbo-frame:not(.hidden) [data-target="tab-switcher"]') do
153
+ find_link(tab_name).click
154
+ end
155
+ end
156
+ else
157
+ within find('[data-controller="tabs"] turbo-frame:not(.hidden) [data-target="tab-switcher"]') do
158
+ find_link(tab_name).click
159
+ end
160
+ end
161
+ end
162
+
163
+ def tab_group(index = 0)
164
+ find_all('[data-controller="tabs"]')[index]
165
+ end
166
+
167
+ def first_tab_group
168
+ tab_group 0
169
+ end
170
+
171
+ def second_tab_group
172
+ tab_group 1
173
+ end
174
+
175
+ def third_tab_group
176
+ tab_group 3
177
+ end
178
+
179
+ def click_on_sidebar_item(label)
180
+ within main_sidebar do
181
+ click_on label
182
+ end
183
+ end
184
+
185
+ def set_picker_day(date)
186
+ find(".flatpickr-day[aria-label=\"#{date}\"]").click
187
+ sleep 0.2
188
+ end
189
+
190
+ def set_picker_hour(value)
191
+ find(".flatpickr-hour").set(value)
192
+ end
193
+
194
+ def set_picker_minute(value)
195
+ find(".flatpickr-minute").set(value)
196
+ end
197
+
198
+ def set_picker_second(value)
199
+ find(".flatpickr-second").set(value)
200
+ end
201
+
202
+ def open_picker
203
+ text_input.click
204
+ end
205
+
206
+ def close_picker
207
+ find('[data-target="title"]').click
208
+ sleep 0.3
209
+ end
210
+
211
+ # Click on the action from the panel (index and show above the table)
212
+ # Pass list: nil to run an action outside of the list
213
+ # Pass list: "List name" if list is not the default "Actions"
214
+ # Example usage:
215
+ # open_panel_action(action_name: "Dummy action")
216
+ # open_panel_action(list: nil, action_name: "Release fish")
217
+ # open_panel_action(list: "Runnables", action_name: "Release fish")
218
+ def open_panel_action(action_name:, list: "Actions")
219
+ open_action(action_name: action_name, list: list, context: first("[data-target='panel-tools']"))
220
+ end
221
+
222
+ # Open the action from the record_id row
223
+ # Pass list: nil to run an action outside of the list
224
+ # Pass list: "List name" if list is not the default "Actions"
225
+ # Example usage:
226
+ # open_row_action(action_name: "Dummy action")
227
+ # open_row_action(list: nil, action_name: "Release fish")
228
+ # open_row_action(list: "Runnables", action_name: "Release fish")
229
+ def open_row_action(record_id:, action_name:, list: "Actions")
230
+ open_action(action_name: action_name, list: list, context: row(record_id))
231
+ end
232
+
233
+ # Click on submit action button if dialog is open
234
+ def run_action
235
+ within(find("[role='dialog']")) do
236
+ find("[data-target='submit_action']").click
237
+ end
238
+
239
+ wait_for_action_dialog_to_disappear
240
+ end
241
+
242
+ def check_select_all
243
+ find("input[type='checkbox'][name='Select all'][data-action='input->item-select-all#toggle']").set(true)
244
+ end
245
+
246
+ def toggle_collapsable(section)
247
+ find("[data-action='click->menu#triggerCollapse'][data-menu-key-param*='main_menu.#{section.underscore}'] svg").click
248
+ end
249
+
250
+ # Example usage:
251
+ # expect(add_tag(field: :tags, tag: "one")).to eq ["one"]
252
+ # add_tag(field: :tags, tag: "two")
253
+ def add_tag(field:, tag:)
254
+ # Find the input field for the specified field
255
+ input = find("[data-field-id='#{field}'] [data-slot='value'] [role='textbox']")
256
+
257
+ # Enter the specified tag into the input field
258
+ input.set(tag)
259
+ sleep 0.1
260
+
261
+ input.send_keys :return
262
+ wait_for_tag_to_appear(tag)
263
+
264
+ # Return an array of the current tags
265
+ tags(field: field)
266
+ end
267
+
268
+ # Example usage:
269
+ # expect(remove_tag(field: :tags, tag: "one")).to eq ["three"]
270
+ # remove_tag(field: :tags, tag: "one")
271
+ def remove_tag(field:, tag:)
272
+ # Within the specified field
273
+ within("[data-field-id='#{field}'] [data-slot='value']") do
274
+ # Find the tag with the specified text and click the remove button for the tag
275
+ page.find(".tagify__tag", text: tag).find(".tagify__tag__removeBtn").click
276
+
277
+ wait_for_tag_to_disappear(tag)
278
+ end
279
+
280
+ # Return an array of the current tags
281
+ tags(field: field)
282
+ end
283
+
284
+ # Example usage:
285
+ # expect(tags(field: :tags)).to eq ["one", "two", "three"]
286
+ # expect(tags(field: :tags)).to eq []
287
+ def tags(field:)
288
+ # Find all elements with class 'tagify__tag'
289
+ # Map the elements to their 'label' attribute values and return the array of labels
290
+ page.all(".tagify__tag").map { |element| element[:label] }
291
+ end
292
+
293
+ # Example usage:
294
+ # expect(tag_suggestions(field: :tags, input: "")).to eq ["one", "two", "three"]
295
+ # expect(tag_suggestions(field: :tags, input: "t")).to eq ["two", "three"]
296
+ def tag_suggestions(field:, input:)
297
+ # Find the input field for the specified tag field
298
+ input_area = find("[data-field-id='#{field}'] [data-slot='value'] [role='textbox']")
299
+
300
+ # If the input argument is present, enter it into the input field
301
+ # Else, just click on the middle of the input field to display the dropdown
302
+ if input.present?
303
+ input_area.set(input)
304
+ else
305
+ input_area.click(x: input_area.native.size.width / 2, y: input_area.native.size.height / 2)
306
+ end
307
+ wait_for_tag_suggestions_to_appear
308
+
309
+ # Find all elements with class 'tagify_dropdown_item' within the dropdown
310
+ # Map the elements to their 'label' attribute values and return the array of labels
311
+ page.all(".tagify__dropdown__item").map { |element| element[:label] }
312
+ end
313
+
314
+ private
315
+
316
+ # Returns the name of the wrapper element for the given field id and type
317
+ def wrapper_name_for(id:, type:)
318
+ "#{id.camelize(:lower)}#{type.camelize}Wrapper"
319
+ end
320
+
321
+ # Finds the context element for the related field with the given id, relation, and view
322
+ # ex: has_and_belongs_to_many_users = related_field_context(id: :users, relation: :has_and_belongs_to_many)
323
+ # Now on the returend element you can do:
324
+ # first_name_wrapper = within has_and_belongs_to_many_users do
325
+ # index_field_wrapper(id: "first_name", type: "text", record_id: 7)
326
+ # end
327
+ def related_field_context(id:, relation:, view: :show)
328
+ turbo_frame = "#{relation}_field_#{view}_#{id}"
329
+ find("[id='#{turbo_frame}']")
330
+ end
331
+
332
+ def main_sidebar
333
+ find('[data-sidebar-target="sidebar"]')
334
+ end
335
+
336
+ # Opens an action. If a list is provided, it will click on the list first
337
+ # and then find the specified action name within the panel.
338
+ # If no list is present, it will directly click on the action link.
339
+ def open_action(action_name:, list:, context:, &block)
340
+ within(context) do
341
+ if list.present?
342
+ sleep 0.1
343
+ click_on list
344
+ within("[data-toggle-target='panel']") do
345
+ find("a[data-action-name='#{action_name}']").click
346
+ end
347
+ else
348
+ click_link(action_name)
349
+ end
350
+ end
351
+
352
+ # Within the dialog, ensure that the action name is present
353
+ within(find("[role='dialog']")) do
354
+ expect(page).to have_content(action_name)
355
+ end
356
+ end
357
+
358
+ def row(id)
359
+ "[data-component-name='avo/index/table_row_component'][data-resource-id='#{id}']"
360
+ end
361
+ end
362
+ end
@@ -0,0 +1,30 @@
1
+ module Avo
2
+ module Tools
3
+ class ToolManager
4
+ class << self
5
+ def build
6
+ new
7
+ end
8
+ end
9
+
10
+ # Insert any partials that we find in app/views/avo/sidebar/items.
11
+ def get_sidebar_partials
12
+ Dir.glob(Rails.root.join("app", "views", "avo", "sidebar", "items", "*.html.erb"))
13
+ .map do |path|
14
+ File.basename path
15
+ end
16
+ .map do |filename|
17
+ # remove the leading underscore (_)
18
+ filename[0] = ""
19
+ # remove the extension
20
+ filename.gsub!(".html.erb", "")
21
+ filename
22
+ end
23
+ end
24
+
25
+ def tools_for_navigation
26
+ get_sidebar_partials
27
+ end
28
+ end
29
+ end
30
+ end
data/lib/avo/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module Avo
2
- VERSION = "2.45.0" unless const_defined?(:VERSION)
2
+ VERSION = "3.0.0.pre1" unless const_defined?(:VERSION)
3
3
  end
data/lib/avo.rb CHANGED
@@ -42,6 +42,7 @@ module Avo
42
42
  COOKIES_KEY = "avo"
43
43
  ENTITIES = {
44
44
  cards: ["app", "avo", "cards"],
45
+ scopes: ["app", "avo", "scopes"],
45
46
  fields: ["app", "avo", "fields"],
46
47
  filters: ["app", "avo", "filters"],
47
48
  actions: ["app", "avo", "actions"],
@@ -59,6 +60,12 @@ module Avo
59
60
  class NoPolicyError < StandardError; end
60
61
 
61
62
  class MissingGemError < StandardError; end
63
+
64
+ class << self
65
+ def avo_filters_installed?
66
+ defined?(AvoFilters).present?
67
+ end
68
+ end
62
69
  end
63
70
 
64
71
  loader.eager_load
@@ -17,7 +17,6 @@ module Generators
17
17
  pre_head: "app/views/avo/partials/_pre_head.html.erb",
18
18
  scripts: "app/views/avo/partials/_scripts.html.erb",
19
19
  sidebar_extra: "app/views/avo/partials/_sidebar_extra.html.erb",
20
- profile_menu_extra: "app/views/avo/partials/_profile_menu_extra.html.erb",
21
20
  }
22
21
 
23
22
  def handle
@@ -13,17 +13,7 @@ module Generators
13
13
  route "mount Avo::Engine, at: Avo.configuration.root_path"
14
14
 
15
15
  template "initializer/avo.tt", "config/initializers/avo.rb"
16
- create_resources
17
- end
18
-
19
- def create_resources
20
- if defined?(User).present?
21
- Rails::Generators.invoke("avo:resource", ["user", "-q"], {destination_root: Rails.root })
22
- end
23
-
24
- if defined?(Account).present?
25
- Rails::Generators.invoke("avo:resource", ["account", "-q"], {destination_root: Rails.root })
26
- end
16
+ directory File.join(__dir__, "templates", "locales"), "config/locales"
27
17
  end
28
18
  end
29
19
  end