decidim-enhanced_textwork 1.0.0

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 (441) hide show
  1. checksums.yaml +7 -0
  2. data/README.md +64 -0
  3. data/Rakefile +3 -0
  4. data/app/cells/decidim/enhanced_textwork/amendment/show.erb +14 -0
  5. data/app/cells/decidim/enhanced_textwork/amendment_cell.rb +39 -0
  6. data/app/cells/decidim/enhanced_textwork/collaborative_draft_cell.rb +49 -0
  7. data/app/cells/decidim/enhanced_textwork/collaborative_draft_link_to_paragraph/show.erb +13 -0
  8. data/app/cells/decidim/enhanced_textwork/collaborative_draft_link_to_paragraph_cell.rb +57 -0
  9. data/app/cells/decidim/enhanced_textwork/collaborative_draft_m/footer.erb +6 -0
  10. data/app/cells/decidim/enhanced_textwork/collaborative_draft_m/tags.erb +1 -0
  11. data/app/cells/decidim/enhanced_textwork/collaborative_draft_m_cell.rb +44 -0
  12. data/app/cells/decidim/enhanced_textwork/collaborative_drafts/reported_content/show.erb +3 -0
  13. data/app/cells/decidim/enhanced_textwork/collaborative_drafts/reported_content_cell.rb +15 -0
  14. data/app/cells/decidim/enhanced_textwork/comments/show.erb +33 -0
  15. data/app/cells/decidim/enhanced_textwork/comments_cell.rb +8 -0
  16. data/app/cells/decidim/enhanced_textwork/content_blocks/highlighted_paragraphs/elements.erb +5 -0
  17. data/app/cells/decidim/enhanced_textwork/content_blocks/highlighted_paragraphs/heading.erb +1 -0
  18. data/app/cells/decidim/enhanced_textwork/content_blocks/highlighted_paragraphs_cell.rb +19 -0
  19. data/app/cells/decidim/enhanced_textwork/cost_report/show.erb +35 -0
  20. data/app/cells/decidim/enhanced_textwork/cost_report_cell.rb +42 -0
  21. data/app/cells/decidim/enhanced_textwork/highlighted_paragraphs/show.erb +3 -0
  22. data/app/cells/decidim/enhanced_textwork/highlighted_paragraphs_cell.rb +25 -0
  23. data/app/cells/decidim/enhanced_textwork/highlighted_paragraphs_for_component/show.erb +19 -0
  24. data/app/cells/decidim/enhanced_textwork/highlighted_paragraphs_for_component_cell.rb +41 -0
  25. data/app/cells/decidim/enhanced_textwork/irreversible_action_modal/show.erb +27 -0
  26. data/app/cells/decidim/enhanced_textwork/irreversible_action_modal_cell.rb +80 -0
  27. data/app/cells/decidim/enhanced_textwork/paragraph_activity_cell.rb +35 -0
  28. data/app/cells/decidim/enhanced_textwork/paragraph_cell.rb +53 -0
  29. data/app/cells/decidim/enhanced_textwork/paragraph_link_to_collaborative_draft_cell.rb +26 -0
  30. data/app/cells/decidim/enhanced_textwork/paragraph_link_to_rejected_emendation/show.erb +9 -0
  31. data/app/cells/decidim/enhanced_textwork/paragraph_link_to_rejected_emendation_cell.rb +34 -0
  32. data/app/cells/decidim/enhanced_textwork/paragraph_linked_resources/show.erb +9 -0
  33. data/app/cells/decidim/enhanced_textwork/paragraph_linked_resources_cell.rb +14 -0
  34. data/app/cells/decidim/enhanced_textwork/paragraph_m/footer.erb +26 -0
  35. data/app/cells/decidim/enhanced_textwork/paragraph_m/tags.erb +1 -0
  36. data/app/cells/decidim/enhanced_textwork/paragraph_m_cell.rb +152 -0
  37. data/app/cells/decidim/enhanced_textwork/paragraph_tags/show.erb +33 -0
  38. data/app/cells/decidim/enhanced_textwork/paragraph_tags_cell.rb +35 -0
  39. data/app/cells/decidim/enhanced_textwork/paragraphs_picker/paragraphs.erb +12 -0
  40. data/app/cells/decidim/enhanced_textwork/paragraphs_picker/show.erb +14 -0
  41. data/app/cells/decidim/enhanced_textwork/paragraphs_picker_cell.rb +72 -0
  42. data/app/cells/decidim/enhanced_textwork/participatory_text_paragraph/buttons.erb +33 -0
  43. data/app/cells/decidim/enhanced_textwork/participatory_text_paragraph/show.erb +38 -0
  44. data/app/cells/decidim/enhanced_textwork/participatory_text_paragraph_cell.rb +104 -0
  45. data/app/cells/decidim/enhanced_textwork/reported_content/show.erb +4 -0
  46. data/app/cells/decidim/enhanced_textwork/reported_content_cell.rb +13 -0
  47. data/app/commands/decidim/enhanced_textwork/accept_access_to_collaborative_draft.rb +70 -0
  48. data/app/commands/decidim/enhanced_textwork/admin/answer_paragraph.rb +74 -0
  49. data/app/commands/decidim/enhanced_textwork/admin/assign_paragraphs_to_valuator.rb +61 -0
  50. data/app/commands/decidim/enhanced_textwork/admin/create_paragraph.rb +97 -0
  51. data/app/commands/decidim/enhanced_textwork/admin/create_paragraph_note.rb +67 -0
  52. data/app/commands/decidim/enhanced_textwork/admin/destroy_paragraph.rb +32 -0
  53. data/app/commands/decidim/enhanced_textwork/admin/discard_participatory_text.rb +40 -0
  54. data/app/commands/decidim/enhanced_textwork/admin/import_from_editor_participatory_text.rb +53 -0
  55. data/app/commands/decidim/enhanced_textwork/admin/import_paragraphs.rb +101 -0
  56. data/app/commands/decidim/enhanced_textwork/admin/import_participatory_text.rb +55 -0
  57. data/app/commands/decidim/enhanced_textwork/admin/merge_paragraphs.rb +69 -0
  58. data/app/commands/decidim/enhanced_textwork/admin/notify_paragraph_answer.rb +85 -0
  59. data/app/commands/decidim/enhanced_textwork/admin/publish_answers.rb +67 -0
  60. data/app/commands/decidim/enhanced_textwork/admin/publish_participatory_text.rb +81 -0
  61. data/app/commands/decidim/enhanced_textwork/admin/split_paragraphs.rb +67 -0
  62. data/app/commands/decidim/enhanced_textwork/admin/unassign_paragraphs_from_valuator.rb +62 -0
  63. data/app/commands/decidim/enhanced_textwork/admin/update_paragraph.rb +86 -0
  64. data/app/commands/decidim/enhanced_textwork/admin/update_paragraph_category.rb +68 -0
  65. data/app/commands/decidim/enhanced_textwork/admin/update_paragraph_scope.rb +75 -0
  66. data/app/commands/decidim/enhanced_textwork/admin/update_participatory_text.rb +68 -0
  67. data/app/commands/decidim/enhanced_textwork/create_collaborative_draft.rb +81 -0
  68. data/app/commands/decidim/enhanced_textwork/create_paragraph.rb +106 -0
  69. data/app/commands/decidim/enhanced_textwork/destroy_paragraph.rb +33 -0
  70. data/app/commands/decidim/enhanced_textwork/gallery_methods.rb +18 -0
  71. data/app/commands/decidim/enhanced_textwork/hashtags_methods.rb +36 -0
  72. data/app/commands/decidim/enhanced_textwork/publish_collaborative_draft.rb +93 -0
  73. data/app/commands/decidim/enhanced_textwork/publish_paragraph.rb +105 -0
  74. data/app/commands/decidim/enhanced_textwork/reject_access_to_collaborative_draft.rb +62 -0
  75. data/app/commands/decidim/enhanced_textwork/request_access_to_collaborative_draft.rb +49 -0
  76. data/app/commands/decidim/enhanced_textwork/unvote_paragraph.rb +65 -0
  77. data/app/commands/decidim/enhanced_textwork/update_collaborative_draft.rb +63 -0
  78. data/app/commands/decidim/enhanced_textwork/update_paragraph.rb +135 -0
  79. data/app/commands/decidim/enhanced_textwork/vote_paragraph.rb +77 -0
  80. data/app/commands/decidim/enhanced_textwork/withdraw_collaborative_draft.rb +65 -0
  81. data/app/commands/decidim/enhanced_textwork/withdraw_paragraph.rb +50 -0
  82. data/app/controllers/concerns/decidim/enhanced_textwork/admin/filterable.rb +82 -0
  83. data/app/controllers/concerns/decidim/enhanced_textwork/admin/picker.rb +21 -0
  84. data/app/controllers/concerns/decidim/enhanced_textwork/collaborative_orderable.rb +42 -0
  85. data/app/controllers/concerns/decidim/enhanced_textwork/orderable.rb +78 -0
  86. data/app/controllers/decidim/enhanced_textwork/admin/application_controller.rb +16 -0
  87. data/app/controllers/decidim/enhanced_textwork/admin/paragraph_answers_controller.rb +50 -0
  88. data/app/controllers/decidim/enhanced_textwork/admin/paragraph_notes_controller.rb +39 -0
  89. data/app/controllers/decidim/enhanced_textwork/admin/paragraphs_controller.rb +237 -0
  90. data/app/controllers/decidim/enhanced_textwork/admin/paragraphs_imports_controller.rb +33 -0
  91. data/app/controllers/decidim/enhanced_textwork/admin/paragraphs_merges_controller.rb +30 -0
  92. data/app/controllers/decidim/enhanced_textwork/admin/paragraphs_splits_controller.rb +30 -0
  93. data/app/controllers/decidim/enhanced_textwork/admin/participatory_texts_controller.rb +128 -0
  94. data/app/controllers/decidim/enhanced_textwork/admin/valuation_assignments_controller.rb +58 -0
  95. data/app/controllers/decidim/enhanced_textwork/application_controller.rb +31 -0
  96. data/app/controllers/decidim/enhanced_textwork/collaborative_draft_collaborator_requests_controller.rb +53 -0
  97. data/app/controllers/decidim/enhanced_textwork/collaborative_drafts_controller.rb +161 -0
  98. data/app/controllers/decidim/enhanced_textwork/paragraph_votes_controller.rb +65 -0
  99. data/app/controllers/decidim/enhanced_textwork/paragraphs_controller.rb +316 -0
  100. data/app/controllers/decidim/enhanced_textwork/versions_controller.rb +21 -0
  101. data/app/controllers/decidim/enhanced_textwork/widgets_controller.rb +19 -0
  102. data/app/events/decidim/enhanced_textwork/accepted_paragraph_event.rb +17 -0
  103. data/app/events/decidim/enhanced_textwork/admin/paragraph_note_created_event.rb +27 -0
  104. data/app/events/decidim/enhanced_textwork/admin/update_paragraph_category_event.rb +11 -0
  105. data/app/events/decidim/enhanced_textwork/admin/update_paragraph_scope_event.rb +11 -0
  106. data/app/events/decidim/enhanced_textwork/collaborative_draft_access_accepted_event.rb +8 -0
  107. data/app/events/decidim/enhanced_textwork/collaborative_draft_access_rejected_event.rb +8 -0
  108. data/app/events/decidim/enhanced_textwork/collaborative_draft_access_request_event.rb +27 -0
  109. data/app/events/decidim/enhanced_textwork/collaborative_draft_access_requested_event.rb +8 -0
  110. data/app/events/decidim/enhanced_textwork/collaborative_draft_access_requester_accepted_event.rb +8 -0
  111. data/app/events/decidim/enhanced_textwork/collaborative_draft_access_requester_rejected_event.rb +8 -0
  112. data/app/events/decidim/enhanced_textwork/collaborative_draft_withdrawn_event.rb +29 -0
  113. data/app/events/decidim/enhanced_textwork/creation_enabled_event.rb +8 -0
  114. data/app/events/decidim/enhanced_textwork/endorsing_enabled_event.rb +8 -0
  115. data/app/events/decidim/enhanced_textwork/evaluating_paragraph_event.rb +11 -0
  116. data/app/events/decidim/enhanced_textwork/paragraph_endorsed_event.rb +33 -0
  117. data/app/events/decidim/enhanced_textwork/paragraph_mentioned_event.rb +21 -0
  118. data/app/events/decidim/enhanced_textwork/publish_paragraph_event.rb +25 -0
  119. data/app/events/decidim/enhanced_textwork/rejected_paragraph_event.rb +17 -0
  120. data/app/events/decidim/enhanced_textwork/voting_enabled_event.rb +8 -0
  121. data/app/forms/decidim/enhanced_textwork/accept_access_to_collaborative_draft_form.rb +10 -0
  122. data/app/forms/decidim/enhanced_textwork/access_to_collaborative_draft_form.rb +33 -0
  123. data/app/forms/decidim/enhanced_textwork/admin/import_editor_participatory_text_form.rb +35 -0
  124. data/app/forms/decidim/enhanced_textwork/admin/import_participatory_text_form.rb +68 -0
  125. data/app/forms/decidim/enhanced_textwork/admin/paragraph_answer_form.rb +44 -0
  126. data/app/forms/decidim/enhanced_textwork/admin/paragraph_base_form.rb +137 -0
  127. data/app/forms/decidim/enhanced_textwork/admin/paragraph_form.rb +32 -0
  128. data/app/forms/decidim/enhanced_textwork/admin/paragraph_note_form.rb +16 -0
  129. data/app/forms/decidim/enhanced_textwork/admin/paragraphs_fork_form.rb +63 -0
  130. data/app/forms/decidim/enhanced_textwork/admin/paragraphs_import_form.rb +67 -0
  131. data/app/forms/decidim/enhanced_textwork/admin/paragraphs_merge_form.rb +13 -0
  132. data/app/forms/decidim/enhanced_textwork/admin/paragraphs_split_form.rb +12 -0
  133. data/app/forms/decidim/enhanced_textwork/admin/participatory_text_paragraph_form.rb +20 -0
  134. data/app/forms/decidim/enhanced_textwork/admin/preview_participatory_text_form.rb +21 -0
  135. data/app/forms/decidim/enhanced_textwork/admin/valuation_assignment_form.rb +37 -0
  136. data/app/forms/decidim/enhanced_textwork/collaborative_draft_form.rb +20 -0
  137. data/app/forms/decidim/enhanced_textwork/paragraph_form.rb +126 -0
  138. data/app/forms/decidim/enhanced_textwork/paragraph_wizard_create_step_form.rb +41 -0
  139. data/app/forms/decidim/enhanced_textwork/reject_access_to_collaborative_draft_form.rb +9 -0
  140. data/app/forms/decidim/enhanced_textwork/request_access_to_collaborative_draft_form.rb +20 -0
  141. data/app/helpers/decidim/enhanced_textwork/admin/filterable_helper.rb +17 -0
  142. data/app/helpers/decidim/enhanced_textwork/admin/paragraph_bulk_actions_helper.rb +35 -0
  143. data/app/helpers/decidim/enhanced_textwork/admin/paragraph_rankings_helper.rb +63 -0
  144. data/app/helpers/decidim/enhanced_textwork/admin/paragraphs_helper.rb +144 -0
  145. data/app/helpers/decidim/enhanced_textwork/admin/paragraphs_picker_helper.rb +30 -0
  146. data/app/helpers/decidim/enhanced_textwork/application_helper.rb +191 -0
  147. data/app/helpers/decidim/enhanced_textwork/collaborative_draft_cells_helper.rb +48 -0
  148. data/app/helpers/decidim/enhanced_textwork/collaborative_draft_helper.rb +29 -0
  149. data/app/helpers/decidim/enhanced_textwork/control_version_helper.rb +12 -0
  150. data/app/helpers/decidim/enhanced_textwork/map_helper.rb +48 -0
  151. data/app/helpers/decidim/enhanced_textwork/paragraph_cells_helper.rb +75 -0
  152. data/app/helpers/decidim/enhanced_textwork/paragraph_votes_helper.rb +103 -0
  153. data/app/helpers/decidim/enhanced_textwork/paragraph_wizard_helper.rb +140 -0
  154. data/app/helpers/decidim/enhanced_textwork/paragraphs_helper.rb +63 -0
  155. data/app/helpers/decidim/enhanced_textwork/participatory_texts_helper.rb +49 -0
  156. data/app/jobs/decidim/enhanced_textwork/notify_paragraphs_mentioned_job.rb +27 -0
  157. data/app/jobs/decidim/enhanced_textwork/settings_change_job.rb +50 -0
  158. data/app/models/decidim/enhanced_textwork/application_record.rb +10 -0
  159. data/app/models/decidim/enhanced_textwork/collaborative_draft.rb +73 -0
  160. data/app/models/decidim/enhanced_textwork/collaborative_draft_collaborator_request.rb +13 -0
  161. data/app/models/decidim/enhanced_textwork/paragraph.rb +411 -0
  162. data/app/models/decidim/enhanced_textwork/paragraph_note.rb +20 -0
  163. data/app/models/decidim/enhanced_textwork/paragraph_vote.rb +50 -0
  164. data/app/models/decidim/enhanced_textwork/participatory_text.rb +16 -0
  165. data/app/models/decidim/enhanced_textwork/valuation_assignment.rb +24 -0
  166. data/app/packs/documents/decidim/enhanced_textwork/participatory_texts/participatory_text.md +52 -0
  167. data/app/packs/documents/decidim/enhanced_textwork/participatory_texts/participatory_text.odt +0 -0
  168. data/app/packs/entrypoints/decidim_enhanced_textwork.js +17 -0
  169. data/app/packs/entrypoints/decidim_enhanced_textwork_admin.js +3 -0
  170. data/app/packs/images/decidim/enhanced_textwork/decidim_paragraphs.svg +1 -0
  171. data/app/packs/images/decidim/gamification/badges/decidim_gamification_badges_accepted_paragraphs.svg +1 -0
  172. data/app/packs/images/decidim/gamification/badges/decidim_gamification_badges_paragraph_votes.svg +1 -0
  173. data/app/packs/images/decidim/gamification/badges/decidim_gamification_badges_paragraphs.svg +1 -0
  174. data/app/packs/src/decidim/enhanced_textwork/add_paragraph.js +49 -0
  175. data/app/packs/src/decidim/enhanced_textwork/admin/paragraphs.js +143 -0
  176. data/app/packs/src/decidim/enhanced_textwork/admin/paragraphs_form.js +29 -0
  177. data/app/packs/src/decidim/enhanced_textwork/admin/paragraphs_picker.js +35 -0
  178. data/app/packs/src/decidim/enhanced_textwork/toggle_element.js +21 -0
  179. data/app/packs/src/decidim/enhanced_textwork/utils.js +11 -0
  180. data/app/packs/stylesheets/decidim/enhanced_textwork/_paragraphs.scss +208 -0
  181. data/app/packs/stylesheets/decidim/enhanced_textwork/paragraphs/_preview.scss +3 -0
  182. data/app/permissions/decidim/enhanced_textwork/admin/permissions.rb +147 -0
  183. data/app/permissions/decidim/enhanced_textwork/permissions.rb +163 -0
  184. data/app/presenters/decidim/enhanced_textwork/admin_log/paragraph_note_presenter.rb +39 -0
  185. data/app/presenters/decidim/enhanced_textwork/admin_log/paragraph_presenter.rb +51 -0
  186. data/app/presenters/decidim/enhanced_textwork/admin_log/valuation_assignment_presenter.rb +51 -0
  187. data/app/presenters/decidim/enhanced_textwork/admin_log/value_types/paragraph_state_presenter.rb +17 -0
  188. data/app/presenters/decidim/enhanced_textwork/admin_log/value_types/paragraph_title_body_presenter.rb +23 -0
  189. data/app/presenters/decidim/enhanced_textwork/admin_log/value_types/valuator_role_user_presenter.rb +19 -0
  190. data/app/presenters/decidim/enhanced_textwork/collaborative_draft_presenter.rb +25 -0
  191. data/app/presenters/decidim/enhanced_textwork/log/resource_presenter.rb +22 -0
  192. data/app/presenters/decidim/enhanced_textwork/log/valuation_assignment_presenter.rb +22 -0
  193. data/app/presenters/decidim/enhanced_textwork/official_author_presenter.rb +14 -0
  194. data/app/presenters/decidim/enhanced_textwork/paragraph_presenter.rb +146 -0
  195. data/app/queries/decidim/enhanced_textwork/filtered_paragraphs.rb +37 -0
  196. data/app/queries/decidim/enhanced_textwork/metrics/accepted_paragraphs_metric_manage.rb +32 -0
  197. data/app/queries/decidim/enhanced_textwork/metrics/endorsements_metric_manage.rb +58 -0
  198. data/app/queries/decidim/enhanced_textwork/metrics/paragraph_followers_metric_measure.rb +58 -0
  199. data/app/queries/decidim/enhanced_textwork/metrics/paragraph_participants_metric_measure.rb +74 -0
  200. data/app/queries/decidim/enhanced_textwork/metrics/paragraphs_metric_manage.rb +48 -0
  201. data/app/queries/decidim/enhanced_textwork/metrics/votes_metric_manage.rb +52 -0
  202. data/app/queries/decidim/enhanced_textwork/similar_paragraphs.rb +67 -0
  203. data/app/services/decidim/enhanced_textwork/collaborative_draft_search.rb +59 -0
  204. data/app/services/decidim/enhanced_textwork/diff_renderer.rb +74 -0
  205. data/app/services/decidim/enhanced_textwork/paragraph_builder.rb +132 -0
  206. data/app/services/decidim/enhanced_textwork/paragraph_search.rb +85 -0
  207. data/app/validators/paragraph_length_validator.rb +40 -0
  208. data/app/views/decidim/enhanced_textwork/admin/paragraph_answers/_form.html.erb +35 -0
  209. data/app/views/decidim/enhanced_textwork/admin/paragraph_notes/_form.html.erb +8 -0
  210. data/app/views/decidim/enhanced_textwork/admin/paragraph_notes/_paragraph_notes.html.erb +45 -0
  211. data/app/views/decidim/enhanced_textwork/admin/paragraphs/_bulk-actions.html.erb +33 -0
  212. data/app/views/decidim/enhanced_textwork/admin/paragraphs/_form.html.erb +101 -0
  213. data/app/views/decidim/enhanced_textwork/admin/paragraphs/_js-callout.html.erb +6 -0
  214. data/app/views/decidim/enhanced_textwork/admin/paragraphs/_paragraph-tr.html.erb +76 -0
  215. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_assign_to_valuator.html.erb +15 -0
  216. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_dropdown.html.erb +56 -0
  217. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_merge.html.erb +15 -0
  218. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_publish_answers.html.erb +14 -0
  219. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_recategorize.html.erb +15 -0
  220. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_scope-change.html.erb +25 -0
  221. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_split.html.erb +15 -0
  222. data/app/views/decidim/enhanced_textwork/admin/paragraphs/bulk_actions/_unassign_from_valuator.html.erb +15 -0
  223. data/app/views/decidim/enhanced_textwork/admin/paragraphs/edit.html.erb +7 -0
  224. data/app/views/decidim/enhanced_textwork/admin/paragraphs/index.html.erb +84 -0
  225. data/app/views/decidim/enhanced_textwork/admin/paragraphs/new.html.erb +7 -0
  226. data/app/views/decidim/enhanced_textwork/admin/paragraphs/publish_answers.js.erb +12 -0
  227. data/app/views/decidim/enhanced_textwork/admin/paragraphs/show.html.erb +186 -0
  228. data/app/views/decidim/enhanced_textwork/admin/paragraphs/update_category.js.erb +26 -0
  229. data/app/views/decidim/enhanced_textwork/admin/paragraphs/update_scope.js.erb +27 -0
  230. data/app/views/decidim/enhanced_textwork/admin/paragraphs_imports/new.html.erb +37 -0
  231. data/app/views/decidim/enhanced_textwork/admin/participatory_texts/_article-preview.html.erb +16 -0
  232. data/app/views/decidim/enhanced_textwork/admin/participatory_texts/_bulk-actions.html.erb +3 -0
  233. data/app/views/decidim/enhanced_textwork/admin/participatory_texts/index.html.erb +55 -0
  234. data/app/views/decidim/enhanced_textwork/admin/participatory_texts/new_editor.html.erb +39 -0
  235. data/app/views/decidim/enhanced_textwork/admin/participatory_texts/new_import.html.erb +39 -0
  236. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_accept_request_access_form.html.erb +8 -0
  237. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_collaborative_drafts.html.erb +16 -0
  238. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_collaborator_requests.html.erb +20 -0
  239. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_count.html.erb +1 -0
  240. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_edit_form_fields.html.erb +83 -0
  241. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_filters.html.erb +32 -0
  242. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_filters_small_view.html.erb +18 -0
  243. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_new_collaborative_draft_button.html.erb +11 -0
  244. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_reject_request_access_form.html.erb +10 -0
  245. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_request_access_form.html.erb +7 -0
  246. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_wizard_aside.html.erb +13 -0
  247. data/app/views/decidim/enhanced_textwork/collaborative_drafts/_wizard_header.html.erb +14 -0
  248. data/app/views/decidim/enhanced_textwork/collaborative_drafts/edit.html.erb +31 -0
  249. data/app/views/decidim/enhanced_textwork/collaborative_drafts/index.html.erb +23 -0
  250. data/app/views/decidim/enhanced_textwork/collaborative_drafts/index.js.erb +10 -0
  251. data/app/views/decidim/enhanced_textwork/collaborative_drafts/new.html.erb +24 -0
  252. data/app/views/decidim/enhanced_textwork/collaborative_drafts/show.html.erb +128 -0
  253. data/app/views/decidim/enhanced_textwork/paragraph_votes/update_buttons_and_counters.js.erb +41 -0
  254. data/app/views/decidim/enhanced_textwork/paragraphs/_count.html.erb +1 -0
  255. data/app/views/decidim/enhanced_textwork/paragraphs/_dynamic_map_instructions.html.erb +4 -0
  256. data/app/views/decidim/enhanced_textwork/paragraphs/_edit_form_fields.html.erb +115 -0
  257. data/app/views/decidim/enhanced_textwork/paragraphs/_endorsements_card_row.html.erb +0 -0
  258. data/app/views/decidim/enhanced_textwork/paragraphs/_filters.html.erb +48 -0
  259. data/app/views/decidim/enhanced_textwork/paragraphs/_filters_small_view.html.erb +18 -0
  260. data/app/views/decidim/enhanced_textwork/paragraphs/_linked_paragraphs.html.erb +34 -0
  261. data/app/views/decidim/enhanced_textwork/paragraphs/_paragraph.html.erb +1 -0
  262. data/app/views/decidim/enhanced_textwork/paragraphs/_paragraph_badge.html.erb +3 -0
  263. data/app/views/decidim/enhanced_textwork/paragraphs/_paragraph_similar.html.erb +22 -0
  264. data/app/views/decidim/enhanced_textwork/paragraphs/_paragraphs.html.erb +46 -0
  265. data/app/views/decidim/enhanced_textwork/paragraphs/_remaining_votes_count.html.erb +3 -0
  266. data/app/views/decidim/enhanced_textwork/paragraphs/_vote_button.html.erb +61 -0
  267. data/app/views/decidim/enhanced_textwork/paragraphs/_votes_count.html.erb +18 -0
  268. data/app/views/decidim/enhanced_textwork/paragraphs/_voting_rules.html.erb +50 -0
  269. data/app/views/decidim/enhanced_textwork/paragraphs/_wizard_aside.html.erb +20 -0
  270. data/app/views/decidim/enhanced_textwork/paragraphs/_wizard_header.html.erb +42 -0
  271. data/app/views/decidim/enhanced_textwork/paragraphs/compare.html.erb +23 -0
  272. data/app/views/decidim/enhanced_textwork/paragraphs/complete.html.erb +24 -0
  273. data/app/views/decidim/enhanced_textwork/paragraphs/edit.html.erb +31 -0
  274. data/app/views/decidim/enhanced_textwork/paragraphs/edit_draft.html.erb +26 -0
  275. data/app/views/decidim/enhanced_textwork/paragraphs/index.html.erb +56 -0
  276. data/app/views/decidim/enhanced_textwork/paragraphs/index.js.erb +10 -0
  277. data/app/views/decidim/enhanced_textwork/paragraphs/new.html.erb +38 -0
  278. data/app/views/decidim/enhanced_textwork/paragraphs/participatory_texts/_index.html.erb +20 -0
  279. data/app/views/decidim/enhanced_textwork/paragraphs/participatory_texts/_overview.html.erb +35 -0
  280. data/app/views/decidim/enhanced_textwork/paragraphs/participatory_texts/_paragraph_vote_button.html.erb +53 -0
  281. data/app/views/decidim/enhanced_textwork/paragraphs/participatory_texts/_paragraph_vote_button_chevron.html.erb +72 -0
  282. data/app/views/decidim/enhanced_textwork/paragraphs/participatory_texts/_paragraph_votes_count.html.erb +41 -0
  283. data/app/views/decidim/enhanced_textwork/paragraphs/participatory_texts/_view_index.html.erb +10 -0
  284. data/app/views/decidim/enhanced_textwork/paragraphs/participatory_texts/participatory_text.html.erb +29 -0
  285. data/app/views/decidim/enhanced_textwork/paragraphs/preview.html.erb +41 -0
  286. data/app/views/decidim/enhanced_textwork/paragraphs/show.html.erb +143 -0
  287. data/app/views/decidim/enhanced_textwork/versions/index.html.erb +16 -0
  288. data/app/views/decidim/enhanced_textwork/versions/show.html.erb +18 -0
  289. data/config/assets.rb +10 -0
  290. data/config/locales/de.yml +927 -0
  291. data/config/locales/en.yml +967 -0
  292. data/config/locales/todo/am-ET.yml +1 -0
  293. data/config/locales/todo/ar-SA.yml +801 -0
  294. data/config/locales/todo/ar.yml +791 -0
  295. data/config/locales/todo/bg-BG.yml +237 -0
  296. data/config/locales/todo/bg.yml +238 -0
  297. data/config/locales/todo/ca.yml +908 -0
  298. data/config/locales/todo/cs-CZ.yml +787 -0
  299. data/config/locales/todo/cs.yml +969 -0
  300. data/config/locales/todo/da-DK.yml +1 -0
  301. data/config/locales/todo/da.yml +1 -0
  302. data/config/locales/todo/el-GR.yml +1 -0
  303. data/config/locales/todo/el.yml +848 -0
  304. data/config/locales/todo/eo-UY.yml +1 -0
  305. data/config/locales/todo/eo.yml +1 -0
  306. data/config/locales/todo/es-MX.yml +908 -0
  307. data/config/locales/todo/es-PY.yml +908 -0
  308. data/config/locales/todo/es.yml +908 -0
  309. data/config/locales/todo/et-EE.yml +1 -0
  310. data/config/locales/todo/et.yml +1 -0
  311. data/config/locales/todo/eu.yml +717 -0
  312. data/config/locales/todo/fi-pl.yml +763 -0
  313. data/config/locales/todo/fi-plain.yml +920 -0
  314. data/config/locales/todo/fi.yml +920 -0
  315. data/config/locales/todo/fr-CA.yml +936 -0
  316. data/config/locales/todo/fr-LU.yml +903 -0
  317. data/config/locales/todo/fr.yml +936 -0
  318. data/config/locales/todo/ga-IE.yml +275 -0
  319. data/config/locales/todo/gl.yml +808 -0
  320. data/config/locales/todo/hr-HR.yml +1 -0
  321. data/config/locales/todo/hr.yml +1 -0
  322. data/config/locales/todo/hu.yml +847 -0
  323. data/config/locales/todo/id-ID.yml +704 -0
  324. data/config/locales/todo/is-IS.yml +269 -0
  325. data/config/locales/todo/is.yml +274 -0
  326. data/config/locales/todo/it.yml +908 -0
  327. data/config/locales/todo/ja.yml +922 -0
  328. data/config/locales/todo/ko-KR.yml +1 -0
  329. data/config/locales/todo/ko.yml +1 -0
  330. data/config/locales/todo/lb-LU.yml +1 -0
  331. data/config/locales/todo/lb.yml +40 -0
  332. data/config/locales/todo/lt-LT.yml +1 -0
  333. data/config/locales/todo/lt.yml +1 -0
  334. data/config/locales/todo/lv.yml +838 -0
  335. data/config/locales/todo/mt-MT.yml +1 -0
  336. data/config/locales/todo/mt.yml +1 -0
  337. data/config/locales/todo/nl.yml +882 -0
  338. data/config/locales/todo/no.yml +770 -0
  339. data/config/locales/todo/om-ET.yml +1 -0
  340. data/config/locales/todo/pl.yml +927 -0
  341. data/config/locales/todo/pt-BR.yml +908 -0
  342. data/config/locales/todo/pt.yml +945 -0
  343. data/config/locales/todo/ro-RO.yml +886 -0
  344. data/config/locales/todo/ru.yml +379 -0
  345. data/config/locales/todo/si-LK.yml +1 -0
  346. data/config/locales/todo/sk-SK.yml +896 -0
  347. data/config/locales/todo/sk.yml +851 -0
  348. data/config/locales/todo/sl.yml +26 -0
  349. data/config/locales/todo/so-SO.yml +1 -0
  350. data/config/locales/todo/sr-CS.yml +125 -0
  351. data/config/locales/todo/sv.yml +908 -0
  352. data/config/locales/todo/sw-KE.yml +1 -0
  353. data/config/locales/todo/ti-ER.yml +1 -0
  354. data/config/locales/todo/tr-TR.yml +890 -0
  355. data/config/locales/todo/uk.yml +379 -0
  356. data/config/locales/todo/vi-VN.yml +1 -0
  357. data/config/locales/todo/vi.yml +1 -0
  358. data/config/locales/todo/zh-CN.yml +857 -0
  359. data/config/locales/todo/zh-TW.yml +1 -0
  360. data/db/migrate/20161212110850_create_decidim_paragraphs.rb +16 -0
  361. data/db/migrate/20170112115253_create_paragraph_votes.rb +14 -0
  362. data/db/migrate/20170113114245_add_enhanced_textwork_text_search_indexes.rb +8 -0
  363. data/db/migrate/20170118120151_add_counter_cache_votes_to_paragraphs.rb +7 -0
  364. data/db/migrate/20170120151202_add_user_group_id_to_paragraphs.rb +7 -0
  365. data/db/migrate/20170131092413_add_answers_to_paragraphs.rb +9 -0
  366. data/db/migrate/20170205082832_add_index_to_decidim_enhanced_textwork_paragraphs_paragraph_votes_count.rb +9 -0
  367. data/db/migrate/20170215113152_create_paragraph_reports.rb +16 -0
  368. data/db/migrate/20170215131720_add_report_count_to_paragraphs.rb +7 -0
  369. data/db/migrate/20170215132030_add_reference_to_paragraphs.rb +13 -0
  370. data/db/migrate/20170220152416_add_hidden_at_to_paragraphs.rb +7 -0
  371. data/db/migrate/20170228105156_add_geolocalization_fields_to_paragraphs.rb +9 -0
  372. data/db/migrate/20170307085300_migrate_paragraph_reports_data_to_reports.rb +24 -0
  373. data/db/migrate/20170410073742_remove_not_null_reference_paragraphs.rb +7 -0
  374. data/db/migrate/20170612101809_migrate_paragraphs_category.rb +15 -0
  375. data/db/migrate/20171201115434_create_paragraph_endorsements.rb +16 -0
  376. data/db/migrate/20171201122623_add_counter_cache_endorsements_to_paragraphs.rb +8 -0
  377. data/db/migrate/20171212102250_enable_pg_trgm_extension_for_paragraphs.rb +18 -0
  378. data/db/migrate/20171220084719_add_published_at_to_paragraphs.rb +14 -0
  379. data/db/migrate/20180111110204_create_decidim_paragraph_notes.rb +15 -0
  380. data/db/migrate/20180115155220_add_index_created_at_paragraph_notes.rb +7 -0
  381. data/db/migrate/20180305133811_rename_features_to_components_at_paragraphs.rb +11 -0
  382. data/db/migrate/20180326091532_create_decidim_enhanced_textwork_collaborative_drafts.rb +29 -0
  383. data/db/migrate/20180413135249_fix_nil_threshold_per_paragraph.rb +18 -0
  384. data/db/migrate/20180529101323_add_counter_cache_coauthorships_to_paragraphs.rb +8 -0
  385. data/db/migrate/20180529110230_move_enhanced_textwork_authorships_to_coauthorships.rb +28 -0
  386. data/db/migrate/20180529110830_remove_authorships_from_paragraphs.rb +8 -0
  387. data/db/migrate/20180613151121_create_enhanced_textwork_collaborative_draft_collaborator_requests.rb +12 -0
  388. data/db/migrate/20180711074134_add_enhanced_textwork_counter_cache_coauthorships_to_collaborative_drafts.rb +7 -0
  389. data/db/migrate/20180711075004_remove_index_counter_cache_coauthorships_to_paragraphs.rb +7 -0
  390. data/db/migrate/20180927111721_create_enhanced_textwork_participatory_texts.rb +13 -0
  391. data/db/migrate/20180930125321_add_participatory_text_level_to_paragraphs.rb +7 -0
  392. data/db/migrate/20180930125321_add_position_to_paragraphs.rb +7 -0
  393. data/db/migrate/20181003074440_fix_user_groups_ids_in_paragraphs_endorsements.rb +20 -0
  394. data/db/migrate/20181010114622_add_enhanced_textwork_temporary_votes.rb +9 -0
  395. data/db/migrate/20181016132225_add_enhanced_textwork_organization_as_author.rb +13 -0
  396. data/db/migrate/20181017084221_make_author_polymorhpic_for_paragraph_endorsements.rb +31 -0
  397. data/db/migrate/20181026073215_add_enhanced_textwork_created_in_meeting.rb +7 -0
  398. data/db/migrate/20190215113158_use_enhanced_textwork_md5_indexes.rb +17 -0
  399. data/db/migrate/20191206154128_add_endorsements_counter_cache_to_paragraphs.rb +7 -0
  400. data/db/migrate/20200120215928_move_paragraph_endorsements_to_core_endorsements.rb +54 -0
  401. data/db/migrate/20200120230130_drop_paragraph_endorsements.rb +8 -0
  402. data/db/migrate/20200203111239_add_paragraph_valuation_assignments.rb +12 -0
  403. data/db/migrate/20200210135152_add_costs_to_paragraphs.rb +9 -0
  404. data/db/migrate/20200212120110_sync_paragraphs_state_with_amendments_state.rb +28 -0
  405. data/db/migrate/20200227175922_add_state_published_at_to_paragraphs.rb +7 -0
  406. data/db/migrate/20200306123652_publish_existing_paragraphs_state.rb +15 -0
  407. data/db/migrate/20200708091228_move_paragraphs_fields_to_i18n.rb +86 -0
  408. data/db/migrate/20200730131631_move_paragraph_endorsed_event_notifications_to_resource_endorsed_event.rb +20 -0
  409. data/db/migrate/20200827154156_add_commentable_counter_cache_to_paragraphs.rb +12 -0
  410. data/db/migrate/20201002085508_fix_paragraphs_data.rb +36 -0
  411. data/db/migrate/20210127115628_fix_answered_paragraphs_after_copy.rb +14 -0
  412. data/db/migrate/20210310102839_add_followable_counter_cache_to_paragraphs.rb +16 -0
  413. data/db/migrate/20210310120812_add_enhanced_textwork_followable_counter_cache_to_collaborative_drafts.rb +16 -0
  414. data/db/migrate/20210318082934_fix_counters_for_copied_paragraphs.rb +19 -0
  415. data/lib/decidim/api/paragraph_input_filter.rb +29 -0
  416. data/lib/decidim/api/paragraph_input_sort.rb +20 -0
  417. data/lib/decidim/api/paragraph_type.rb +56 -0
  418. data/lib/decidim/api/paragraphs_type.rb +43 -0
  419. data/lib/decidim/content_parsers/paragraph_parser.rb +101 -0
  420. data/lib/decidim/content_renderers/paragraph_renderer.rb +33 -0
  421. data/lib/decidim/enhanced_textwork/admin.rb +10 -0
  422. data/lib/decidim/enhanced_textwork/admin_engine.rb +52 -0
  423. data/lib/decidim/enhanced_textwork/api.rb +10 -0
  424. data/lib/decidim/enhanced_textwork/commentable_collaborative_draft.rb +38 -0
  425. data/lib/decidim/enhanced_textwork/commentable_paragraph.rb +36 -0
  426. data/lib/decidim/enhanced_textwork/component.rb +448 -0
  427. data/lib/decidim/enhanced_textwork/doc_to_markdown.rb +50 -0
  428. data/lib/decidim/enhanced_textwork/engine.rb +204 -0
  429. data/lib/decidim/enhanced_textwork/html_to_markdown.rb +22 -0
  430. data/lib/decidim/enhanced_textwork/markdown_to_paragraphs.rb +153 -0
  431. data/lib/decidim/enhanced_textwork/odt_to_markdown.rb +46 -0
  432. data/lib/decidim/enhanced_textwork/paragraph_creator.rb +98 -0
  433. data/lib/decidim/enhanced_textwork/paragraph_serializer.rb +95 -0
  434. data/lib/decidim/enhanced_textwork/participatory_text_section.rb +21 -0
  435. data/lib/decidim/enhanced_textwork/test/capybara_paragraphs_picker.rb +59 -0
  436. data/lib/decidim/enhanced_textwork/test/factories.rb +492 -0
  437. data/lib/decidim/enhanced_textwork/valuatable.rb +21 -0
  438. data/lib/decidim/enhanced_textwork/version.rb +14 -0
  439. data/lib/decidim/enhanced_textwork.rb +58 -0
  440. data/lib/decidim/exporters/word.rb +309 -0
  441. metadata +704 -0
@@ -0,0 +1,58 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ module Metrics
6
+ class EndorsementsMetricManage < Decidim::MetricManage
7
+ def metric_name
8
+ "endorsements"
9
+ end
10
+
11
+ def save
12
+ cumulative.each do |key, cumulative_value|
13
+ next if cumulative_value.zero?
14
+
15
+ quantity_value = quantity[key] || 0
16
+ category_id, space_type, space_id, paragraph_id = key
17
+ record = Decidim::Metric.find_or_initialize_by(day: @day.to_s, metric_type: @metric_name,
18
+ organization: @organization, decidim_category_id: category_id,
19
+ participatory_space_type: space_type, participatory_space_id: space_id,
20
+ related_object_type: "Decidim::EnhancedTextwork::Paragraph", related_object_id: paragraph_id)
21
+ record.assign_attributes(cumulative: cumulative_value, quantity: quantity_value)
22
+ record.save!
23
+ end
24
+ end
25
+
26
+ private
27
+
28
+ def query
29
+ return @query if @query
30
+
31
+ components = Decidim::Component.where(participatory_space: retrieve_participatory_spaces).published
32
+ paragraphs = Decidim::EnhancedTextwork::Paragraph.where(component: components).except_withdrawn
33
+ join_components = "INNER JOIN decidim_components ON decidim_components.manifest_name = 'paragraphs' AND paragraphs.decidim_component_id = decidim_components.id"
34
+ join_categories = <<~EOJOINCATS
35
+ LEFT OUTER JOIN decidim_categorizations
36
+ ON (paragraphs.id = decidim_categorizations.categorizable_id
37
+ AND decidim_categorizations.categorizable_type = 'Decidim::EnhancedTextwork::Paragraph')
38
+ EOJOINCATS
39
+ @query = Decidim::Endorsement.joins("INNER JOIN decidim_enhanced_textwork_paragraphs paragraphs ON resource_id = paragraphs.id")
40
+ .joins(join_components)
41
+ .joins(join_categories)
42
+ .where(resource_id: paragraphs.pluck(:id))
43
+ .where(resource_type: Decidim::EnhancedTextwork::Paragraph.name)
44
+ @query = @query.where("decidim_endorsements.created_at <= ?", end_time)
45
+ @query = @query.group("decidim_categorizations.id",
46
+ :participatory_space_type,
47
+ :participatory_space_id,
48
+ :resource_id)
49
+ @query
50
+ end
51
+
52
+ def quantity
53
+ @quantity ||= query.where("decidim_endorsements.created_at >= ?", start_time).count
54
+ end
55
+ end
56
+ end
57
+ end
58
+ end
@@ -0,0 +1,58 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ module Metrics
6
+ # Searches for unique Users following the next objects
7
+ # - Paragraphs
8
+ # - CollaborativeDrafts
9
+ class ParagraphFollowersMetricMeasure < Decidim::MetricMeasure
10
+ def valid?
11
+ super && @resource.is_a?(Decidim::Component)
12
+ end
13
+
14
+ def calculate
15
+ cumulative_users = []
16
+ cumulative_users |= retrieve_paragraphs_followers.pluck(:decidim_user_id)
17
+ cumulative_users |= retrieve_drafts_followers.pluck(:decidim_user_id)
18
+
19
+ quantity_users = []
20
+ quantity_users |= retrieve_paragraphs_followers(from_start: true).pluck(:decidim_user_id)
21
+ quantity_users |= retrieve_drafts_followers(from_start: true).pluck(:decidim_user_id)
22
+
23
+ {
24
+ cumulative_users: cumulative_users.uniq,
25
+ quantity_users: quantity_users.uniq
26
+ }
27
+ end
28
+
29
+ private
30
+
31
+ def retrieve_paragraphs_followers(from_start: false)
32
+ @paragraphs_followers ||= Decidim::Follow.where(followable: retrieve_paragraphs).joins(:user)
33
+ .where("decidim_follows.created_at <= ?", end_time)
34
+
35
+ return @paragraphs_followers.where("decidim_follows.created_at >= ?", start_time) if from_start
36
+
37
+ @paragraphs_followers
38
+ end
39
+
40
+ def retrieve_drafts_followers(from_start: false)
41
+ @drafts_followers ||= Decidim::Follow.where(followable: retrieve_collaborative_drafts).joins(:user)
42
+ .where("decidim_follows.created_at <= ?", end_time)
43
+ return @drafts_followers.where("decidim_follows.created_at >= ?", start_time) if from_start
44
+
45
+ @drafts_followers
46
+ end
47
+
48
+ def retrieve_paragraphs
49
+ Decidim::EnhancedTextwork::Paragraph.where(component: @resource).except_withdrawn
50
+ end
51
+
52
+ def retrieve_collaborative_drafts
53
+ Decidim::EnhancedTextwork::CollaborativeDraft.where(component: @resource).except_withdrawn
54
+ end
55
+ end
56
+ end
57
+ end
58
+ end
@@ -0,0 +1,74 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ module Metrics
6
+ # Searches for Participants in the following actions
7
+ # - Create a paragraph (Paragraphs)
8
+ # - Give support to a paragraph (Paragraphs)
9
+ # - Endorse (Paragraphs)
10
+ class ParagraphParticipantsMetricMeasure < Decidim::MetricMeasure
11
+ def valid?
12
+ super && @resource.is_a?(Decidim::Component)
13
+ end
14
+
15
+ def calculate
16
+ cumulative_users = []
17
+ cumulative_users |= retrieve_votes.pluck(:decidim_author_id)
18
+ cumulative_users |= retrieve_endorsements.pluck(:decidim_author_id)
19
+ cumulative_users |= retrieve_paragraphs.pluck("decidim_coauthorships.decidim_author_id") # To avoid ambiguosity must be called this way
20
+
21
+ quantity_users = []
22
+ quantity_users |= retrieve_votes(from_start: true).pluck(:decidim_author_id)
23
+ quantity_users |= retrieve_endorsements(from_start: true).pluck(:decidim_author_id)
24
+ quantity_users |= retrieve_paragraphs(from_start: true).pluck("decidim_coauthorships.decidim_author_id") # To avoid ambiguosity must be called this way
25
+
26
+ {
27
+ cumulative_users: cumulative_users.uniq,
28
+ quantity_users: quantity_users.uniq
29
+ }
30
+ end
31
+
32
+ private
33
+
34
+ def retrieve_paragraphs(from_start: false)
35
+ @paragraphs ||= Decidim::EnhancedTextwork::Paragraph.where(component: @resource).joins(:coauthorships)
36
+ .includes(:votes, :endorsements)
37
+ .where(decidim_coauthorships: {
38
+ decidim_author_type: [
39
+ "Decidim::UserBaseEntity",
40
+ "Decidim::Organization",
41
+ "Decidim::Meetings::Meeting"
42
+ ]
43
+ })
44
+ .where("decidim_enhanced_textwork_paragraphs.published_at <= ?", end_time)
45
+ .except_withdrawn
46
+
47
+ return @paragraphs.where("decidim_enhanced_textwork_paragraphs.published_at >= ?", start_time) if from_start
48
+
49
+ @paragraphs
50
+ end
51
+
52
+ def retrieve_votes(from_start: false)
53
+ @votes ||= Decidim::EnhancedTextwork::ParagraphVote.joins(:paragraph).where(paragraph: retrieve_paragraphs).joins(:author)
54
+ .where("decidim_enhanced_textwork_paragraph_votes.created_at <= ?", end_time)
55
+
56
+ return @votes.where("decidim_enhanced_textwork_paragraph_votes.created_at >= ?", start_time) if from_start
57
+
58
+ @votes
59
+ end
60
+
61
+ def retrieve_endorsements(from_start: false)
62
+ @endorsements ||= Decidim::Endorsement.joins("INNER JOIN decidim_enhanced_textwork_paragraphs paragraphs ON resource_id = paragraphs.id")
63
+ .where(resource: retrieve_paragraphs)
64
+ .where("decidim_endorsements.created_at <= ?", end_time)
65
+ .where(decidim_author_type: "Decidim::UserBaseEntity")
66
+
67
+ return @endorsements.where("decidim_endorsements.created_at >= ?", start_time) if from_start
68
+
69
+ @endorsements
70
+ end
71
+ end
72
+ end
73
+ end
74
+ end
@@ -0,0 +1,48 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ module Metrics
6
+ class ParagraphsMetricManage < Decidim::MetricManage
7
+ def metric_name
8
+ "paragraphs"
9
+ end
10
+
11
+ def save
12
+ cumulative.each do |key, cumulative_value|
13
+ next if cumulative_value.zero?
14
+
15
+ quantity_value = quantity[key] || 0
16
+ category_id, space_type, space_id = key
17
+ record = Decidim::Metric.find_or_initialize_by(day: @day.to_s, metric_type: @metric_name,
18
+ organization: @organization, decidim_category_id: category_id,
19
+ participatory_space_type: space_type, participatory_space_id: space_id)
20
+ record.assign_attributes(cumulative: cumulative_value, quantity: quantity_value)
21
+ record.save!
22
+ end
23
+ end
24
+
25
+ private
26
+
27
+ def query
28
+ return @query if @query
29
+
30
+ spaces = Decidim.participatory_space_manifests.flat_map do |manifest|
31
+ manifest.participatory_spaces.call(@organization)
32
+ end
33
+ @query = Decidim::EnhancedTextwork::Paragraph.where(component: visible_components_from_spaces(spaces)).joins(:component)
34
+ .left_outer_joins(:category)
35
+ @query = @query.where("decidim_enhanced_textwork_paragraphs.published_at <= ?", end_time).except_withdrawn.not_hidden
36
+ @query = @query.group("decidim_categorizations.decidim_category_id",
37
+ :participatory_space_type,
38
+ :participatory_space_id)
39
+ @query
40
+ end
41
+
42
+ def quantity
43
+ @quantity ||= query.where("decidim_enhanced_textwork_paragraphs.published_at >= ?", start_time).count
44
+ end
45
+ end
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,52 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ module Metrics
6
+ class VotesMetricManage < Decidim::MetricManage
7
+ def metric_name
8
+ "votes"
9
+ end
10
+
11
+ def save
12
+ cumulative.each do |key, cumulative_value|
13
+ next if cumulative_value.zero?
14
+
15
+ quantity_value = quantity[key] || 0
16
+ category_id, space_type, space_id, paragraph_id = key
17
+ record = Decidim::Metric.find_or_initialize_by(day: @day.to_s, metric_type: @metric_name,
18
+ organization: @organization, decidim_category_id: category_id,
19
+ participatory_space_type: space_type, participatory_space_id: space_id,
20
+ related_object_type: "Decidim::EnhancedTextwork::Paragraph", related_object_id: paragraph_id)
21
+ record.assign_attributes(cumulative: cumulative_value, quantity: quantity_value)
22
+ record.save!
23
+ end
24
+ end
25
+
26
+ private
27
+
28
+ def query
29
+ return @query if @query
30
+
31
+ spaces = Decidim.participatory_space_manifests.flat_map do |manifest|
32
+ manifest.participatory_spaces.call(@organization).public_spaces
33
+ end
34
+ paragraph_ids = Decidim::EnhancedTextwork::Paragraph.where(component: visible_components_from_spaces(spaces)).except_withdrawn.not_hidden.pluck(:id)
35
+ @query = Decidim::EnhancedTextwork::ParagraphVote.joins(paragraph: :component)
36
+ .left_outer_joins(paragraph: :category)
37
+ .where(paragraph: paragraph_ids)
38
+ @query = @query.where("decidim_enhanced_textwork_paragraph_votes.created_at <= ?", end_time)
39
+ @query = @query.group("decidim_categorizations.id",
40
+ :participatory_space_type,
41
+ :participatory_space_id,
42
+ :decidim_paragraph_id)
43
+ @query
44
+ end
45
+
46
+ def quantity
47
+ @quantity ||= query.where("decidim_enhanced_textwork_paragraph_votes.created_at >= ?", start_time).count
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,67 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ # Class used to retrieve similar paragraphs.
6
+ class SimilarParagraphs < Rectify::Query
7
+ include Decidim::TranslationsHelper
8
+
9
+ # Syntactic sugar to initialize the class and return the queried objects.
10
+ #
11
+ # components - Decidim::CurrentComponent
12
+ # paragraph - Decidim::EnhancedTextwork::Paragraph
13
+ def self.for(components, paragraph)
14
+ new(components, paragraph).query
15
+ end
16
+
17
+ # Initializes the class.
18
+ #
19
+ # components - Decidim::CurrentComponent
20
+ # paragraph - Decidim::EnhancedTextwork::Paragraph
21
+ def initialize(components, paragraph)
22
+ @components = components
23
+ @paragraph = paragraph
24
+ @translations_enabled = paragraph.component.organization.enable_machine_translations
25
+ end
26
+
27
+ # Retrieves similar paragraphs
28
+ def query
29
+ Decidim::EnhancedTextwork::Paragraph
30
+ .where(component: @components)
31
+ .published
32
+ .not_hidden
33
+ .where(
34
+ "GREATEST(#{title_similarity}, #{body_similarity}) >= ?",
35
+ *similarity_params,
36
+ Decidim::EnhancedTextwork.similarity_threshold
37
+ )
38
+ .limit(Decidim::EnhancedTextwork.similarity_limit)
39
+ end
40
+
41
+ private
42
+
43
+ attr_reader :translations_enabled, :paragraph
44
+
45
+ def title_similarity
46
+ return "similarity(title::text, ?)" unless translations_enabled
47
+
48
+ language = paragraph.content_original_language
49
+ "similarity(title->>'#{language}'::text, ?), similarity(title->'machine_translations'->>'#{language}'::text, ?)"
50
+ end
51
+
52
+ def body_similarity
53
+ return "similarity(body::text, ?)" unless translations_enabled
54
+
55
+ language = paragraph.content_original_language
56
+ "similarity(body->>'#{language}'::text, ?), similarity(body->'machine_translations'->>'#{language}'::text, ?)"
57
+ end
58
+
59
+ def similarity_params
60
+ title_attr = translated_attribute(paragraph.title)
61
+ body_attr = translated_attribute(paragraph.body)
62
+
63
+ translations_enabled ? [title_attr, title_attr, body_attr, body_attr] : [title_attr, body_attr]
64
+ end
65
+ end
66
+ end
67
+ end
@@ -0,0 +1,59 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ # A service to encapsualte all the logic when searching and filtering
6
+ # collaborative drafts in a participatory process.
7
+ class CollaborativeDraftSearch < ResourceSearch
8
+ text_search_fields :title, :body
9
+
10
+ # Public: Initializes the service.
11
+ # component - A Decidim::Component to get the drafts from.
12
+ # page - The page number to paginate the results.
13
+ # per_page - The number of drafts to return per page.
14
+ def initialize(options = {})
15
+ super(CollaborativeDraft.all, options)
16
+ end
17
+
18
+ # Handle the search_text filter
19
+ #
20
+ # We can't use the search from `ResourceFilter` since these fields aren't
21
+ # translated.
22
+ def search_search_text
23
+ query
24
+ .where("title::text ILIKE ?", "%#{search_text}%")
25
+ .or(query.where("body ILIKE ?", "%#{search_text}%"))
26
+ end
27
+
28
+ # Handle the state filter
29
+ def search_state
30
+ return query if state.member?("all")
31
+
32
+ apply_scopes(%w(open withdrawn published), state)
33
+ end
34
+
35
+ # Filters drafts by the name of the classes they are linked to. By default,
36
+ # returns all drafts. When a `related_to` param is given, then it camelcases item
37
+ # to find the real class name and checks the links for the Collaborative Draft.
38
+ #
39
+ # The `related_to` param is expected to be in this form:
40
+ #
41
+ # "decidim/meetings/meeting"
42
+ #
43
+ # This can be achieved by performing `klass.name.underscore`.
44
+ #
45
+ # Returns only those drafts that are linked to the given class name.
46
+ def search_related_to
47
+ from = query
48
+ .joins(:resource_links_from)
49
+ .where(decidim_resource_links: { to_type: related_to.camelcase })
50
+
51
+ to = query
52
+ .joins(:resource_links_to)
53
+ .where(decidim_resource_links: { from_type: related_to.camelcase })
54
+
55
+ query.where(id: from).or(query.where(id: to))
56
+ end
57
+ end
58
+ end
59
+ end
@@ -0,0 +1,74 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module EnhancedTextwork
5
+ class DiffRenderer < BaseDiffRenderer
6
+ private
7
+
8
+ # Lists which attributes will be diffable and how they should be rendered.
9
+ def attribute_types
10
+ {
11
+ title: :i18n,
12
+ body: :i18n,
13
+ decidim_category_id: :category,
14
+ decidim_scope_id: :scope,
15
+ address: :string,
16
+ latitude: :string,
17
+ longitude: :string,
18
+ state: :string
19
+ }
20
+ end
21
+
22
+ # Parses the values before parsing the changeset.
23
+ def parse_changeset(attribute, values, type, diff)
24
+ return parse_scope_changeset(attribute, values, type, diff) if type == :scope
25
+
26
+ values = parse_values(attribute, values)
27
+ old_value = values[0]
28
+ new_value = values[1]
29
+
30
+ diff.update(
31
+ attribute => {
32
+ type: type,
33
+ label: I18n.t(attribute, scope: i18n_scope),
34
+ old_value: old_value,
35
+ new_value: new_value
36
+ }
37
+ )
38
+ end
39
+
40
+ # Handles which values to use when diffing emendations and
41
+ # normalizes line endings of the :body attribute values.
42
+ # Returns and Array of two Strings.
43
+ def parse_values(attribute, values)
44
+ values = [amended_previous_value(attribute), values[1]] if paragraph&.emendation?
45
+ values = values.map { |value| normalize_line_endings(value) } if attribute == :body
46
+ values
47
+ end
48
+
49
+ # Sets the previous value so the emendation can be compared with the amended paragraph.
50
+ # If the amendment is being evaluated, returns the CURRENT attribute value of the amended paragraph;
51
+ # else, returns the attribute value of amended paragraph at the moment of making the amendment.
52
+ def amended_previous_value(attribute)
53
+ if paragraph.amendment.evaluating?
54
+ paragraph.amendable.attributes[attribute.to_s]
55
+ else # See Decidim::Amendable::PublishDraft#set_first_emendation_version
56
+ paragraph.versions.first.changeset[attribute.to_s].last
57
+ end
58
+ end
59
+
60
+ # Returns a String with the newline escape sequences normalized.
61
+ def normalize_line_endings(value)
62
+ if value.is_a?(Hash)
63
+ value.values.map { |subvalue| normalize_line_endings(subvalue) }
64
+ else
65
+ Decidim::ContentParsers::NewlineParser.new(value, context: {}).rewrite
66
+ end
67
+ end
68
+
69
+ def paragraph
70
+ @paragraph ||= Paragraph.find_by(id: version.item_id)
71
+ end
72
+ end
73
+ end
74
+ end
@@ -0,0 +1,132 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "open-uri"
4
+
5
+ module Decidim
6
+ module EnhancedTextwork
7
+ # A factory class to ensure we always create Paragraphs the same way since it involves some logic.
8
+ module ParagraphBuilder
9
+ # Public: Creates a new Paragraph.
10
+ #
11
+ # attributes - The Hash of attributes to create the Paragraph with.
12
+ # author - An Authorable the will be the first coauthor of the Paragraph.
13
+ # user_group_author - A User Group to, optionally, set it as the author too.
14
+ # action_user - The User to be used as the user who is creating the paragraph in the traceability logs.
15
+ #
16
+ # Returns a Paragraph.
17
+ def create(attributes:, author:, action_user:, user_group_author: nil)
18
+ Decidim.traceability.perform_action!(:create, Paragraph, action_user, visibility: "all") do
19
+ paragraph = Paragraph.new(attributes)
20
+ paragraph.add_coauthor(author, user_group: user_group_author)
21
+ paragraph.save!
22
+ paragraph
23
+ end
24
+ end
25
+
26
+ module_function :create
27
+
28
+ # Public: Creates a new Paragraph with the authors of the `original_paragraph`.
29
+ #
30
+ # attributes - The Hash of attributes to create the Paragraph with.
31
+ # action_user - The User to be used as the user who is creating the paragraph in the traceability logs.
32
+ # original_paragraph - The paragraph from which authors will be copied.
33
+ #
34
+ # Returns a Paragraph.
35
+ def create_with_authors(attributes:, action_user:, original_paragraph:)
36
+ Decidim.traceability.perform_action!(:create, Paragraph, action_user, visibility: "all") do
37
+ paragraph = Paragraph.new(attributes)
38
+ original_paragraph.coauthorships.each do |coauthorship|
39
+ paragraph.add_coauthor(coauthorship.author, user_group: coauthorship.user_group)
40
+ end
41
+ paragraph.save!
42
+ paragraph
43
+ end
44
+ end
45
+
46
+ module_function :create_with_authors
47
+
48
+ # Public: Creates a new Paragraph by copying the attributes from another one.
49
+ #
50
+ # original_paragraph - The Paragraph to be used as base to create the new one.
51
+ # author - An Authorable the will be the first coauthor of the Paragraph.
52
+ # user_group_author - A User Group to, optionally, set it as the author too.
53
+ # action_user - The User to be used as the user who is creating the paragraph in the traceability logs.
54
+ # extra_attributes - A Hash of attributes to create the new paragraph, will overwrite the original ones.
55
+ # skip_link - Whether to skip linking the two paragraphs or not (default false).
56
+ #
57
+ # Returns a Paragraph
58
+ #
59
+ # rubocop:disable Metrics/ParameterLists
60
+ def copy(original_paragraph, author:, action_user:, user_group_author: nil, extra_attributes: {}, skip_link: false)
61
+ origin_attributes = original_paragraph.attributes.except(
62
+ "id",
63
+ "created_at",
64
+ "updated_at",
65
+ "state",
66
+ "state_published_at",
67
+ "answer",
68
+ "answered_at",
69
+ "decidim_component_id",
70
+ "reference",
71
+ "comments_count",
72
+ "endorsements_count",
73
+ "follows_count",
74
+ "paragraph_notes_count",
75
+ "paragraph_votes_count"
76
+ ).merge(
77
+ "category" => original_paragraph.category
78
+ ).merge(
79
+ extra_attributes
80
+ )
81
+
82
+ paragraph = if author.nil?
83
+ create_with_authors(
84
+ attributes: origin_attributes,
85
+ original_paragraph: original_paragraph,
86
+ action_user: action_user
87
+ )
88
+ else
89
+ create(
90
+ attributes: origin_attributes,
91
+ author: author,
92
+ user_group_author: user_group_author,
93
+ action_user: action_user
94
+ )
95
+ end
96
+
97
+ paragraph.link_resources(original_paragraph, "copied_from_component") unless skip_link
98
+ copy_attachments(original_paragraph, paragraph)
99
+
100
+ paragraph
101
+ end
102
+ # rubocop:enable Metrics/ParameterLists
103
+
104
+ module_function :copy
105
+
106
+ def copy_attachments(original_paragraph, paragraph)
107
+ original_paragraph.attachments.each do |attachment|
108
+ new_attachment = Decidim::Attachment.new(
109
+ {
110
+ # Attached to needs to be always defined before the file is set
111
+ attached_to: paragraph
112
+ }.merge(
113
+ attachment.attributes.slice("content_type", "description", "file_size", "title", "weight")
114
+ )
115
+ )
116
+
117
+ if attachment.file.attached?
118
+ new_attachment.file = attachment.file.blob
119
+ else
120
+ new_attachment.attached_uploader(:file).remote_url = attachment.attached_uploader(:file).url(host: original_paragraph.organization.host)
121
+ end
122
+
123
+ new_attachment.save!
124
+ rescue Errno::ENOENT, OpenURI::HTTPError => e
125
+ Rails.logger.warn("[ERROR] Couldn't copy attachment from paragraph #{original_paragraph.id} when copying to component due to #{e.message}")
126
+ end
127
+ end
128
+
129
+ module_function :copy_attachments
130
+ end
131
+ end
132
+ end