decidim-assemblies 0.23.1 → 0.24.0.rc2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (84) hide show
  1. checksums.yaml +4 -4
  2. data/app/cells/decidim/assemblies/assembly_m_cell.rb +2 -0
  3. data/app/cells/decidim/assemblies/statistic/show.erb +9 -0
  4. data/app/cells/decidim/assemblies/statistic_cell.rb +20 -0
  5. data/app/cells/decidim/assemblies/statistics/show.erb +17 -0
  6. data/app/cells/decidim/assemblies/statistics_cell.rb +18 -0
  7. data/app/commands/decidim/assemblies/admin/create_assembly.rb +1 -0
  8. data/app/commands/decidim/assemblies/admin/create_assembly_admin.rb +12 -72
  9. data/app/commands/decidim/assemblies/admin/update_assembly.rb +2 -1
  10. data/app/controllers/decidim/assemblies/admin/imports_controller.rb +14 -0
  11. data/app/controllers/decidim/assemblies/admin/moderations/reports_controller.rb +14 -0
  12. data/app/controllers/decidim/assemblies/assemblies_controller.rb +1 -1
  13. data/app/events/decidim/role_assigned_to_assembly_event.rb +1 -1
  14. data/app/forms/decidim/assemblies/admin/assembly_form.rb +3 -0
  15. data/app/forms/decidim/assemblies/admin/assembly_user_role_form.rb +0 -5
  16. data/app/helpers/decidim/assemblies/admin/assemblies_admin_menu_helper.rb +15 -0
  17. data/app/models/decidim/assembly.rb +3 -3
  18. data/app/presenters/decidim/assemblies/admin_log/assemblies_type_presenter.rb +2 -2
  19. data/app/presenters/decidim/assemblies/admin_log/assembly_member_presenter.rb +2 -2
  20. data/app/presenters/decidim/assemblies/admin_log/assembly_presenter.rb +2 -2
  21. data/app/presenters/decidim/assemblies/admin_log/assembly_user_role_presenter.rb +2 -2
  22. data/app/presenters/decidim/assemblies/assembly_stats_presenter.rb +35 -25
  23. data/app/queries/decidim/assemblies/organization_assemblies.rb +1 -1
  24. data/app/queries/decidim/assemblies/organization_published_assemblies.rb +1 -1
  25. data/app/serializers/decidim/assemblies/assembly_serializer.rb +1 -0
  26. data/app/views/decidim/assemblies/admin/assemblies/_form.html.erb +4 -0
  27. data/app/views/decidim/assemblies/admin/assemblies/index.html.erb +11 -1
  28. data/app/views/decidim/assemblies/assemblies/show.html.erb +1 -1
  29. data/app/views/layouts/decidim/admin/assemblies.html.erb +2 -20
  30. data/app/views/layouts/decidim/admin/assembly.html.erb +2 -1
  31. data/config/locales/ar.yml +2 -1
  32. data/config/locales/ca.yml +13 -4
  33. data/config/locales/cs.yml +25 -16
  34. data/config/locales/de.yml +65 -53
  35. data/config/locales/el.yml +2 -4
  36. data/config/locales/en.yml +12 -3
  37. data/config/locales/es-MX.yml +12 -3
  38. data/config/locales/es-PY.yml +12 -3
  39. data/config/locales/es.yml +12 -3
  40. data/config/locales/eu.yml +2 -1
  41. data/config/locales/fi-plain.yml +13 -4
  42. data/config/locales/fi.yml +16 -7
  43. data/config/locales/fr-CA.yml +12 -3
  44. data/config/locales/fr.yml +13 -4
  45. data/config/locales/gl.yml +39 -17
  46. data/config/locales/hu.yml +2 -4
  47. data/config/locales/id-ID.yml +2 -1
  48. data/config/locales/is-IS.yml +23 -1
  49. data/config/locales/it.yml +8 -4
  50. data/config/locales/ja.yml +8 -4
  51. data/config/locales/lv.yml +2 -4
  52. data/config/locales/nl.yml +17 -5
  53. data/config/locales/no.yml +12 -11
  54. data/config/locales/pl.yml +19 -7
  55. data/config/locales/pt-BR.yml +2 -1
  56. data/config/locales/pt.yml +2 -4
  57. data/config/locales/ro-RO.yml +149 -102
  58. data/config/locales/ru.yml +3 -2
  59. data/config/locales/si-LK.yml +1 -0
  60. data/config/locales/sk.yml +0 -3
  61. data/config/locales/sl.yml +2 -1
  62. data/config/locales/sr-CS.yml +0 -3
  63. data/config/locales/sv.yml +4 -5
  64. data/config/locales/sw-KE.yml +1 -0
  65. data/config/locales/tr-TR.yml +225 -153
  66. data/config/locales/uk.yml +3 -2
  67. data/config/locales/zh-CN.yml +2 -4
  68. data/db/migrate/20210204152393_add_weight_field_to_assembly.rb +7 -0
  69. data/lib/decidim/api/assemblies_type_type.rb +16 -0
  70. data/lib/decidim/api/assembly_member_type.rb +28 -0
  71. data/lib/decidim/api/assembly_type.rb +64 -0
  72. data/lib/decidim/assemblies.rb +1 -0
  73. data/lib/decidim/assemblies/admin_engine.rb +31 -1
  74. data/lib/decidim/assemblies/api.rb +9 -0
  75. data/lib/decidim/assemblies/engine.rb +3 -5
  76. data/lib/decidim/assemblies/participatory_space.rb +38 -38
  77. data/lib/decidim/assemblies/query_extensions.rb +39 -20
  78. data/lib/decidim/assemblies/test/factories.rb +5 -4
  79. data/lib/decidim/assemblies/version.rb +1 -1
  80. metadata +29 -19
  81. data/app/types/decidim/assemblies/assemblies_type_type.rb +0 -17
  82. data/app/types/decidim/assemblies/assembly_member_type.rb +0 -29
  83. data/app/types/decidim/assemblies/assembly_type.rb +0 -67
  84. data/app/views/decidim/assemblies/assemblies/_statistics.html.erb +0 -10
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 14a57e28c47e324ad6eccfae0739b11f694a592524897b3050b9c2298be03d9b
4
- data.tar.gz: ef3a2ac737a5a09fda27ce64745897adc0e72ad6fffbd5d1d9532c178308aaf3
3
+ metadata.gz: cd7fb3a5b3f9d98cc9726e71eeed8299fd5bee6b658c78df23c86be5039102e0
4
+ data.tar.gz: d632427f79df83e271a36bd869028678210744e1e0fcb5b8da035a47088b61ac
5
5
  SHA512:
6
- metadata.gz: c35cf008d9f11ed052bf64d1a5cd271893c8a75355ea721b716940055fe3e4872cb72f27918073fd6f0ae29ee5624e1e4ef14d634579f77ebd01e443a63588a7
7
- data.tar.gz: '002951e359e52ced0da4355357b0418bd9a3e8b79ac65499a1dd6cd68a6de70a316e17b9135ce54f07b72866a00fb7666d83070cdc039ce6afa4a7bdf819f463'
6
+ metadata.gz: 47a29cd586c5b1eb0a2077bf7c0ea8b71c16b9d501a3347646faf6009a569e46960441e41808ddecb93eb5ee40aba4d9c44284033f80bb561b3f7f0f71557cbf
7
+ data.tar.gz: d0c7f59e15bf18dac4f571a795136bd14f5c36b665c2fe5bf6101385ea44d32340acc491dcc95920321cc082a45dbcfbfa559fc5d0f61c7890269128b7f6310c
@@ -41,10 +41,12 @@ module Decidim
41
41
  end
42
42
 
43
43
  def children_count_status
44
+ # rubocop: disable Style/StringConcatenation
44
45
  content_tag(
45
46
  :strong,
46
47
  t("layouts.decidim.assemblies.index.children")
47
48
  ) + " " + children_assemblies_visible_for_user
49
+ # rubocop: enable Style/StringConcatenation
48
50
  end
49
51
 
50
52
  def children_assemblies_visible_for_user
@@ -0,0 +1,9 @@
1
+ <div class="space-stats__data">
2
+ <span class="space-stats__number">
3
+ <%= stat_number %>
4
+ </span>
5
+
6
+ <h4 class="space-stats__title">
7
+ <%= stat_title %>
8
+ </h4>
9
+ </div>
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Assemblies
5
+ # This cell renders a Statistic of a Assemblies
6
+ class StatisticCell < Decidim::ViewModel
7
+ include ActionView::Helpers::NumberHelper
8
+
9
+ private
10
+
11
+ def stat_number
12
+ number_with_delimiter(model[:stat_number])
13
+ end
14
+
15
+ def stat_title
16
+ t(model[:stat_title], scope: "decidim.assemblies.statistics")
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,17 @@
1
+ <section class="row statistics" id="participatory_process-statistics">
2
+ <div class="columns large-8">
3
+ <div class="row column">
4
+ <h3 class="section-heading">
5
+ <%= stats_heading %>
6
+ </h3>
7
+
8
+ <div class="space-stats">
9
+ <% if model.present? %>
10
+ <%= cell("decidim/assemblies/statistic", collection: model) %>
11
+ <% else %>
12
+ <span class="muted"><%= no_stats %></span>
13
+ <% end %>
14
+ </div>
15
+ </div>
16
+ </div>
17
+ </section>
@@ -0,0 +1,18 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Assemblies
5
+ # This cell renders the Statistics of an Assembly
6
+ class StatisticsCell < Decidim::ViewModel
7
+ private
8
+
9
+ def stats_heading
10
+ t("statistics.headline", scope: "decidim.assemblies")
11
+ end
12
+
13
+ def no_stats
14
+ t("statistics.no_stats", scope: "decidim.assemblies")
15
+ end
16
+ end
17
+ end
18
+ end
@@ -45,6 +45,7 @@ module Decidim
45
45
  organization: form.current_organization,
46
46
  title: form.title,
47
47
  subtitle: form.subtitle,
48
+ weight: form.weight,
48
49
  slug: form.slug,
49
50
  hashtag: form.hashtag,
50
51
  description: form.description,
@@ -6,6 +6,8 @@ module Decidim
6
6
  # A command with all the business logic when creating a new participatory
7
7
  # process admin in the system.
8
8
  class CreateAssemblyAdmin < NotifyRoleAssignedToAssembly
9
+ include ::Decidim::Admin::CreateParticipatorySpaceAdminUserActions
10
+
9
11
  # Public: Initializes the command.
10
12
  #
11
13
  # form - A form object with the params.
@@ -14,34 +16,21 @@ module Decidim
14
16
  def initialize(form, current_user, assembly)
15
17
  @form = form
16
18
  @current_user = current_user
17
- @assembly = assembly
19
+ @participatory_space = assembly
18
20
  end
19
21
 
20
- # Executes the command. Broadcasts these events:
21
- #
22
- # - :ok when everything is valid.
23
- # - :invalid if the form wasn't valid and we couldn't proceed.
24
- #
25
- # Returns nothing.
26
- def call
27
- return broadcast(:invalid) if form.invalid?
22
+ private
28
23
 
29
- ActiveRecord::Base.transaction do
30
- @user = @user ||= existing_user || new_user
31
- create_role
32
- add_admin_as_follower
33
- end
24
+ attr_reader :form, :participatory_space, :current_user, :user
34
25
 
35
- broadcast(:ok)
36
- rescue ActiveRecord::RecordInvalid
37
- form.errors.add(:email, :taken)
38
- broadcast(:invalid)
26
+ def existing_role
27
+ Decidim::AssemblyUserRole.exists?(
28
+ role: form.role.to_sym,
29
+ user: user,
30
+ assembly: @participatory_process
31
+ )
39
32
  end
40
33
 
41
- private
42
-
43
- attr_reader :form, :assembly, :current_user, :user
44
-
45
34
  def create_role
46
35
  Decidim.traceability.perform_action!(
47
36
  :create,
@@ -54,60 +43,11 @@ module Decidim
54
43
  Decidim::AssemblyUserRole.find_or_create_by!(
55
44
  role: form.role.to_sym,
56
45
  user: user,
57
- assembly: @assembly
46
+ assembly: participatory_space
58
47
  )
59
48
  end
60
49
  send_notification user
61
50
  end
62
-
63
- def existing_user
64
- return @existing_user if defined?(@existing_user)
65
-
66
- @existing_user = User.find_by(
67
- email: form.email,
68
- organization: assembly.organization
69
- )
70
-
71
- InviteUserAgain.call(@existing_user, invitation_instructions) if @existing_user && !@existing_user.invitation_accepted?
72
-
73
- @existing_user
74
- end
75
-
76
- def new_user
77
- @new_user ||= InviteUser.call(user_form) do
78
- on(:ok) do |user|
79
- return user
80
- end
81
- end
82
- end
83
-
84
- def user_form
85
- OpenStruct.new(name: form.name,
86
- email: form.email.downcase,
87
- organization: assembly.organization,
88
- admin: false,
89
- invited_by: current_user,
90
- invitation_instructions: invitation_instructions)
91
- end
92
-
93
- def invitation_instructions
94
- return "invite_admin" if form.role == "admin"
95
-
96
- "invite_collaborator"
97
- end
98
-
99
- def add_admin_as_follower
100
- return if user.follows?(assembly)
101
-
102
- form = Decidim::FollowForm
103
- .from_params(followable_gid: assembly.to_signed_global_id.to_s)
104
- .with_context(
105
- current_organization: assembly.organization,
106
- current_user: user
107
- )
108
-
109
- Decidim::CreateFollow.new(form, user).call
110
- end
111
51
  end
112
52
  end
113
53
  end
@@ -94,7 +94,8 @@ module Decidim
94
94
  facebook_handler: form.facebook_handler,
95
95
  instagram_handler: form.instagram_handler,
96
96
  youtube_handler: form.youtube_handler,
97
- github_handler: form.github_handler
97
+ github_handler: form.github_handler,
98
+ weight: form.weight
98
99
  }.merge(uploader_attributes)
99
100
  end
100
101
 
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Assemblies
5
+ module Admin
6
+ # This controller allows importing things.
7
+ # It is targeted for customizations for importing things that lives under
8
+ # an assembly.
9
+ class ImportsController < Decidim::Admin::ImportsController
10
+ include Concerns::AssemblyAdmin
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Assemblies
5
+ module Admin
6
+ module Moderations
7
+ # This controller allows admins to manage moderation reports in an assembly.
8
+ class ReportsController < Decidim::Admin::Moderations::ReportsController
9
+ include Concerns::AssemblyAdmin
10
+ end
11
+ end
12
+ end
13
+ end
14
+ end
@@ -77,7 +77,7 @@ module Decidim
77
77
  end
78
78
 
79
79
  def parent_assemblies
80
- search.results.parent_assemblies.order(promoted: :desc)
80
+ search.results.parent_assemblies.order(weight: :asc, promoted: :desc)
81
81
  end
82
82
 
83
83
  def stats
@@ -10,7 +10,7 @@ module Decidim
10
10
  end
11
11
 
12
12
  def i18n_role
13
- I18n.t(extra["role"], "decidim.admin.models.assembly_user_role.roles", default: extra["role"])
13
+ I18n.t(extra["role"], scope: "decidim.admin.models.assembly_user_role.roles", default: extra["role"])
14
14
  end
15
15
 
16
16
  def i18n_options
@@ -45,6 +45,7 @@ module Decidim
45
45
  attribute :parent_id, Integer
46
46
  attribute :participatory_processes_ids, Array[Integer]
47
47
  attribute :scope_id, Integer
48
+ attribute :weight, Integer, default: 0
48
49
 
49
50
  attribute :is_transparent, Boolean
50
51
  attribute :promoted, Boolean
@@ -79,6 +80,8 @@ module Decidim
79
80
  validates :banner_image, passthru: { to: Decidim::Assembly }
80
81
  validates :hero_image, passthru: { to: Decidim::Assembly }
81
82
 
83
+ validates :weight, presence: true
84
+
82
85
  alias organization current_organization
83
86
 
84
87
  def ensure_parent_cannot_be_child
@@ -16,7 +16,6 @@ module Decidim
16
16
  validates :role, inclusion: { in: Decidim::AssemblyUserRole::ROLES }
17
17
 
18
18
  validates :name, format: { with: UserBaseEntity::REGEXP_NAME }
19
- validate :admin_uniqueness
20
19
 
21
20
  def roles
22
21
  Decidim::AssemblyUserRole::ROLES.map do |role|
@@ -26,10 +25,6 @@ module Decidim
26
25
  ]
27
26
  end
28
27
  end
29
-
30
- def admin_uniqueness
31
- errors.add(:email, :taken) if context && context.current_organization && context.current_organization.admins.where(email: email).exists?
32
- end
33
28
  end
34
29
  end
35
30
  end
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Assemblies
5
+ module Admin
6
+ module AssembliesAdminMenuHelper
7
+ include Decidim::Admin::SidebarMenuHelper
8
+
9
+ def admin_assemblies_menu
10
+ @admin_assemblies_menu ||= sidebar_menu(:admin_assemblies_menu)
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -67,7 +67,7 @@ module Decidim
67
67
  has_many :components, as: :participatory_space, dependent: :destroy
68
68
 
69
69
  has_many :children, foreign_key: "parent_id", class_name: "Decidim::Assembly", inverse_of: :parent, dependent: :destroy
70
- belongs_to :parent, foreign_key: "parent_id", class_name: "Decidim::Assembly", inverse_of: :children, optional: true, counter_cache: :children_count
70
+ belongs_to :parent, class_name: "Decidim::Assembly", inverse_of: :children, optional: true, counter_cache: :children_count
71
71
 
72
72
  validates_upload :hero_image
73
73
  mount_uploader :hero_image, Decidim::HeroImageUploader
@@ -215,9 +215,9 @@ module Decidim
215
215
  # rubocop:disable Rails/SkipsModelValidations
216
216
  def update_children_paths
217
217
  self.class.where(
218
- ["#{self.class.table_name}.parents_path <@ :old_path AND #{self.class.table_name}.id != :id", old_path: parents_path_before_last_save, id: id]
218
+ ["#{self.class.table_name}.parents_path <@ :old_path AND #{self.class.table_name}.id != :id", { old_path: parents_path_before_last_save, id: id }]
219
219
  ).update_all(
220
- ["parents_path = :new_path || subpath(parents_path, nlevel(:old_path))", new_path: parents_path, old_path: parents_path_before_last_save]
220
+ ["parents_path = :new_path || subpath(parents_path, nlevel(:old_path))", { new_path: parents_path, old_path: parents_path_before_last_save }]
221
221
  )
222
222
  end
223
223
  # rubocop:enable Rails/SkipsModelValidations
@@ -34,8 +34,8 @@ module Decidim
34
34
  end
35
35
  end
36
36
 
37
- def has_diff?
38
- action == "delete" || super
37
+ def diff_actions
38
+ super + %w(delete)
39
39
  end
40
40
  end
41
41
  end
@@ -43,8 +43,8 @@ module Decidim
43
43
  end
44
44
  end
45
45
 
46
- def has_diff?
47
- action == "delete" || super
46
+ def diff_actions
47
+ super + %w(delete)
48
48
  end
49
49
  end
50
50
  end
@@ -70,8 +70,8 @@ module Decidim
70
70
  end
71
71
  end
72
72
 
73
- def has_diff?
74
- action == "unpublish" || super
73
+ def diff_actions
74
+ super + %w(unpublish)
75
75
  end
76
76
  end
77
77
  end
@@ -44,8 +44,8 @@ module Decidim
44
44
  ).changeset
45
45
  end
46
46
 
47
- def has_diff?
48
- action == "delete" || super
47
+ def diff_actions
48
+ super + %w(delete)
49
49
  end
50
50
  end
51
51
  end
@@ -2,46 +2,56 @@
2
2
 
3
3
  module Decidim
4
4
  module Assemblies
5
- # A presenter to render statistics in the homepage.
5
+ # A presenter to render statistics in an Assembly.
6
6
  class AssemblyStatsPresenter < Rectify::Presenter
7
7
  attribute :assembly, Decidim::Assembly
8
- include IconHelper
8
+ include Decidim::IconHelper
9
9
 
10
- # Public: Render a collection of primary stats.
11
- def highlighted
12
- highlighted_stats = component_stats(priority: StatsRegistry::HIGH_PRIORITY)
13
- highlighted_stats = highlighted_stats.concat(component_stats(priority: StatsRegistry::MEDIUM_PRIORITY))
10
+ # Public: returns a collection of stats (Hash) for the Assembly Home.
11
+ def collection
12
+ highlighted_stats = assembly_participants_stats
13
+ highlighted_stats.concat(assembly_followers_stats(priority: StatsRegistry::HIGH_PRIORITY))
14
+ highlighted_stats.concat(component_stats(priority: StatsRegistry::HIGH_PRIORITY))
15
+ highlighted_stats.concat(component_stats(priority: StatsRegistry::MEDIUM_PRIORITY))
14
16
  highlighted_stats = highlighted_stats.reject(&:empty?)
15
- highlighted_stats = highlighted_stats.reject { |_manifest, _name, data| data.zero? }
16
- grouped_highlighted_stats = highlighted_stats.group_by { |stats| stats.first.name }
17
-
18
- safe_join(
19
- grouped_highlighted_stats.map do |_manifest_name, stats|
20
- content_tag :div, class: "process_stats-item" do
21
- safe_join(
22
- stats.each_with_index.map do |stat, index|
23
- render_stats_data(stat[0], stat[1], stat[2], index)
24
- end
25
- )
17
+ highlighted_stats = highlighted_stats.reject { |_stat_manifest, _stat_title, stat_number| stat_number.zero? }
18
+ grouped_highlighted_stats = highlighted_stats.group_by(&:first)
19
+
20
+ statistics = []
21
+ grouped_highlighted_stats.each do |_manifest_name, stats|
22
+ stats.each_with_index.each do |stat, _index|
23
+ stat.each_with_index.map do |_item, subindex|
24
+ next unless (subindex % 3).zero?
25
+ next if stat[subindex + 2].zero?
26
+
27
+ statistics << { stat_title: stat[subindex + 1], stat_number: stat[subindex + 2] }
26
28
  end
27
29
  end
28
- )
30
+ end
31
+ statistics
29
32
  end
30
33
 
31
34
  private
32
35
 
36
+ def assembly_participants_stats
37
+ Decidim.stats.only([:participants_count]).with_context(assembly)
38
+ .map { |stat_title, stat_number| [assembly.manifest.name, stat_title, stat_number] }
39
+ end
40
+
33
41
  def component_stats(conditions)
34
42
  Decidim.component_manifests.map do |component_manifest|
35
- component_manifest.stats.filter(conditions).with_context(published_components).map { |name, data| [component_manifest, name, data] }.flatten
43
+ component_manifest.stats.except([:proposals_accepted])
44
+ .filter(conditions)
45
+ .with_context(published_components)
46
+ .map { |stat_title, stat_number| [component_manifest.name, stat_title, stat_number] }.flatten
36
47
  end
37
48
  end
38
49
 
39
- def render_stats_data(component_manifest, name, data, index)
40
- safe_join([
41
- index.zero? ? manifest_icon(component_manifest, role: "img", "aria-hidden": true) : " /&nbsp".html_safe,
42
- content_tag(:span, "#{number_with_delimiter(data)} " + I18n.t(name, scope: "decidim.assemblies.statistics"),
43
- class: "#{name} process_stats-text")
44
- ])
50
+ def assembly_followers_stats(conditions)
51
+ Decidim.stats.only([:followers_count])
52
+ .filter(conditions)
53
+ .with_context(assembly)
54
+ .map { |stat_title, stat_number| [assembly.manifest.name, stat_title, stat_number] }
45
55
  end
46
56
 
47
57
  def published_components