Skip to content

Commit

Permalink
Introduce sac section membership config, refs #472
Browse files Browse the repository at this point in the history
  • Loading branch information
mtnstar committed May 21, 2024
1 parent 677a916 commit c7a01da
Show file tree
Hide file tree
Showing 35 changed files with 975 additions and 68 deletions.
16 changes: 16 additions & 0 deletions app/abilities/sac_section_membership_config_ability.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# frozen_string_literal: true

# Copyright (c) 2024, Schweizer Alpen-Club. This file is part of
# hitobito_sac_cas and licensed under the Affero General Public License version 3
# or later. See the COPYING file at the top-level directory or at
# https://github.com/hitobito/hitobito_sac_cas

class SacSectionMembershipConfigAbility < AbilityDsl::Base

include AbilityDsl::Constraints::Group

on(SacSectionMembershipConfig) do
permission(:layer_and_below_full).may(:manage).in_same_layer_or_below
end

end
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,13 @@
- @attrs.each do |attr|
.row
.col-3.p-1
= SacMembershipConfig.human_attribute_name(attr)
= human_attribute_name(attr)
.col-3.p-1
.input-group.input-group-sm
= @form.input_field attr
- if currency?(attr)
%span.input-group-text
= t('global.currency')
- if years?(attr)
%span.input-group-text
= t('global.years')
16 changes: 16 additions & 0 deletions app/components/sac_membership_configs/field_rows_component.rb
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,26 @@
module SacMembershipConfigs
class FieldRowsComponent < ApplicationComponent

delegate :entry, :model_class, :column_type, to: :helpers

def initialize(form:, attrs:)
@form = form
@attrs = attrs
end

private

def currency?(attr)
column_type(entry, attr) == :decimal
end

def years?(attr)
attr.to_s.match?(/_age|_years/)
end

def human_attribute_name(attr)
model_class.human_attribute_name(attr)
end

end
end
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,5 @@
- @available_configs.each do |config|
%li.page-item{ class: [active?(config) && 'active'] }
= link_to_edit_config(config)
%li.page-item{ class: [@entry.new_record? && 'active'] }
%li.page-item{ class: [entry.new_record? && 'active'] }
= link_new_config
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,9 @@
module SacMembershipConfigs
class ValidFromSelectorComponent < ApplicationComponent

def initialize(entry:, available_configs:)
@entry = entry
delegate :entry, to: :helpers

def initialize(available_configs:)
@available_configs = available_configs
end

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# frozen_string_literal: true

# Copyright (c) 2024, Schweizer Alpen-Club. This file is part of
# hitobito_sac_cas and licensed under the Affero General Public License version 3
# or later. See the COPYING file at the top-level directory or at
# https://github.com/hitobito/hitobito_sac_cas

module SacSectionMembershipConfigs
class ReductionFieldRowsComponent < SacMembershipConfigs::FieldRowsComponent

def initialize(form:, attrs: [])
super
@attrs = [:sac_fee_exemption_for_honorary_members,
:sac_section_fee_exemption_for_honorary_members,
:sac_fee_exemption_for_benefited_members,
:sac_section_fee_exemption_for_benefited_members,
:reduction_amount,
:reduction_required_membership_years,
:reduction_required_age]

end

end
end
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
%ul.pagination.pagination-sm
- @available_configs.each do |config|
%li.page-item{ class: [active?(config) && 'active'] }
= link_to_edit_config(config)
%li.page-item{ class: [entry.new_record? && 'active'] }
= link_new_config
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
# frozen_string_literal: true

# Copyright (c) 2024, Schweizer Alpen-Club. This file is part of
# hitobito_sac_cas and licensed under the Affero General Public License version 3
# or later. See the COPYING file at the top-level directory or at
# https://github.com/hitobito/hitobito_sac_cas

module SacSectionMembershipConfigs
class ValidFromSelectorComponent < ApplicationComponent

delegate :entry, to: :helpers

def initialize(available_configs:, sac_section_id:)
@available_configs = available_configs
@sac_section_id = sac_section_id
end

private

def active?(config)
config.id == params[:id].to_i
end

def link_to_edit_config(config)
link_to(config.valid_from,
edit_group_sac_section_membership_config_path(group_id: config.group_id, id: config.id),
class: 'page-link')
end

def link_new_config
link_to(t('sac_section_membership_configs.global.link.add'),
new_group_sac_section_membership_config_path(group_id: helpers.params[:group_id]),
class: 'page-link')
end

end
end
10 changes: 9 additions & 1 deletion app/controllers/sac_membership_configs_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,8 @@ class SacMembershipConfigsController < CrudController
decorates :sac_membership_config
helper_method :cancel_url, :available_configs

before_action :assert_root_layer

def index
redirect_to latest_config_entry_path
end
Expand Down Expand Up @@ -99,10 +101,16 @@ def cancel_url
end

def available_configs
@available_configs ||= SacMembershipConfig.all.order(:valid_from)
@available_configs ||= SacMembershipConfig.order(:valid_from)
end

def latest_config
available_configs.last
end

def assert_root_layer
return if params[:group_id].to_i == Group.root.id

head :not_found
end
end
99 changes: 99 additions & 0 deletions app/controllers/sac_section_membership_configs_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
# frozen_string_literal: true

# Copyright (c) 2024, Schweizer Alpen-Club. This file is part of
# hitobito_sac_cas and licensed under the Affero General Public License version 3
# or later. See the COPYING file at the top-level directory or at
# https://github.com/hitobito/hitobito_sac_cas

class SacSectionMembershipConfigsController < CrudController
self.nesting = Group
self.permitted_attrs =[:valid_from,
:sac_section_fee_adult,
:sac_section_fee_family,
:sac_section_fee_youth,
:entry_fee_adult,
:entry_fee_family,
:entry_fee_youth,
:bulletin_postage_abroad,
:sac_fee_exemption_for_honorary_members,
:sac_section_fee_exemption_for_honorary_members,
:sac_fee_exemption_for_benefited_members,
:sac_section_fee_exemption_for_benefited_members,
:reduction_amount,
:reduction_required_membership_years,
:reduction_required_age]

decorates :sac_section_membership_config
helper_method :cancel_url, :available_configs, :sac_section

before_action :assert_sac_section_or_ortsgruppe

def index
redirect_to latest_config_entry_path
end

def show
redirect_to edit_path(params[:id])
end

private

def build_entry
if latest_config
attrs = latest_config.attributes
attrs.delete('id')
attrs[:valid_from] = latest_config.valid_from + 1
else
attrs = { valid_from: Time.zone.now.year }
end
SacSectionMembershipConfig.new(attrs)
end

def find_entry
SacSectionMembershipConfig.find(params[:id])
end

def latest_config_entry_path
if latest_config
edit_path(latest_config.id)
else
new_path
end
end

def edit_path(id)
helpers.edit_group_sac_section_membership_config_path(group_id: sac_section.id, id: id)
end

def new_path
helpers.new_group_sac_section_membership_config_path(group_id: sac_section.id)
end

def cancel_url
group_path(id: sac_section.id)
end

def available_configs
@available_configs ||=
SacSectionMembershipConfig.where(group_id: sac_section.id).order(:valid_from)
end

def latest_config
available_configs.last
end

def sac_section
@sac_section ||= fetch_sac_section
end

def fetch_sac_section
group_types = [Group::Sektion, Group::Ortsgruppe].collect(&:sti_name)
Group.find_by(id: params[:group_id], type: group_types)
end

def assert_sac_section_or_ortsgruppe
return if sac_section

head :not_found
end
end
15 changes: 15 additions & 0 deletions app/decorators/sac_section_membership_config_decorator.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# frozen_string_literal: true

# Copyright (c) 2024, Schweizer Alpen-Club. This file is part of
# hitobito_sac_cas and licensed under the Affero General Public License version 3
# or later. See the COPYING file at the top-level directory or at
# https://github.com/hitobito/hitobito_sac_cas.

class SacSectionMembershipConfigDecorator < ApplicationDecorator
decorates SacSectionMembershipConfig

def to_s
"#{@object.class.model_name.human} (#{valid_from})"
end

end
14 changes: 14 additions & 0 deletions app/helpers/sac_cas/dropdown/group_edit.rb
Original file line number Diff line number Diff line change
Expand Up @@ -13,5 +13,19 @@ def initialize(template, group)
template.group_sac_membership_configs_path(
group_id: Group.root.id))
end

if sac_section_or_ortsgruppe? &&
template.can?(:index, SacSectionMembershipConfig)
add_item(translate(:sac_section_membership_configs),
template.group_sac_section_membership_configs_path(
group_id: group.id))
end
end

private

def sac_section_or_ortsgruppe?
group_types = [Group::Sektion, Group::Ortsgruppe]
group_types.one? {|t| group.is_a?(t) }
end
end
12 changes: 12 additions & 0 deletions app/helpers/sheet/sac_section_membership_config.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# frozen_string_literal: true

# Copyright (c) 2024, Schweizer Alpen-Club. This file is part of
# hitobito_sac_cas and licensed under the Affero General Public License version 3
# or later. See the COPYING file at the top-level directory or at
# https://github.com/hitobito/hitobito_sac_cas

module Sheet
class SacSectionMembershipConfig < Base
self.parent_sheet = Sheet::Group
end
end
2 changes: 0 additions & 2 deletions app/models/group/ortsgruppe.rb
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,7 @@ class Group::Ortsgruppe < ::Group
{ greater_or_equal_to: 1863, smaller_than: Time.zone.now.year + 2 }

mounted_attr :section_canton, :string, enum: Cantons.short_name_strings.map(&:upcase)

mounted_attr :language, :string, enum: %w(DE FR IT), default: 'DE', null: false

mounted_attr :mitglied_termination_by_section_only, :boolean, default: false, null: false

def sac_cas_self_registration_url(host)
Expand Down
7 changes: 3 additions & 4 deletions app/models/group/sektion.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# frozen_string_literal: true

# Copyright (c) 2012-2023, Schweizer Alpen-Club. This file is part of
# Copyright (c) 2024, Schweizer Alpen-Club. This file is part of
# hitobito_sac_cas and licensed under the Affero General Public License version 3
# or later. See the COPYING file at the top-level directory or at
# https://github.com/hitobito/hitobito_sac_cas.
Expand Down Expand Up @@ -30,13 +30,12 @@ class Group::Sektion < ::Group
validates :foundation_year,
numericality:
{ greater_or_equal_to: 1863, smaller_than: Time.zone.now.year + 2 }

mounted_attr :section_canton, :string, enum: Cantons.short_name_strings.map(&:upcase)

mounted_attr :language, :string, enum: %w(DE FR IT), default: 'DE', null: false

mounted_attr :mitglied_termination_by_section_only, :boolean, default: false, null: false

has_many :sektion_membership_configs

def sac_cas_self_registration_url(host)
Groups::SektionSelfRegistrationLink.new(self, host).url
end
Expand Down

0 comments on commit c7a01da

Please sign in to comment.