decidim-assemblies 0.31.3 → 0.32.0.rc1

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 (122) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +4 -12
  3. data/app/cells/decidim/assemblies/content_blocks/main_data_cell.rb +1 -0
  4. data/app/commands/decidim/assemblies/admin/create_assembly.rb +4 -4
  5. data/app/commands/decidim/assemblies/admin/duplicate_assembly.rb +1 -2
  6. data/app/commands/decidim/assemblies/admin/update_assembly.rb +3 -3
  7. data/app/controllers/concerns/decidim/assemblies/admin/filterable.rb +6 -2
  8. data/app/controllers/concerns/decidim/assemblies/assembly_breadcrumb.rb +0 -3
  9. data/app/controllers/decidim/assemblies/admin/assemblies_controller.rb +2 -2
  10. data/app/controllers/decidim/assemblies/admin/assembly_duplicates_controller.rb +1 -1
  11. data/app/controllers/decidim/assemblies/admin/assembly_imports_controller.rb +1 -1
  12. data/app/controllers/decidim/assemblies/admin/concerns/assembly_admin.rb +1 -0
  13. data/app/controllers/decidim/assemblies/admin/members_controller.rb +14 -0
  14. data/app/controllers/decidim/assemblies/admin/members_csv_imports_controller.rb +22 -0
  15. data/app/controllers/decidim/assemblies/{participatory_space_private_users_controller.rb → members_controller.rb} +2 -2
  16. data/app/forms/decidim/assemblies/admin/assembly_form.rb +9 -6
  17. data/app/helpers/decidim/assemblies/assemblies_helper.rb +2 -2
  18. data/app/helpers/decidim/assemblies/filter_assemblies_helper.rb +2 -1
  19. data/app/models/decidim/assembly.rb +12 -15
  20. data/app/packs/src/decidim/assemblies/controllers/assembly_admin/assembly_admin.test.js +1 -130
  21. data/app/packs/src/decidim/assemblies/controllers/assembly_admin/controller.js +0 -28
  22. data/app/permissions/decidim/assemblies/permissions.rb +9 -9
  23. data/app/presenters/decidim/assemblies/admin_log/assembly_presenter.rb +1 -2
  24. data/app/presenters/decidim/assemblies/assembly_presenter.rb +0 -4
  25. data/app/queries/decidim/assemblies/admin/admin_users.rb +1 -1
  26. data/app/serializers/decidim/assemblies/assembly_importer.rb +10 -13
  27. data/app/serializers/decidim/assemblies/assembly_serializer.rb +1 -1
  28. data/app/serializers/decidim/assemblies/open_data_assembly_serializer.rb +2 -8
  29. data/app/views/decidim/assemblies/admin/assemblies/_assemblies_thead.html.erb +1 -1
  30. data/app/views/decidim/assemblies/admin/assemblies/_assembly_row.html.erb +5 -6
  31. data/app/views/decidim/assemblies/admin/assemblies/_form.html.erb +33 -17
  32. data/app/views/decidim/assemblies/admin/assemblies/edit.html.erb +3 -2
  33. data/app/views/decidim/assemblies/admin/assemblies/index.html.erb +2 -1
  34. data/app/views/decidim/assemblies/admin/assemblies/manage_trash.html.erb +2 -2
  35. data/app/views/decidim/assemblies/admin/assemblies/new.html.erb +2 -2
  36. data/app/views/decidim/assemblies/admin/assembly_duplicates/new.html.erb +2 -2
  37. data/app/views/decidim/assemblies/admin/assembly_imports/new.html.erb +2 -2
  38. data/app/views/decidim/assemblies/admin/assembly_user_roles/edit.html.erb +2 -2
  39. data/app/views/decidim/assemblies/admin/assembly_user_roles/index.html.erb +2 -2
  40. data/app/views/decidim/assemblies/admin/assembly_user_roles/new.html.erb +2 -2
  41. data/app/views/decidim/assemblies/assemblies/_collection.html.erb +1 -1
  42. data/app/views/decidim/assemblies/assemblies/show.html.erb +9 -3
  43. data/app/views/decidim/assemblies/members/index.html.erb +24 -0
  44. data/config/locales/ar.yml +0 -26
  45. data/config/locales/bg.yml +0 -26
  46. data/config/locales/bs-BA.yml +0 -8
  47. data/config/locales/ca-IT.yml +36 -35
  48. data/config/locales/ca.yml +36 -35
  49. data/config/locales/cs.yml +36 -35
  50. data/config/locales/de.yml +27 -28
  51. data/config/locales/el.yml +0 -26
  52. data/config/locales/en.yml +36 -34
  53. data/config/locales/es-MX.yml +36 -35
  54. data/config/locales/es-PY.yml +36 -35
  55. data/config/locales/es.yml +36 -35
  56. data/config/locales/eu.yml +36 -35
  57. data/config/locales/fi-plain.yml +36 -29
  58. data/config/locales/fi.yml +36 -29
  59. data/config/locales/fr-CA.yml +34 -35
  60. data/config/locales/fr.yml +34 -35
  61. data/config/locales/ga-IE.yml +0 -12
  62. data/config/locales/gl.yml +0 -24
  63. data/config/locales/he-IL.yml +0 -11
  64. data/config/locales/hu.yml +0 -26
  65. data/config/locales/id-ID.yml +0 -22
  66. data/config/locales/is-IS.yml +1 -10
  67. data/config/locales/it.yml +0 -28
  68. data/config/locales/ja.yml +23 -35
  69. data/config/locales/kaa.yml +0 -1
  70. data/config/locales/ko.yml +0 -9
  71. data/config/locales/lb.yml +0 -24
  72. data/config/locales/lt.yml +0 -25
  73. data/config/locales/lv.yml +0 -25
  74. data/config/locales/nl.yml +0 -26
  75. data/config/locales/no.yml +0 -26
  76. data/config/locales/pl.yml +0 -26
  77. data/config/locales/pt-BR.yml +4 -28
  78. data/config/locales/pt.yml +0 -28
  79. data/config/locales/ro-RO.yml +2 -25
  80. data/config/locales/ru.yml +0 -15
  81. data/config/locales/sk.yml +0 -10
  82. data/config/locales/sl.yml +0 -11
  83. data/config/locales/sq-AL.yml +0 -17
  84. data/config/locales/sr-CS.yml +0 -8
  85. data/config/locales/sv.yml +16 -29
  86. data/config/locales/tr-TR.yml +0 -26
  87. data/config/locales/uk.yml +0 -15
  88. data/config/locales/zh-CN.yml +0 -25
  89. data/config/locales/zh-TW.yml +0 -26
  90. data/db/data/20260104094930_remove_assemblies_types_references.rb +25 -0
  91. data/db/data/20260111185230_replace_legacy_fields_to_access_mode_for_assemblies.rb +25 -0
  92. data/db/data/20260210195653_move_announcement_to_content_block_on_assemblies.rb +40 -0
  93. data/db/migrate/20180226103942_add_parent_child_relation_to_assemblies.rb +4 -4
  94. data/db/migrate/20190215093700_reset_negative_children_count_counters.rb +6 -2
  95. data/db/migrate/20210310120444_add_followable_counter_cache_to_assemblies.rb +6 -2
  96. data/db/migrate/20251112114736_remove_legacy_images_from_assemblies_module.rb +8 -0
  97. data/db/migrate/20251205120000_add_has_members_to_decidim_assemblies.rb +7 -0
  98. data/db/migrate/20260104093601_remove_assemblies_types.rb +12 -0
  99. data/db/migrate/20260111120000_add_access_mode_to_assemblies.rb +11 -0
  100. data/decidim-assemblies.gemspec +8 -9
  101. data/lib/decidim/api/assembly_type.rb +1 -8
  102. data/lib/decidim/assemblies/admin_engine.rb +10 -4
  103. data/lib/decidim/assemblies/content_blocks/registry_manager.rb +5 -0
  104. data/lib/decidim/assemblies/engine.rb +26 -42
  105. data/lib/decidim/assemblies/menu.rb +5 -5
  106. data/lib/decidim/assemblies/participatory_space.rb +0 -2
  107. data/lib/decidim/assemblies/seeds.rb +1 -2
  108. data/lib/decidim/assemblies/test/factories.rb +8 -20
  109. data/lib/decidim/assemblies/version.rb +1 -1
  110. metadata +25 -30
  111. data/app/cells/decidim/assemblies/assembly_dropdown_metadata_cell.rb +0 -19
  112. data/app/commands/decidim/assemblies/admin/create_assemblies_type.rb +0 -17
  113. data/app/commands/decidim/assemblies/admin/update_assemblies_type.rb +0 -13
  114. data/app/controllers/decidim/assemblies/admin/participatory_space_private_users_controller.rb +0 -22
  115. data/app/controllers/decidim/assemblies/admin/participatory_space_private_users_csv_imports_controller.rb +0 -22
  116. data/app/forms/decidim/assemblies/admin/assemblies_type_form.rb +0 -17
  117. data/app/models/decidim/assemblies_type.rb +0 -27
  118. data/app/presenters/decidim/assemblies/admin_log/assemblies_type_presenter.rb +0 -43
  119. data/app/presenters/decidim/log/value_types/assembly_type_presenter.rb +0 -29
  120. data/app/queries/decidim/assemblies/filtered_assemblies.rb +0 -22
  121. data/app/views/decidim/assemblies/pages/user_profile/_member_of.html.erb +0 -9
  122. data/app/views/decidim/assemblies/participatory_space_private_users/index.html.erb +0 -23
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b390ecc1992cc0c80979a2dd3009efae463a452f3c051190409abb098ed060a9
4
- data.tar.gz: 2f68bbb23efa90ea3bd940c7d8f28d4468703e699c406ddcb32eb2c3d64896ae
3
+ metadata.gz: e281f489f7f47da21acec28d2771d799f6a46de0d0ca7fb34d1a6e4f9baa8a32
4
+ data.tar.gz: 3b173a11dc651d6dececd6c9c05022365e85f91e406abd0ba1b06d4e0c5e079e
5
5
  SHA512:
6
- metadata.gz: ab090584ef6a4dc05849df9c88daff436857b44241f712bc319fcc7e8a4eb77f7c3003f1524fe9495a8a9607bdcdf6a1fdaf3f82c80da9d51d516527ca1a553c
7
- data.tar.gz: 7836b2a30013e7e032f8271d6c3935b43732c65aecbca6e3ff8f01f7dd3376769c4feac7620389bbed10e44ac99109da03ab479bb0c3afd283d968fa2aa897a2
6
+ metadata.gz: 1a2e340210186d6225909ff074fae66f02b153cc63808ff8d14ae2d723be1d1a3acf02e95962869e2f2f1250d83cb608b3953801170e6fc60e3d60255f919328
7
+ data.tar.gz: 4f334da82cd6ce0ddb35b3a7a51c6bf2efb00a3b301f8e413db1a5d6d308861f04cef4f2da55870fb39536960c765e157b3bf04484d4d1bead3188790e26dc5b
data/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # Decidim::Assemblies
1
+ # decidim-assemblies
2
2
 
3
3
  Assemblies are the permanent Decidim's participatory space. They are always
4
4
  "active" so unlike participatory processes, they have no steps or phases.
@@ -15,19 +15,11 @@ This module provides:
15
15
 
16
16
  * Public views for assembly via a high level section in the main menu.
17
17
 
18
- ## Installation
19
-
20
- Add this line to your application's Gemfile:
18
+ You can see the documentation of this feature at the [Decidim Documentation](https://docs.decidim.org/en/develop/admin/spaces/assemblies).
21
19
 
22
- ```ruby
23
- gem 'decidim-assemblies'
24
- ```
25
-
26
- And then execute:
20
+ ## Installation
27
21
 
28
- ```bash
29
- bundle
30
- ```
22
+ This is on the default Decidim installation so you should not change anything to use this participatory space.
31
23
 
32
24
  ## Contributing
33
25
 
@@ -7,6 +7,7 @@ module Decidim
7
7
  include AssembliesHelper
8
8
  include Decidim::ComponentPathHelper
9
9
  include ActiveLinkTo
10
+ include Decidim::ActiveLinkToHelper
10
11
 
11
12
  EXTRA_ATTRIBUTES = %w(purpose_of_action internal_organisation composition).freeze
12
13
 
@@ -6,15 +6,15 @@ module Decidim
6
6
  # A command with all the business logic when creating a new assembly
7
7
  # in the system.
8
8
  class CreateAssembly < Decidim::Commands::CreateResource
9
- fetch_file_attributes :hero_image, :banner_image
9
+ fetch_file_attributes :hero_image
10
10
 
11
11
  fetch_form_attributes :title, :subtitle, :weight, :slug, :description, :short_description,
12
- :promoted, :taxonomizations, :parent, :announcement, :organization,
13
- :private_space, :developer_group, :local_area, :target, :participatory_scope,
12
+ :promoted, :taxonomizations, :parent, :organization,
13
+ :access_mode, :developer_group, :local_area, :target, :participatory_scope,
14
14
  :participatory_structure, :meta_scope, :purpose_of_action,
15
15
  :composition, :creation_date, :created_by, :created_by_other,
16
16
  :duration, :included_at, :closing_date, :closing_date_reason, :internal_organisation,
17
- :is_transparent, :special_features, :twitter_handler, :facebook_handler,
17
+ :has_members, :special_features, :twitter_handler, :facebook_handler,
18
18
  :instagram_handler, :youtube_handler, :github_handler
19
19
 
20
20
  protected
@@ -58,13 +58,12 @@ module Decidim
58
58
  participatory_scope: @assembly.participatory_scope,
59
59
  participatory_structure: @assembly.participatory_structure,
60
60
  meta_scope: @assembly.meta_scope,
61
- announcement: @assembly.announcement,
62
61
  taxonomies: @assembly.taxonomies
63
62
  )
64
63
  end
65
64
 
66
65
  def duplicate_assembly_attachments
67
- [:hero_image, :banner_image].each do |attribute|
66
+ [:hero_image].each do |attribute|
68
67
  next unless @assembly.attached_uploader(attribute).attached?
69
68
 
70
69
  @duplicated_assembly.send(attribute).attach(@assembly.send(attribute).blob)
@@ -6,14 +6,14 @@ module Decidim
6
6
  # A command with all the business logic when updating a new assembly
7
7
  # in the system.
8
8
  class UpdateAssembly < Decidim::Commands::UpdateResource
9
- fetch_file_attributes :hero_image, :banner_image
9
+ fetch_file_attributes :hero_image
10
10
 
11
11
  fetch_form_attributes :title, :subtitle, :slug, :promoted, :description, :short_description,
12
- :taxonomizations, :parent, :private_space, :developer_group, :local_area,
12
+ :taxonomizations, :parent, :access_mode, :developer_group, :local_area,
13
13
  :target, :participatory_scope, :participatory_structure, :meta_scope,
14
14
  :purpose_of_action, :composition, :creation_date, :created_by,
15
15
  :created_by_other, :duration, :included_at, :closing_date, :closing_date_reason,
16
- :internal_organisation, :is_transparent, :special_features, :twitter_handler, :announcement,
16
+ :internal_organisation, :has_members, :special_features, :twitter_handler,
17
17
  :facebook_handler, :instagram_handler, :youtube_handler, :github_handler, :weight
18
18
 
19
19
  private
@@ -25,15 +25,19 @@ module Decidim
25
25
  end
26
26
 
27
27
  def filters
28
- [:private_space_eq, :published_at_null]
28
+ [:with_any_access_mode, :published_at_null]
29
29
  end
30
30
 
31
31
  def filters_with_values
32
32
  {
33
- private_space_eq: [true, false],
33
+ with_any_access_mode: access_modes,
34
34
  published_at_null: [true, false]
35
35
  }
36
36
  end
37
+
38
+ def access_modes
39
+ Assembly::ACCESS_MODES.keys
40
+ end
37
41
  end
38
42
  end
39
43
  end
@@ -12,14 +12,11 @@ module Decidim
12
12
  return {} if current_participatory_space.blank?
13
13
  return super unless current_participatory_space.is_a?(Decidim::Assembly)
14
14
 
15
- dropdown_cell = current_participatory_space_manifest.breadcrumb_cell
16
-
17
15
  items = current_participatory_space.ancestors.map do |participatory_space|
18
16
  {
19
17
  label: participatory_space.title,
20
18
  url: Decidim::ResourceLocatorPresenter.new(participatory_space).path,
21
19
  active: false,
22
- dropdown_cell:,
23
20
  resource: participatory_space
24
21
  }
25
22
  end
@@ -37,7 +37,7 @@ module Decidim
37
37
 
38
38
  on(:invalid) do
39
39
  flash.now[:alert] = I18n.t("assemblies.create.error", scope: "decidim.admin")
40
- render :new, status: :unprocessable_entity
40
+ render :new, status: :unprocessable_content
41
41
  end
42
42
  end
43
43
  end
@@ -63,7 +63,7 @@ module Decidim
63
63
 
64
64
  on(:invalid) do
65
65
  flash.now[:alert] = I18n.t("assemblies.update.error", scope: "decidim.admin")
66
- render :edit, layout: "decidim/admin/assembly", status: :unprocessable_entity
66
+ render :edit, layout: "decidim/admin/assembly", status: :unprocessable_content
67
67
  end
68
68
  end
69
69
  end
@@ -25,7 +25,7 @@ module Decidim
25
25
 
26
26
  on(:invalid) do
27
27
  flash.now[:alert] = I18n.t("assemblies_duplicates.create.error", scope: "decidim.admin")
28
- render :new, status: :unprocessable_entity
28
+ render :new, status: :unprocessable_content
29
29
  end
30
30
  end
31
31
  end
@@ -24,7 +24,7 @@ module Decidim
24
24
 
25
25
  on(:invalid) do
26
26
  flash.now[:alert] = I18n.t("assembly_imports.create.error", scope: "decidim.admin")
27
- render :new, status: :unprocessable_entity
27
+ render :new, status: :unprocessable_content
28
28
  end
29
29
  end
30
30
  end
@@ -19,6 +19,7 @@ module Decidim
19
19
 
20
20
  included do
21
21
  include Decidim::Admin::ParticipatorySpaceAdminContext
22
+
22
23
  helper_method :current_assembly
23
24
  add_breadcrumb_item_from_menu :admin_assembly_menu
24
25
 
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Assemblies
5
+ module Admin
6
+ # Controller that allows managing assembly members
7
+ # on assemblies
8
+ class MembersController < Decidim::Assemblies::Admin::ApplicationController
9
+ include Concerns::AssemblyAdmin
10
+ include Decidim::Admin::ParticipatorySpace::Concerns::HasMembers
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Assemblies
5
+ module Admin
6
+ # Controller that allows importing assembly members
7
+ # on assemblies
8
+ class MembersCsvImportsController < Decidim::Admin::ApplicationController
9
+ include Concerns::AssemblyAdmin
10
+ include Decidim::Admin::ParticipatorySpace::Concerns::HasMembersCsvImport
11
+
12
+ def after_import_path
13
+ members_path(current_assembly)
14
+ end
15
+
16
+ def participatory_space
17
+ current_assembly
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end
@@ -2,9 +2,9 @@
2
2
 
3
3
  module Decidim
4
4
  module Assemblies
5
- class ParticipatorySpacePrivateUsersController < Decidim::Assemblies::ApplicationController
5
+ class MembersController < Decidim::Assemblies::ApplicationController
6
6
  include ParticipatorySpaceContext
7
- include Decidim::HasMembersPage
7
+ include Decidim::ParticipatorySpace::HasMembersPage
8
8
 
9
9
  def index
10
10
  raise ActionController::RoutingError, "No members for this assembly" if members.none?
@@ -31,7 +31,6 @@ module Decidim
31
31
  translatable_attribute :subtitle, String
32
32
  translatable_attribute :target, String
33
33
  translatable_attribute :title, String
34
- translatable_attribute :announcement, Decidim::Attributes::RichText
35
34
 
36
35
  attribute :created_by, String
37
36
  attribute :facebook_handler, String
@@ -45,18 +44,16 @@ module Decidim
45
44
  attribute :participatory_processes_ids, Array[Integer]
46
45
  attribute :weight, Integer, default: 0
47
46
 
48
- attribute :is_transparent, Boolean
47
+ attribute :access_mode, String, default: :open
48
+ attribute :has_members, Boolean
49
49
  attribute :promoted, Boolean
50
- attribute :private_space, Boolean
51
50
 
52
51
  attribute :closing_date, Decidim::Attributes::LocalizedDate
53
52
  attribute :creation_date, Decidim::Attributes::LocalizedDate
54
53
  attribute :duration, Decidim::Attributes::LocalizedDate
55
54
  attribute :included_at, Decidim::Attributes::LocalizedDate
56
55
 
57
- attribute :banner_image
58
56
  attribute :hero_image
59
- attribute :remove_banner_image, Boolean, default: false
60
57
  attribute :remove_hero_image, Boolean, default: false
61
58
 
62
59
  validates :parent, presence: true, if: ->(form) { form.parent.present? }
@@ -69,11 +66,13 @@ module Decidim
69
66
  validates :created_by_other, translatable_presence: true, if: ->(form) { form.created_by == "others" }
70
67
  validates :title, :subtitle, :description, :short_description, translatable_presence: true
71
68
 
72
- validates :banner_image, passthru: { to: Decidim::Assembly }
73
69
  validates :hero_image, passthru: { to: Decidim::Assembly }
74
70
 
75
71
  validates :weight, presence: true
76
72
 
73
+ validates :access_mode, presence: true, inclusion: { in: Decidim::Assembly.access_modes.keys }
74
+ validate :ensure_access_mode_for_has_members
75
+
77
76
  alias organization current_organization
78
77
 
79
78
  def participatory_space_manifest
@@ -125,6 +124,10 @@ module Decidim
125
124
 
126
125
  errors.add(:slug, :taken)
127
126
  end
127
+
128
+ def ensure_access_mode_for_has_members
129
+ self.access_mode = :open if has_members == false
130
+ end
128
131
  end
129
132
  end
130
133
  end
@@ -23,8 +23,8 @@ module Decidim
23
23
  *(if participatory_space.members_public_page?
24
24
  [{
25
25
  name: t("assembly_member_menu_item", scope: "layouts.decidim.assembly_navigation"),
26
- url: decidim_assemblies.assembly_participatory_space_private_users_path(participatory_space),
27
- active: is_active_link?(decidim_assemblies.assembly_participatory_space_private_users_path(participatory_space), :inclusive)
26
+ url: decidim_assemblies.assembly_members_path(participatory_space),
27
+ active: is_active_link?(decidim_assemblies.assembly_members_path(participatory_space), :inclusive)
28
28
  }]
29
29
  end
30
30
  )
@@ -10,7 +10,8 @@ module Decidim
10
10
  items = []
11
11
 
12
12
  available_taxonomy_filters.find_each do |taxonomy_filter|
13
- items.append(method: "with_any_taxonomies[#{taxonomy_filter.root_taxonomy_id}]",
13
+ items.append(method: :with_any_taxonomies,
14
+ name: "[with_any_taxonomies][#{taxonomy_filter.root_taxonomy_id}]",
14
15
  collection: filter_taxonomy_values_for(taxonomy_filter),
15
16
  label: decidim_sanitize_translated(taxonomy_filter.name),
16
17
  id: "taxonomy-#{taxonomy_filter.root_taxonomy_id}")
@@ -31,7 +31,7 @@ module Decidim
31
31
  include Decidim::Traceable
32
32
  include Decidim::Loggable
33
33
  include Decidim::ParticipatorySpaceResourceable
34
- include Decidim::HasPrivateUsers
34
+ include Decidim::ParticipatorySpace::HasMembers
35
35
  include Decidim::Searchable
36
36
  include Decidim::HasUploadValidations
37
37
  include Decidim::TranslatableResource
@@ -53,10 +53,6 @@ module Decidim
53
53
  foreign_key: "decidim_area_id",
54
54
  class_name: "Decidim::Area",
55
55
  optional: true
56
- belongs_to :assembly_type,
57
- foreign_key: "decidim_assemblies_type_id",
58
- class_name: "Decidim::AssembliesType",
59
- optional: true
60
56
  has_many :categories,
61
57
  foreign_key: "decidim_participatory_space_id",
62
58
  foreign_type: "decidim_participatory_space_type",
@@ -71,9 +67,6 @@ module Decidim
71
67
  has_one_attached :hero_image
72
68
  validates_upload :hero_image, uploader: Decidim::HeroImageUploader
73
69
 
74
- has_one_attached :banner_image
75
- validates_upload :banner_image, uploader: Decidim::BannerImageUploader
76
-
77
70
  validates :slug, uniqueness: { scope: :organization }
78
71
  validates :slug, presence: true, format: { with: Decidim::Assembly.slug_format }
79
72
 
@@ -92,10 +85,14 @@ module Decidim
92
85
  index_on_create: ->(_assembly) { false },
93
86
  index_on_update: ->(assembly) { assembly.visible? })
94
87
 
95
- # Overwriting existing method Decidim::HasPrivateUsers.public_spaces
96
- def self.public_spaces
97
- where(private_space: false).or(where(private_space: true).where(is_transparent: true)).published
98
- end
88
+ # Access modes are consistent across participatory spaces (assemblies and processes)
89
+ # open: visible and accessible for all
90
+ # transparent: visible for all but the actions require to be a member of the space
91
+ # restricted: visible and accessible only for members fo the space
92
+ ACCESS_MODES = { open: 0, transparent: 1, restricted: 2 }.freeze
93
+ enum :access_mode, ACCESS_MODES
94
+
95
+ scope_search_multi :with_any_access_mode, ACCESS_MODES.keys
99
96
 
100
97
  # Scope to return only the promoted assemblies.
101
98
  #
@@ -120,7 +117,7 @@ module Decidim
120
117
 
121
118
  # This is a overwrite for Decidim::ParticipatorySpaceResourceable.visible?
122
119
  def visible?
123
- published? && (!private_space? || (private_space? && is_transparent?))
120
+ published? && (open? || transparent?)
124
121
  end
125
122
 
126
123
  def to_param
@@ -157,7 +154,7 @@ module Decidim
157
154
  end
158
155
 
159
156
  def self.ransackable_scopes(_auth_object = nil)
160
- [:with_any_taxonomies]
157
+ [:with_any_taxonomies, :with_any_access_mode]
161
158
  end
162
159
 
163
160
  def shareable_url(share_token)
@@ -169,7 +166,7 @@ module Decidim
169
166
 
170
167
  return base unless auth_object&.admin?
171
168
 
172
- base + %w(published_at created_at private_space parent_id)
169
+ base + %w(published_at created_at parent_id access_mode)
173
170
  end
174
171
 
175
172
  def self.ransackable_associations(_auth_object = nil)
@@ -363,7 +363,6 @@ describe("AssemblyAdminController", () => {
363
363
  <div aria-disabled="false" aria-label="Choose date" class="wc-datepicker sc-wc-datepicker" role="group">
364
364
  </div>
365
365
  </wc-datepicker>
366
- <button class="datepicker__pick-calendar button button__secondary button__xs" disabled="true" type="button">Select</button>
367
366
  <button class="datepicker__close-calendar button button__transparent-secondary button__xs" type="button">Close</button>
368
367
  </div>
369
368
  </div>
@@ -388,7 +387,6 @@ describe("AssemblyAdminController", () => {
388
387
  <div class="datepicker__container" style="display: none;">
389
388
  <wc-datepicker id="assembly_included_at_date_datepicker" locale="en" class="sc-wc-datepicker-h sc-wc-datepicker-s hydrated">
390
389
  </wc-datepicker>
391
- <button class="datepicker__pick-calendar button button__secondary button__xs" disabled="true" type="button">Select</button>
392
390
  <button class="datepicker__close-calendar button button__transparent-secondary button__xs" type="button">Close</button>
393
391
  </div>
394
392
  </div>
@@ -411,7 +409,6 @@ describe("AssemblyAdminController", () => {
411
409
  </svg>
412
410
  </button>
413
411
  <div class="datepicker__container" style="display: none;">
414
- <button class="datepicker__pick-calendar button button__secondary button__xs" disabled="true" type="button">Select</button>
415
412
  <button class="datepicker__close-calendar button button__transparent-secondary button__xs" type="button">Close</button>
416
413
  </div>
417
414
  </div>
@@ -433,7 +430,6 @@ describe("AssemblyAdminController", () => {
433
430
  </svg>
434
431
  </button>
435
432
  <div class="datepicker__container" style="display: none;">
436
- <button class="datepicker__pick-calendar button button__secondary button__xs" disabled="true" type="button">Select</button>
437
433
  <button class="datepicker__close-calendar button button__transparent-secondary button__xs" type="button">Close</button>
438
434
  </div>
439
435
  </div>
@@ -494,15 +490,6 @@ describe("AssemblyAdminController", () => {
494
490
  <button id="assembly_hero_image_button" name="hero_image" class="button button__sm button__transparent-secondary" type="button" data-dialog-open="upload_c5515a82-b6d4-4c1c-a957-013c9679b956" data-upload="{&quot;addAttribute&quot;:&quot;hero_image&quot;,&quot;resourceName&quot;:&quot;assembly&quot;,&quot;resourceClass&quot;:&quot;Decidim::Assembly&quot;,&quot;required&quot;:false,&quot;maxFileSize&quot;:10485760.0,&quot;multiple&quot;:false,&quot;titled&quot;:false,&quot;formObjectClass&quot;:&quot;Decidim::Assemblies::Admin::AssemblyForm&quot;}" aria-haspopup="dialog">Add image</button>
495
491
  </div>
496
492
  </div>
497
- <div class="columns">
498
- <div class="upload-modal__files-container upload-container-for-banner_image ">
499
- <div>
500
- <label>Banner image</label>
501
- <div class="upload-modal__files" data-active-uploads="upload_0d6b6c3f-3681-450e-dummy-2"></div>
502
- </div>
503
- <button id="assembly_banner_image_button" name="banner_image" class="button button__sm button__transparent-secondary" type="button" data-dialog-open="upload_0d6b6c3f-3681-450e-dummy-2" data-upload="{&quot;addAttribute&quot;:&quot;banner_image&quot;,&quot;resourceName&quot;:&quot;assembly&quot;,&quot;resourceClass&quot;:&quot;Decidim::Assembly&quot;,&quot;required&quot;:false,&quot;maxFileSize&quot;:10485760.0,&quot;multiple&quot;:false,&quot;titled&quot;:false,&quot;formObjectClass&quot;:&quot;Decidim::Assemblies::Admin::AssemblyForm&quot;}" aria-haspopup="dialog">Add image</button>
504
- </div>
505
- </div>
506
493
  </div>
507
494
  </div>
508
495
  </div>
@@ -748,7 +735,7 @@ describe("AssemblyAdminController", () => {
748
735
  <label for="assembly_private_space">
749
736
  <input name="assembly[private_space]" type="hidden" value="0" autocomplete="off">
750
737
  <input type="checkbox" value="1" name="assembly[private_space]" id="assembly_private_space">Private space </label>
751
- <p class="help-text">You will be able to manage private participants after setting it as private</p>
738
+ <p class="help-text">You will be able to manage members after setting it as private</p>
752
739
  </div>
753
740
  <div class="row column" id="is_transparent">
754
741
  <label for="assembly_is_transparent">
@@ -870,28 +857,6 @@ describe("AssemblyAdminController", () => {
870
857
  it("should initialize the controller and set up event listeners", () => {
871
858
  expect(controller).toBeDefined();
872
859
  expect(element).toBeDefined();
873
-
874
- // Test that initial state is set correctly
875
- const isTransparentCheckbox = element.querySelector("#is_transparent input[type='checkbox']");
876
- const specialFeatures = element.querySelector("#special_features");
877
-
878
- expect(isTransparentCheckbox.disabled).toBe(true);
879
- expect(specialFeatures.style.display).toBe("none");
880
- });
881
-
882
- it("should call assignBehavior for assembly_type and created_by fields", () => {
883
- const assemblyType = element.querySelector("#assembly_assembly_type");
884
- const createdBy = element.querySelector("#assembly_created_by");
885
-
886
- expect(assemblyType).toBeDefined();
887
- expect(createdBy).toBeDefined();
888
-
889
- // Verify that event listeners are attached by triggering changes
890
- // const assemblyTypeOther = element.querySelector("#assembly_type_other");
891
- const createdByOther = element.querySelector("#created_by_other");
892
-
893
- // expect(assemblyTypeOther.style.display).toBe("none");
894
- expect(createdByOther.style.display).toBe("none");
895
860
  });
896
861
  });
897
862
 
@@ -931,16 +896,6 @@ describe("AssemblyAdminController", () => {
931
896
  // Should hide initially if value is not "others"
932
897
  expect(targetDiv.style.display).toBe("none");
933
898
  });
934
-
935
- it("should handle null elements gracefully", () => {
936
- expect(() => {
937
- controller.attachVisibility(null, null);
938
- }).not.toThrow();
939
-
940
- expect(() => {
941
- controller.attachVisibility(element.querySelector("#assembly_assembly_type"), null);
942
- }).not.toThrow();
943
- });
944
899
  });
945
900
 
946
901
  describe("toggleDependsOnSelect", () => {
@@ -963,79 +918,6 @@ describe("AssemblyAdminController", () => {
963
918
 
964
919
  expect(targetDiv.style.display).toBe("none");
965
920
  });
966
-
967
- it("should return early if target or showDiv is null", () => {
968
- const select = element.querySelector("#assembly_assembly_type");
969
-
970
- expect(() => {
971
- controller.toggleDependsOnSelect(null, null);
972
- }).not.toThrow();
973
-
974
- expect(() => {
975
- controller.toggleDependsOnSelect(select, null);
976
- }).not.toThrow();
977
- });
978
- });
979
-
980
- describe("toggleDisabledHiddenFields", () => {
981
- it("should initially disable transparent checkbox and hide special features", () => {
982
- controller.toggleDisabledHiddenFields();
983
-
984
- const isTransparentCheckbox = element.querySelector("#is_transparent input[type='checkbox']");
985
- const specialFeatures = element.querySelector("#special_features");
986
-
987
- expect(isTransparentCheckbox.disabled).toBe(true);
988
- expect(specialFeatures.style.display).toBe("none");
989
- });
990
-
991
- it("should enable transparent checkbox and show special features when private space is checked", () => {
992
- const privateSpaceCheckbox = element.querySelector("#private_space input[type='checkbox']");
993
- const isTransparentCheckbox = element.querySelector("#is_transparent input[type='checkbox']");
994
- const specialFeatures = element.querySelector("#special_features");
995
-
996
- // Check private space checkbox
997
- privateSpaceCheckbox.checked = true;
998
-
999
- controller.toggleDisabledHiddenFields();
1000
-
1001
- expect(isTransparentCheckbox.disabled).toBe(false);
1002
- expect(specialFeatures.style.display).toBe("block");
1003
- });
1004
-
1005
- it("should disable transparent checkbox and hide special features when private space is unchecked", () => {
1006
- const privateSpaceCheckbox = element.querySelector("#private_space input[type='checkbox']");
1007
- const isTransparentCheckbox = element.querySelector("#is_transparent input[type='checkbox']");
1008
- const specialFeatures = element.querySelector("#special_features");
1009
-
1010
- // Uncheck private space checkbox
1011
- privateSpaceCheckbox.checked = false;
1012
-
1013
- controller.toggleDisabledHiddenFields();
1014
-
1015
- expect(isTransparentCheckbox.disabled).toBe(true);
1016
- expect(specialFeatures.style.display).toBe("none");
1017
- });
1018
-
1019
- it("should handle missing elements gracefully", () => {
1020
- // Remove elements to test graceful handling
1021
- element.querySelector("#private_space").remove();
1022
- element.querySelector("#is_transparent").remove();
1023
- element.querySelector("#special_features").remove();
1024
-
1025
- expect(() => {
1026
- controller.toggleDisabledHiddenFields();
1027
- }).not.toThrow();
1028
- });
1029
-
1030
- it("should handle missing checkbox inside transparent div", () => {
1031
- // Remove checkbox from transparent div
1032
- const isTransparent = element.querySelector("#is_transparent");
1033
- isTransparent.innerHTML = "";
1034
-
1035
- expect(() => {
1036
- controller.toggleDisabledHiddenFields();
1037
- }).not.toThrow();
1038
- });
1039
921
  });
1040
922
 
1041
923
  describe("integration tests", () => {
@@ -1063,15 +945,4 @@ describe("AssemblyAdminController", () => {
1063
945
  });
1064
946
  });
1065
947
 
1066
- describe("edge cases", () => {
1067
- it("should handle elements with no checkbox inside", () => {
1068
- // Replace private space with div that has no checkbox
1069
- const privateSpace = element.querySelector("#private_space");
1070
- privateSpace.innerHTML = "<div>No checkbox here</div>";
1071
-
1072
- expect(() => {
1073
- controller.toggleDisabledHiddenFields();
1074
- }).not.toThrow();
1075
- });
1076
- });
1077
948
  });
@@ -2,14 +2,6 @@ import { Controller } from "@hotwired/stimulus"
2
2
 
3
3
  export default class extends Controller {
4
4
  connect() {
5
- const privateSpace = this.element.querySelector("#private_space");
6
-
7
- if (privateSpace) {
8
- privateSpace.addEventListener("change", this.toggleDisabledHiddenFields);
9
- }
10
- this.toggleDisabledHiddenFields();
11
-
12
- this.assignBehavior("assembly_type");
13
5
  this.assignBehavior("created_by");
14
6
  }
15
7
 
@@ -39,24 +31,4 @@ export default class extends Controller {
39
31
  showDiv.style.display = "block";
40
32
  }
41
33
  }
42
-
43
- toggleDisabledHiddenFields() {
44
- const privateSpace = document.getElementById("private_space");
45
- const isTransparent = document.getElementById("is_transparent");
46
- const specialFeatures = document.getElementById("special_features");
47
-
48
- const enabledPrivateSpace = privateSpace?.querySelector("input[type='checkbox']")?.checked;
49
- const isTransparentCheckbox = isTransparent?.querySelector("input[type='checkbox']");
50
-
51
- if (isTransparentCheckbox) {
52
- isTransparentCheckbox.disabled = (enabledPrivateSpace === false);
53
- }
54
-
55
- if (specialFeatures) {
56
- specialFeatures.style.display = enabledPrivateSpace
57
- ? "block"
58
- : "none";
59
- }
60
- }
61
-
62
34
  }